= Configuration

The behavior of RuboCop can be controlled via the
https://github.com/rubocop/rubocop/blob/master/.rubocop.yml[.rubocop.yml]
configuration file. It makes it possible to enable/disable certain cops
(checks) and to alter their behavior if they accept any parameters. The file
can be placed in your home directory, XDG config directory, or in some project
directory.

The file has the following format:

[source,yaml]
----
inherit_from: ../.rubocop.yml

Style/Encoding:
  Enabled: false

Layout/LineLength:
  Max: 99
----

This page covers general configuration topics. For more specific areas, see:

* xref:configuration/inheritance.adoc[Inheritance] — `inherit_from`, `inherit_gem`, and `inherit_mode`
* xref:configuration/include_exclude.adoc[Including and Excluding Files] — controlling which files RuboCop inspects
* xref:configuration/cop_settings.adoc[Configuring Cops] — `Enabled`, `Severity`, `AutoCorrect`, `AllowedMethods`, `AllowedPatterns`

== Config file locations

RuboCop will start looking for the configuration file in the directory
where the inspected file is and continue its way up to the root directory.

If it cannot be found until reaching the project's root directory, then it will
be searched for in the https://dot-config.github.io[.config directory of the project root]
and the user's global config locations. The user's global config locations consist of a
dotfile or a config file inside the https://specifications.freedesktop.org/basedir-spec/latest/index.html[XDG Base Directory
specification].

* `.config/.rubocop.yml` or `.config/rubocop/config.yml` at the project root
* `~/.rubocop.yml`
* `$XDG_CONFIG_HOME/rubocop/config.yml` (expands to `~/.config/rubocop/config.yml`
if `$XDG_CONFIG_HOME` is not set)

If both files exist, the dotfile will be selected.

As an example, if RuboCop is invoked from inside `/path/to/project/lib/utils`,
then RuboCop will use the config as specified inside the first of the following
files:

* `/path/to/project/lib/utils/.rubocop.yml`
* `/path/to/project/lib/.rubocop.yml`
* `/path/to/project/.rubocop.yml`
* `/path/to/project/.config/.rubocop.yml`
* `/path/to/project/.config/rubocop/config.yml`
* `~/.rubocop.yml`
* `~/.config/rubocop/config.yml`
* https://github.com/rubocop/rubocop/blob/master/config/default.yml[RuboCop's default configuration]

NOTE: All the previous logic does not apply if a specific configuration file is passed
on the command line through the `--config` flag. In that case, the resolved
configuration file will be the one passed to the CLI.

== Pre-processing

Configuration files are pre-processed using the ERB templating mechanism. This
makes it possible to add dynamic content that will be evaluated when the
configuration file is read. For example, you could let RuboCop ignore all files
ignored by Git.

[source,yaml]
----
AllCops:
  Exclude:
  <% `git status --ignored --porcelain`.lines.grep(/^!! /).each do |path| %>
    - <%= path.sub(/^!! /, '').sub(/\/$/, '/**/*') %>
  <% end %>
----

[[defaults]]
== Defaults

The file https://github.com/rubocop/rubocop/blob/master/config/default.yml[config/default.yml] under the RuboCop home directory contains the
default settings that all configurations inherit from. Project and personal
`.rubocop.yml` files need only make settings that are different from the
default ones. If there is no `.rubocop.yml` file in the project, home or XDG
directories, `config/default.yml` will be used.

== Setting the target Ruby version

Some checks are dependent on the version of the Ruby interpreter which the
inspected code must run on. For example, enforcing using Ruby 2.6+ endless
ranges `foo[n..]` rather than `foo[n..-1]` can help make your code shorter and
more consistent... _unless_ it must run on e.g. Ruby 2.5.

Users may let RuboCop know the oldest version of Ruby which your project
supports with:

[source,yaml]
----
AllCops:
  TargetRubyVersion: 2.5
----

If a `TargetRubyVersion` is not specified in your config, then RuboCop will
check your project for a series of other files where the Ruby version may be
specified already. The files that will be checked are (in this order):
`*.gemspec`, `.ruby-version`, `mise.toml`, `.tool-versions`, and `Gemfile.lock`.

The target ruby version may also be specified by setting the
`RUBOCOP_TARGET_RUBY_VERSION` environment variable to the desired version: for
example, running `RUBOCOP_TARGET_RUBY_VERSION=3.3 rubocop` will
run rubocop with a target ruby version of 3.3. Using this environment variable
will override all other sources of version information, including
`.rubocop.yml`.

If a target Ruby version cannot be found via any of the above sources, then a
default target Ruby version will be used.

=== Finding target Ruby in a `*.gemspec` file

In order for RuboCop to parse a `*.gemspec` file's `required_ruby_version`, the
Ruby version must be specified using one of these syntaxes:

1. a string range, e.g. `'~> 3.2.0'` or `'>= 3.2.2'`
2. an array of strings, e.g. `['>= 3.0.0', '< 3.4.0']`
3. a `Gem::Requirement`, e.g. `Gem::Requirement.new('>= 3.1.2')`

If a `*.gemspec` file specifies a range of supported Ruby versions via any of
these means, then the greater of the following Ruby versions will be used:

- the lowest Ruby version that is compatible with your specified range
- the lowest version of Ruby that is still supported by your version of RuboCop

If a `*.gemspec` file defines its `required_ruby_version` dynamically (e.g. by
reading from a `.ruby-version` file, via an environment variable, referencing a
constant or local variable, etc), then RuboCop will _not_ detect that Ruby
version, and will instead try to find a target Ruby version elsewhere.

== Setting the parser engine

NOTE: The parser engine configuration was introduced in RuboCop 1.62. Since RuboCop 1.75, RuboCop chooses the parser engine automatically, so you don't need to configure it yourself.

RuboCop allows switching the backend parser by specifying either
`parser_whitequark` or `parser_prism` as the value for the `ParserEngine`.

Here are the parsers used as backends for each value:

- `ParserEngine: default`
- `ParserEngine: parser_whitequark` ... https://github.com/whitequark/parser
- `ParserEngine: parser_prism` ... https://github.com/ruby/prism (`Prism::Translation::Parser`)

`parser_whitequark` can analyze source code from Ruby 2.0 until Ruby 3.4:

[source,yaml]
----
AllCops:
  ParserEngine: parser_whitequark
----

`parser_prism` can analyze source code from Ruby 3.3 and above:

[source,yaml]
----
AllCops:
  ParserEngine: parser_prism
  TargetRubyVersion: 3.3
----

TIP: `parser_prism` tends to perform analysis faster than `parser_whitequark`.

== Setting the style guide URL

You can specify the base URL of the style guide using `StyleGuideBaseURL`.
If specified under `AllCops`, all cops are targeted.

[source,yaml]
----
AllCops:
  StyleGuideBaseURL: https://rubystyle.guide
----

`StyleGuideBaseURL` is combined with `StyleGuide` specified to the cop.

[source,yaml]
----
Lint/UselessAssignment:
  StyleGuide: '#underscore-unused-vars'
----

The style guide URL is https://rubystyle.guide#underscore-unused-vars.

If specified under a specific department, it takes precedence over `AllCops`.
The following is an example of specifying `Rails` department.

[source,yaml]
----
Rails:
  StyleGuideBaseURL: https://rails.rubystyle.guide
----

[source,yaml]
----
Rails/TimeZone:
  StyleGuide: '#time'
----

The style guide URL is https://rails.rubystyle.guide#time.

== Setting the documentation URL

You can specify the base URL of the documentation using `DocumentationBaseURL`.
If specified under `AllCops`, all cops are targeted.

[source,yaml]
----
AllCops:
  DocumentationBaseURL: https://docs.rubocop.org/rubocop
----

If specified under a specific department, it takes precedence over `AllCops`.
The following is an example of specifying `Rails` department.

[source,yaml]
----
Rails:
  DocumentationBaseURL: https://docs.rubocop.org/rubocop-rails
----

By default, documentation is expected to be served as HTML but if you prefer
to use something else like markdown you can set `DocumentationExtension`.

With markdown as the documentation format you are able to host it directly through
GitHub without having to own a domain or using GitHub Pages. The `rubocop-sorbet`
extension is an example of this, its docs are available
https://github.com/Shopify/rubocop-sorbet/blob/main/manual[here].

[source,yaml]
----
Sorbet:
  DocumentationBaseURL: https://github.com/Shopify/rubocop-sorbet/blob/main/manual
  DocumentationExtension: .md
----

== Setting the version tracking metadata for cops

This configuration is particularly useful when custom cops are distributed as a gem.

Each cop can have the following additional metadata:

* `VersionAdded` - the RuboCop version in which it was added
* `VersionChanged` (optional) - the latest RuboCop version in which it was changed in a user-impacting way (new config, updated defaults, etc)

[source,yaml]
----
Style/HashSyntax:
  VersionAdded: '0.9'
  VersionChanged: '1.67'
----

NOTE: These values do not include patch versions.

Those will be pretty useful for the documentation (so the manual generation has to be enhanced to include them) and keeping track of changes.

== Enable checking Active Support extensions

Some cops for checking specified methods (e.g. `Style/HashExcept`) support Active Support extensions.
This is off by default, but can be enabled by the `ActiveSupportExtensionsEnabled` option.

[source,yaml]
----
AllCops:
  ActiveSupportExtensionsEnabled: true
----

== Opting into globally frozen string literals

Ruby continues to move into the direction of having all string literals frozen by default.
Ruby 3.4, for example, will show a warning if a non-frozen string literal from a file without
the frozen string literal magic comment gets modified. By starting Ruby with the environment
variable `RUBYOPT` set to `--enable=frozen-string-literal` you can opt into that behaviour today.
For RuboCop to provide accurate analysis you must also configure the `StringLiteralsFrozenByDefault`
option.

[source,yaml]
----
AllCops:
  StringLiteralsFrozenByDefault: true
----
