Skip to content

Commit

Permalink
[Fix #8063] Add new AllowedNames option for `Naming/ClassAndModuleC…
Browse files Browse the repository at this point in the history
…amelCase`

Closes #8063
  • Loading branch information
tejasbubane authored and bbatsov committed May 31, 2020
1 parent f34cc0e commit 9ffd1cc
Show file tree
Hide file tree
Showing 5 changed files with 58 additions and 5 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Expand Up @@ -8,6 +8,7 @@
* [#8069](https://github.com/rubocop-hq/rubocop/issues/8069): New option for `expect_offense` to help format offense templates. ([@marcandre][])
* [#7908](https://github.com/rubocop-hq/rubocop/pull/7908): Add new `Style/RedundantRegexpEscape` cop. ([@owst][])
* [#7978](https://github.com/rubocop-hq/rubocop/pull/7978): Add new option `OnlyFor` to the `Bundler/GemComment` cop. ([@ric2b][])
* [#8063](https://github.com/rubocop-hq/rubocop/issues/8063): Add new `AllowedNames` option for `Naming/ClassAndModuleCamelCase`. ([@tejasbubane][])

### Bug fixes

Expand Down
5 changes: 5 additions & 0 deletions config/default.yml
Expand Up @@ -2006,6 +2006,11 @@ Naming/ClassAndModuleCamelCase:
StyleGuide: '#camelcase-classes'
Enabled: true
VersionAdded: '0.50'
VersionChanged: '0.85'
# Allowed class/module names can be specified here.
# These can be full or part of the name.
AllowedNames:
- module_parent

Naming/ConstantName:
Description: 'Constants should use SCREAMING_SNAKE_CASE.'
Expand Down
20 changes: 19 additions & 1 deletion docs/modules/ROOT/pages/cops_naming.adoc
Expand Up @@ -200,12 +200,18 @@ baz { |age, height, gender| do_stuff(age, height, gender) }
| Yes
| No
| 0.50
| -
| 0.85
|===

This cop checks for class and module names with
an underscore in them.

`AllowedNames` config takes an array of permitted names.
Its default value is `['module_parent']`.
These names can be full class/module names or part of the name.
eg. Adding `my_class` to the `AllowedNames` config will allow names like
`my_class`, `my_class::User`, `App::my_class`, `App::my_class::User`, etc.

=== Examples

[source,ruby]
Expand All @@ -221,8 +227,20 @@ class MyClass
end
module MyModule
end
class module_parent::MyModule
end
----

=== Configurable attributes

|===
| Name | Default value | Configurable values

| AllowedNames
| `module_parent`
| Array
|===

=== References

* https://rubystyle.guide#camelcase-classes
Expand Down
12 changes: 11 additions & 1 deletion lib/rubocop/cop/naming/class_and_module_camel_case.rb
Expand Up @@ -6,6 +6,12 @@ module Naming
# This cop checks for class and module names with
# an underscore in them.
#
# `AllowedNames` config takes an array of permitted names.
# Its default value is `['module_parent']`.
# These names can be full class/module names or part of the name.
# eg. Adding `my_class` to the `AllowedNames` config will allow names like
# `my_class`, `my_class::User`, `App::my_class`, `App::my_class::User`, etc.
#
# @example
# # bad
# class My_Class
Expand All @@ -18,11 +24,15 @@ module Naming
# end
# module MyModule
# end
# class module_parent::MyModule
# end
class ClassAndModuleCamelCase < Cop
MSG = 'Use CamelCase for classes and modules.'

def on_class(node)
return unless /_/.match?(node.loc.name.source)
allowed = /#{cop_config['AllowedNames'].join('|')}/
name = node.loc.name.source.gsub(allowed, '')
return unless /_/.match?(name)

add_offense(node, location: :name)
end
Expand Down
25 changes: 22 additions & 3 deletions spec/rubocop/cop/naming/class_and_module_camel_case_spec.rb
@@ -1,8 +1,6 @@
# frozen_string_literal: true

RSpec.describe RuboCop::Cop::Naming::ClassAndModuleCamelCase do
subject(:cop) { described_class.new }

RSpec.describe RuboCop::Cop::Naming::ClassAndModuleCamelCase, :config do
it 'registers an offense for underscore in class and module name' do
expect_offense(<<~RUBY)
class My_Class
Expand Down Expand Up @@ -36,4 +34,25 @@ module Mine
end
RUBY
end

it 'allows module_parent method' do
expect_no_offenses(<<~RUBY)
class module_parent::MyClass
end
RUBY
end

context 'custom allowed names' do
let(:cop_config) { { 'AllowedNames' => %w[getter_class setter_class] } }

it 'does not register offense for multiple allowed names' do
expect_no_offenses(<<~RUBY)
class getter_class::MyClass
end
class setter_class::MyClass
end
RUBY
end
end
end

0 comments on commit 9ffd1cc

Please sign in to comment.