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

Implement some parameter name check cop #3666

Closed
bbatsov opened this issue Oct 22, 2016 · 8 comments
Closed

Implement some parameter name check cop #3666

bbatsov opened this issue Oct 22, 2016 · 8 comments

Comments

@bbatsov
Copy link
Collaborator

bbatsov commented Oct 22, 2016

People keep referring to Reek's Uncommunicative Variable Name check as one of the big omissions in RuboCop. We didn't include it initially, as it can't be implemented reliably (some short names are pretty meaningful - like x and y when dealing with points), but I guess if the users want it we should give it to them.

This cop should act on both method and block param names.

@palkan
Copy link
Contributor

palkan commented Oct 25, 2016

@bbatsov

Are we going to use the same checks as Reek does?
More precisely:

  • 1-letter names
  • capital letters
  • names ending with a number.

I'm not sure about "names beginning with an underscore" because it's a common pattern for naming unused vars when overriding methods (kinda Erlang style).

And what about this hash.each_key { |k| p k }?
Block params are very likely to be one-letters. I guess, we should check them only for other offenses (capitals, numbers).

And I think, we should have a flexible configuration here, smth like:

Style/UncommunicativeName:
  # Do not report offenses on the provided names
  IgnoreNames: []

@bbatsov
Copy link
Collaborator Author

bbatsov commented Oct 26, 2016

I'm not sure about "names beginning with an underscore" because it's a common pattern for naming unused vars when overriding methods (kinda Erlang style).

I wouldn't check about this.

And what about this hash.each_key { |k| p k }?
Block params are very likely to be one-letters. I guess, we should check them only for other offenses (capitals, numbers).

Might make sense to have 2 cops for method params and block param names. At any rate the cop should have a rather flexible configuration.

@palkan
Copy link
Contributor

palkan commented Oct 26, 2016

Might make sense to have 2 cops for method params and block param names. At any rate the cop should have a rather flexible configuration.

And what about variable names? Yet another cop?

@garettarrowood
Copy link
Contributor

garettarrowood commented Nov 28, 2017

I've been thinking about this and would like to tackle it. Here is my proposal:

This issue can represent the addition of 2 Cops.

  1. Style/UncommunicativeBlockParamName
  2. Style/UncommunicativeMethodArgName

After those, we can discuss the possibility of other reek Uncommunicative Names. Although, at first inspection they look like they are possibly overkill.

To accommodate meaningful single char names, configuration could be added to whitelist particular letters. OR we can just allow them all for block params & never for method. I'd love to go as far as including a little strong typing here, by checking that the class of a single char var match a value passed to configuration. But we can't and shouldn't do that in RuboCop.

Is there any appropriate place in Rubocop to allow code owners to specify what Class those single chars should represent but not enforce it. e.x. { h: [Hash], i: [Integer, Numeric], c: [CustomClass], etc. }? I think this is just wishful thinking on my part, but wanted to bring up the possibility.

@bbatsov @palkan - Any last thoughts on this?

@palkan
Copy link
Contributor

palkan commented Nov 28, 2017

OR we can just allow them all for block params & never for method

I prefer this way. It's very common to have single char (or less meaningful) block params names, especially for keys/values (|k|, |k, v|).

Methods are likely to have (and, IMO, should have) more descriptive arguments names though.

Is there any appropriate place in Rubocop to allow code owners to specify what Class those single chars should represent but not enforce it

It can be configurable in Rubocop, but I think in most cases there gonna be the whole alphabet) Using the first char of a class name is popular.

Of course, having good list of defaults (k, v, h, i, j, t, for example) and disable this cop by default still make sense.

@garettarrowood
Copy link
Contributor

garettarrowood commented Nov 28, 2017

So to recap:

Style/UncommunicativeBlockParamName -

  1. No capital letters
  2. No names ending in numbers
  3. Config that allows one to whitelist param names that break these rules.

Style/UncommunicativeMethodArgName -

  1. No single letter names
  2. No capital letters
  3. No names ending in numbers
  4. Config that allows one to whitelist arg names that break these rules.

And disable this cop in the rubocop code base by default.

@palkan
Copy link
Contributor

palkan commented Nov 28, 2017

Style/UncommunicativeBlockParamName -

  1. No capital letters
  2. No names ending in numbers
  3. Config that allows one to whitelist param names that break these rules.

And I think:

  1. Predefined list of accepted names (such as k, v, etc); not sure that that should be a default whitelist, maybe, a separate list (always included).

And according to:

No single letter names

What about having a parameter MinArgNameLength to make it even more configurable. And, I think, default value of 3 is better (2-letter names? not sure).

@garettarrowood
Copy link
Contributor

Ok. Ready to start crafting this over the next few days. I'm still not sold on passing a predefined list of exceptions to the rule. But I really like the idea of a MinArgNameLength and think something equivalent would work well for the blocks as a MinParamNameLength. MinArg could default to 3, but MinParam could default to 1, making it more up to the users to actively enforce block param length restrictions.

In this first pass, I'm going to forego "Config that allows one to whitelist param names that break these rules." Since this is addition and not a replacement of existing functionality, let's get something that makes sense up and working. And disable it by default. Then we can then raise additional issues to add more configuration, whatever that may be.

garettarrowood added a commit to garettarrowood/rubocop that referenced this issue Dec 28, 2017
garettarrowood added a commit to garettarrowood/rubocop that referenced this issue Dec 28, 2017
garettarrowood added a commit to garettarrowood/rubocop that referenced this issue Dec 28, 2017
garettarrowood added a commit to garettarrowood/rubocop that referenced this issue Dec 28, 2017
garettarrowood added a commit to garettarrowood/rubocop that referenced this issue Dec 29, 2017
koic added a commit to koic/rubocop that referenced this issue Jan 7, 2018
Follow up of rubocop#5410.

This PR fixes the following error on Travis CI.

```console
% bundle exec rspec ./spec/project_spec.rb
Run options: include {:focus=>true}

All examples were filtered out; ignoring {:focus=>true}

Randomized with seed 45488
..............F.F

Failures:

  1) RuboCop Project changelog entry body ends with a punctuation
     Failure/Error: expect(bodies).to all(match(/[\.\!]$/))

       expected ["Add new `` cop.", "Add new `` cop.", "Add new ``
       cop.", "Add new `` cop.", "Add new `` cop.", "Add ...nclosed in
       braces are not noticed.", "Received malformed format string
       ArgumentError from rubocop."] to all match /[\.\!]$/

          object at index 18 failed to match:
             expected "Fix ``'s false positive with a method
             call with arguments. ([@pocke][]) " to match /[\.\!]$/
     # ./spec/project_spec.rb:174:in `block (5 levels) in <top (required)>'

  2) RuboCop Project changelog entry after version 0.14.0 has a link to
  the contributors at the end
     Failure/Error: expect(entries).to all(match(/\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/))

       expected ["* [rubocop#3666](rubocop#3666): Add new
       `Naming/UncommunicativeBlockPara...552): `RaiseArgs` allows
       exception constructor calls with more than one 1
       argument. ([@bbatsov][])"] to all match /\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/

          object at index 18 failed to match:
             expected "* [rubocop#5393](rubocop#5393):
             Fix `Rails/Delegate`'s false positive with a
             method call with arguments. ([@pocke][]) " to
             match /\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/
     # ./spec/project_spec.rb:123:in `block (5 levels) in <top (required)>'

Finished in 1.36 seconds (files took 1.07 seconds to load)
17 examples, 2 failures

Failed examples:

rspec ./spec/project_spec.rb:173 # RuboCop Project changelog entry body
ends with a punctuation
rspec ./spec/project_spec.rb:122 # RuboCop Project changelog entry after
version 0.14.0 has a link to the contributors at the end
```

https://travis-ci.org/bbatsov/rubocop/jobs/325980721#L1146-L1162
bbatsov pushed a commit that referenced this issue Jan 7, 2018
Follow up of #5410.

This PR fixes the following error on Travis CI.

```console
% bundle exec rspec ./spec/project_spec.rb
Run options: include {:focus=>true}

All examples were filtered out; ignoring {:focus=>true}

Randomized with seed 45488
..............F.F

Failures:

  1) RuboCop Project changelog entry body ends with a punctuation
     Failure/Error: expect(bodies).to all(match(/[\.\!]$/))

       expected ["Add new `` cop.", "Add new `` cop.", "Add new ``
       cop.", "Add new `` cop.", "Add new `` cop.", "Add ...nclosed in
       braces are not noticed.", "Received malformed format string
       ArgumentError from rubocop."] to all match /[\.\!]$/

          object at index 18 failed to match:
             expected "Fix ``'s false positive with a method
             call with arguments. ([@pocke][]) " to match /[\.\!]$/
     # ./spec/project_spec.rb:174:in `block (5 levels) in <top (required)>'

  2) RuboCop Project changelog entry after version 0.14.0 has a link to
  the contributors at the end
     Failure/Error: expect(entries).to all(match(/\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/))

       expected ["* [#3666](#3666): Add new
       `Naming/UncommunicativeBlockPara...552): `RaiseArgs` allows
       exception constructor calls with more than one 1
       argument. ([@bbatsov][])"] to all match /\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/

          object at index 18 failed to match:
             expected "* [#5393](#5393):
             Fix `Rails/Delegate`'s false positive with a
             method call with arguments. ([@pocke][]) " to
             match /\(\[@\S+\]\[\](?:, \[@\S+\]\[\])*\)$/
     # ./spec/project_spec.rb:123:in `block (5 levels) in <top (required)>'

Finished in 1.36 seconds (files took 1.07 seconds to load)
17 examples, 2 failures

Failed examples:

rspec ./spec/project_spec.rb:173 # RuboCop Project changelog entry body
ends with a punctuation
rspec ./spec/project_spec.rb:122 # RuboCop Project changelog entry after
version 0.14.0 has a link to the contributors at the end
```

https://travis-ci.org/bbatsov/rubocop/jobs/325980721#L1146-L1162
This was referenced Mar 21, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants