Skip to content
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

feat(useExplicitType): support explicit function argument types #4463

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

kaykdm
Copy link
Contributor

@kaykdm kaykdm commented Nov 4, 2024

Summary

related: #2017

This PR adds support for enforcing explicit type annotations on arguments in all functions and class methods. The rule is inspired by the explicit-module-boundary-types rule, but it expands coverage beyond exported functions to include all functions and methods within a class.

@github-actions github-actions bot added A-CLI Area: CLI A-Project Area: project A-Linter Area: linter L-JavaScript Language: JavaScript and super languages labels Nov 4, 2024
Copy link

codspeed-hq bot commented Nov 4, 2024

CodSpeed Performance Report

Merging #4463 will degrade performances by 9.81%

Comparing kaykdm:explicit-argument-types (925a373) with main (3f152b3)

Summary

⚡ 1 improvements
❌ 1 regressions
✅ 95 untouched benchmarks

⚠️ Please fix the performance issues or acknowledge them on CodSpeed.

Benchmarks breakdown

Benchmark main kaykdm:explicit-argument-types Change
pure_9395922602181450299.css[uncached] 4 ms 4.4 ms -9.81%
react.production.min_3378072959512366797.js[cached] 2 ms 1.8 ms +6.32%

}
}

declare_node_union! {
pub AnyJsFunctionWithReturnType = AnyJsFunction | JsMethodClassMember | JsMethodObjectMember | JsGetterClassMember | JsGetterObjectMember
pub AnyJsFunctionWithReturnTypeOrJsParameters = AnyJsFunction | JsMethodClassMember | JsMethodObjectMember | JsGetterClassMember | JsGetterObjectMember | JsParameters
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've just noticed that some types are missing for checking if the return type is explicitly set:

  • TsMethodSignatureTypeMember
  • TsCallSignatureTypeMember
  • TsMethodSignatureClassMember
  • TsSetterSignatureClassMember
  • TsDeclareFunctionDeclaration
  • TsDeclareFunctionExportDefaultDeclaration

I wonder if directly matching against JsParameters is a good idea. I see two possible alternative approaches:

  1. matching directly against JsFormalParameter, JsRestParameter, and TsThisParameter
  2. matching against functions with parameters (We already have most of them, we need to add setter and constructors).

Personally I could choose (2) because this allows us to issue a single diagnostic when a parameter or a return type is absent on a function.
Also, similarly to return type, we should ignore callbacks.

Besides, we should think to a better name for this union because we will have to add properties and top-level variables. Maybe AnyJsTypeableEntity? Have you a better suggestion?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the review, and apologies for the late response.

I've just noticed that some types are missing for checking if the return type is explicitly set:

I understand. I'll create a separate for this this.

I wonder if directly matching against JsParameters is a good idea. I see two possible alternative approaches:

I see your point. I'll revisit this after implementing the missing return types.

Maybe AnyJsTypeableEntity? Do you have a better suggestion?

AnyJsTypeableEntity looks good to me.

For now, I will make this PR draft.


enum UseExplicitTypeCause {
MissingReturnType,
MissingArgumentnType(String),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Usually we try to avoid allocating a string. You could directly take the token:

Suggested change
MissingArgumentnType(String),
MissingArgumentnType(JsSyntaxToken),

In this case we could rewrite UseExplicitTypeState as:

pub enum UseExplicitTypeState {
    MissingReturnType(TextRange),
    MissingArgumentnType(JsSyntaxToken),
}

Because we can get the range from a token.

Comment on lines +672 to +673
for p in parameters.items() {
let param = p.ok()?;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We could avoid returning as soon as we met an error by iterating only over node without errors:

Suggested change
for p in parameters.items() {
let param = p.ok()?;
for p in parameters.items().into_iter().flatten() {

fn check_function_parameters_type(parameters: &JsParameters) -> Option<UseExplicitTypeState> {
for p in parameters.items() {
let param = p.ok()?;
let formal_param = param.as_any_js_formal_parameter()?;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should certainly handle the other parameter kinds (rest parameter and this parameter).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-CLI Area: CLI A-Linter Area: linter A-Project Area: project L-JavaScript Language: JavaScript and super languages
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants