-
Notifications
You must be signed in to change notification settings - Fork 12.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. Weβll occasionally send you account related emails.
Already on GitHub? Sign in to your account
New flag --noImplicitAbstractOverride
which mandates the use of override
when implementing an abstract method
#47250
Comments
I found myself here after having enabled |
I am rather ok with this !, sugar view i always welcome for productivity and ts is a powerful productivity tool ! |
I see the problem as the lack of identifiability of the inherited abstract methods. |
I would wish for this feature, as well, and I would like to add the following scenario that applies especially for larger teams/projects: Developer A creates abstract class Other developers derive various subclasses from Now, as it turns out, several of these classes share the same implementation of Result: Suddenly, all of the existing subclasses of Undesirable consequences: Just two options, both of which should not be necessary, and could have been prevented with the proposed
|
I agree with this. I think the |
Just ran into this issue myself, I'd love to see it added. What needs to be done to get it accepted? |
@djmisterjon
Would you mind having a look at my use case and share your thoughts? My motivation for supporting this feature request is specifically that I do not want to have to change my subclass code depending on whether I am overriding an abstract (i.e. non-implemented, must-override) or a virtual (i.e. implemented, but overrideable) method of the parent class. Same as in C#, if you will, where |
I'd really appreciate this - requiring the use of the override keyword makes it easier to see which methods are inherited. |
Just found this issue after wondering why noImplicitOverride doesnt work. If typescript has a way to force override, there should be a way to enable it for everything. |
Bumping this question:
I'd be happy to take on whatever additional work needs to be done if given direction. Does the proposal need more details or motivating examples? Do we just need to be patient? There hasn't been any activity by any of the contributors since the initial filing well over a year ago. |
I would also vote for the addition of this flag. |
Interesting... I came here to figure out how to flag use of unnecessary export abstract class Foo {
public abstract bar(): boolean;
public qux(): void {
console.log('LOL');
}
}
export class Baz extends Foo {
// Expected warning/error for override keyword here. It's no override. It's an initial implementation.
public override bar(): boolean {
return true;
}
// This is correct. Because it's an override.
public override qux(): void {
console.log('ROFL');
}
} Here I would remove Currently you can add or omit the override without any issues. I understand the idea behind require |
In the context of your example, recognizing that bar originates from the parent class provides a crucial insight. The inclusion of the override modifier serves as a clear indicator that this method is inherent to the parent class rather than introducing new functionalities. Therefore, I think it is better to force override, as it makes more logical sense, even if it is technically not overriding anything. It is also how java handles the |
For example, if you have: export abstract class Animal {
public abstract makeNoise();
public makeLotsOfNoise() {
setInterval(() => this.makeNoise(), 100);
}
} And in another file, you have:
For the However, for non- |
Is it not? It changes the behaviour of something declared (and thus callable) on the base class. In this case, from "having undefined behaviour" (even though in practice, you won't get there, because it doesn't compile) to "doing whatever is implemented in the overridden method.
At least in my view, a part of this is that it should not matter to the subclass whether whatever method it overrides was abstract or virtual in the base class. The base class should be able to e.g. replace an abstract method with a virtual method at a later time without breaking any of the already existing subclasses. It's no conceptual change from the subclass's point of view - the subclass author just needs to know they are supplying behaviour that might be invoked via the base class. Maybe you can argue
If you have no marker on the method that implements an abstract method, how can the compiler know the abstract method implemented by a given method X has been removed, rather than the method X simply being a newly introduced method in the class at hand?
Well, in C#, it's the |
In most languages, (e.g Kotlin, C#, Java), "override" not only means we meant to override some method but it also warns the user (if he's not prevented from compiling) if the method doesn't override nor implement anything. I think the discussion should be about the meaning of the "override" word which may not be appropriate. Maybe we could use an "implements" keyword, but adding further keywords has to be balanced by the language complexity and learning curve. |
This is the critical thing that's missing in TypeScript without
Python similarly has an override annotation for static type checking with the same intent:
And explicitly mentions a strict mode that requires @override:
I don't see a need to endlessly work on defining what "override" means. C#, Kotlin, Scala, and Swift always require explicit overrides. Override has clear semantics and precedence across other languages that already match TypeScript. The only part that's missing is a warning or error if the user implicitly overrides a base class/interface method. Like Python, we can make it opt-in and possibly add it to |
I completely agree with you, I just provided another point of view that fhaag may find acceptable. |
For the use case described above, I do not really care what the keyword is, as long as it is the same keyword no matter whether the inherited method was virtual or abstract. |
My team just ran into this, and I wish we could accept this proposal. It looks like there was already a PR the didn't go anywhere in #51357. What will it take to get momentum on this issue? 50 upvotes and a fix already proposed isn't enough? |
I would love this. I hope it gets accepted; seems like an easy win to me. |
Wow, I honestly can't believe it has been just about 3 years since this issue was opened and no movement from maintainers yet... |
Suggestion
π Search Terms
flag override implicit noImplicitOverride abstract
β Viability Checklist
My suggestion meets these guidelines:
β Suggestion
Currently, when
--noImplicitOverride
is enabled, overriding (or implementing) an abstract method does not require the use of keywordoverride
.I suggest adding a new flag
--noImplicitAbstractOverride
, which, when enabled in conjunction with--noImplicitOverride
, will also requireoverride
when implementing an abstract method.π Motivating Example
In issue #44457, @RyanCavanaugh explained the rationale behind
--noImplicitOverride
not covering implementing abstract methods is that--noImplicitOverride
is designed to prevent typos. Since not implementing an abstract method will already result in an error, it is not necessary to let--noImplicitOverride
also cover that case.However, that is only one use case for the
override
keyword. In fact, I don't think--noImplicitOverride
has ever helped me catch any typo bugs that way, thanks to the modern IDE I use, which automatically fills in method names when I am about to override a method. (I am not saying it is not helpful, though.)In my opinion, one of the most valuable functionality that
override
provides is explicitly telling the programmers which methods are from the the super class and which methods are new. This is especially valuable when reading code of a class in a complicated inheritance tree.Ideally, I think such behavior should be a part of
--noImplicitOverride
. However, since that ship has already sailed, it seems a new flag is required.Side note: I do realize that implementing an abstract method is technically not really overriding anything. However, by this line of reasoning, when implementing abstract methods
override
should be completely disallowed instead of optional.(Hey, the person giving me thumbs down, it will be better if you can come out and explain why you don't agree with me.)
The text was updated successfully, but these errors were encountered: