eslint-plugin-functional icon indicating copy to clipboard operation
eslint-plugin-functional copied to clipboard

feat(functional-parameters): add support for ignoring selector prefixes

Open RebeccaStevens opened this issue 4 years ago • 5 comments
trafficstars

re #207 re #244

This allows for ignoring functions where one of the given selectors matches the parent node in the AST of the function's node. For more information see ESLint Selectors.

Example:

With the following config:

{
  "enforceParameterCount": "exactlyOne",
  "ignorePrefixSelector": "CallExpression[callee.property.name='reduce']"
},

The following inline callback won't be flaged:

const sum = [1, 2, 3].reduce(
  (carry, current) => carry + current,
  0
);`,

RebeccaStevens avatar Aug 11 '21 15:08 RebeccaStevens

@jonaskello Could I get your opinion on this feature. I'm not too sure on it now after implementing it.

The use-case I'm trying to solve, is to allow for the use of Array.prototype.reduce while still enforcing that all other functions abided by the exactly one parameter enforcement.

Currently the only way to try and ignore "reduce" calls is with a regex expression but that's really not practical or very robust so a better solution is required. However, I'm not sure if this approach is the best.

I initially thought this would be a nice way to do it as this same sort of "ignore via selector" concept could easily be brought into other rules. Although this is still true, I don't think this approach fully solves the issue properly as there is no type checking taking place. All object.reduce() calls will be ignored, regardless of whether object is an array or not. However, trying to address this would then likely make the option not very flexible.

RebeccaStevens avatar Aug 11 '21 16:08 RebeccaStevens

I did not know about selectors. They seem like a really nice feature, thanks for pointing them out :-). Reminds me of CodeQL. I agree that implementing selectors seems like a really good idea. At least at first look they seem like a huge improvement over regexp for solving the ignore problem in all rules. Several use-cases comes to mind. For example I have a case where I would like to ignore readonly checks of a tuple type that is a generic type parameter of a specific generic type but only when it is a return type from an iterator function :-).

So if I understand it correctly you can only select on the AST and it does not include type information (but I guess it do contain type declaration nodes?). Therefore you cannot determine if .reduce() is a call on an array or any other object. However according to the description in #207 it seems that it was not possible at all to ignore all .reduce() calls so it would still be an improvement? I would probably be willing to make the tradeoff to ignore all reduce()calls and try not to name anything to reduce() that does not have a standard reduce signature. This would be the effect if regexp had worked anyway? The alternative would be to add ignore comments on every reduce() call which is much worse IMO. Another alternative would of course be to create more specific and advanced ignore options for the rule but I think we can perhaps add that later if needed.

jonaskello avatar Aug 12 '21 06:08 jonaskello

Looking a bit further there seems to be a CodeQL library for typescript that can query on both type annotations and actual types if I understand correctly. However selectors seems more native to eslint so they are probably a better choice here.

jonaskello avatar Aug 12 '21 06:08 jonaskello

Do you think this current PR should be merged as is? (well, after I fixup some small mistakes in the docs)

RebeccaStevens avatar Aug 12 '21 06:08 RebeccaStevens

Codecov Report

Merging #257 (af3cbcc) into main (9a50dda) will increase coverage by 0.11%. The diff coverage is 100.00%.

@@            Coverage Diff             @@
##             main     #257      +/-   ##
==========================================
+ Coverage   93.73%   93.84%   +0.11%     
==========================================
  Files          34       34              
  Lines         782      796      +14     
  Branches      199      202       +3     
==========================================
+ Hits          733      747      +14     
  Misses         24       24              
  Partials       25       25              
Flag Coverage Δ
4.0.2 93.71% <100.00%> (+0.11%) :arrow_up:
JS 93.46% <100.00%> (+0.11%) :arrow_up:
latest 93.46% <100.00%> (+0.11%) :arrow_up:
next 93.46% <100.00%> (+0.11%) :arrow_up:

Flags with carried forward coverage won't be shown. Click here to find out more.

Impacted Files Coverage Δ
src/common/ignore-options.ts 100.00% <100.00%> (ø)
src/rules/functional-parameters.ts 97.56% <100.00%> (+0.68%) :arrow_up:
src/util/rule.ts 88.57% <100.00%> (+1.47%) :arrow_up:

:mega: We’re building smart automated test selection to slash your CI/CD build times. Learn more

codecov[bot] avatar Sep 20 '22 12:09 codecov[bot]

:tada: This PR is included in version 4.4.0 :tada:

The release is available on:

Your semantic-release bot :package::rocket:

github-actions[bot] avatar Sep 20 '22 12:09 github-actions[bot]