Repository: eslint/eslint
Pull request #9852 (2018-01-17 03:58:25)

Fix: Removing curly quotes in no-eq-null report message
<!--
    ESLint adheres to the [JS Foundation Code of Conduct](https://js.foundation/community/code-of-conduct).
-->

**What is the purpose of this pull request? (put an "X" next to item)**

[ ] Documentation update
[x] Bug fix ([template](https://raw.githubusercontent.com/eslint/eslint/master/templates/bug-report.md))
[ ] New rule ([template](https://raw.githubusercontent.com/eslint/eslint/master/templates/rule-proposal.md))
[ ] Changes an existing rule ([template](https://raw.githubusercontent.com/eslint/eslint/master/templates/rule-change-proposal.md))
[ ] Add autofixing to a rule
[ ] Add a CLI option
[ ] Add something to the core
[ ] Other, please explain:

<!--
    If the item you've checked above has a template, please paste the template questions below and answer them. (If this pull request is addressing an issue, you can just paste a link to the issue here instead.)
-->

**Tell us about your environment**

* **ESLint Version:** master
* **Node Version:** doesn't matter
* **npm Version:** doesn't matter

**What parser (default, Babel-ESLint, etc.) are you using?**

Default, but doesn't matter

**Please show your full configuration:**

```json
{
    "rules": {
        "no-eq-null": "error"
    }
}
```

**What did you do? Please include the actual source code causing the issue.**

```js
if (foo == null) {
}
```

**What did you expect to happen?**

Error message: Use == when comparing to null.

**What actually happened? Please include the actual, raw output from ESLint.**

Got an error message, but it uses a multibyte character that does not render well in some contexts and furthermore is inconsistent with the rest of the core rules.

<!--
    Please ensure your pull request is ready:

    - Read the pull request guide (https://eslint.org/docs/developer-guide/contributing/pull-requests)
    - Include tests for this change
    - Update documentation for this change (if appropriate)
-->

<!--
    The following is required for all pull requests:
-->

**What changes did you make? (Give an overview)**

Changed the lint message for no-eq-null to avoid using multibyte characters (curly quotes).

**Is there anything you'd like reviewers to focus on?**

Does this feel consistent with messages in other core rules?

platinumazure: True, we could normalize among those at some point. But this curly quote
business has to go, for sure.

On Jan 16, 2018 10:02 PM, "Teddy Katz" <notifications@github.com> wrote:

> *@not-an-aardvark* approved this pull request.
>
> LGTM. I think we also use ` in some places, but I'm not sure how much we
> use it compared to '.
>
> —
> You are receiving this because you authored the thread.
> Reply to this email directly, view it on GitHub
> <https://github.com/eslint/eslint/pull/9852#pullrequestreview-89323492>,
> or mute the thread
> <https://github.com/notifications/unsubscribe-auth/AARWekI1NyYMK1LRTtPelXMm20s5HE5Vks5tLXDXgaJpZM4Rgxt3>
> .
>

j-f1: Once we [use `messageId`s](https://github.com/eslint/eslint/pull/9648), we’ll be able to make a new rule (maybe in `eslint-plugin-eslint-plugin` to require all messages to match a pattern.

Patch:
diff --git a/docs/developer-guide/nodejs-api.md b/docs/developer-guide/nodejs-api.md
index b774d3694..c774666e0 100644
--- a/docs/developer-guide/nodejs-api.md
+++ b/docs/developer-guide/nodejs-api.md
@@ -334,7 +334,7 @@ The `CLIEngine` is a constructor, and you can create a new instance by passing i
 * `cache` - Operate only on changed files (default: `false`). Corresponds to `--cache`.
 * `cacheFile` - Name of the file where the cache will be stored (default: `.eslintcache`). Corresponds to `--cache-file`. Deprecated: use `cacheLocation` instead.
 * `cacheLocation` - Name of the file or directory where the cache will be stored (default: `.eslintcache`). Corresponds to `--cache-location`.
-* `configFile` - The configuration file to use (default: null). Corresponds to `-c`.
+* `configFile` - The configuration file to use (default: null). If `useEslintrc` is true or not specified, this configuration will be merged with any configuration defined in `.eslintrc.*` files, with options in this configuration having precedence. Corresponds to `-c`.
 * `cwd` - Path to a directory that should be considered as the current working directory.
 * `envs` - An array of environments to load (default: empty array). Corresponds to `--env`.
 * `extensions` - An array of filename extensions that should be checked for code. The default is an array containing just `".js"`. Corresponds to `--ext`. It is only used in conjunction with directories, not with filenames or glob patterns.
diff --git a/docs/rules/no-useless-escape.md b/docs/rules/no-useless-escape.md
index 2bb0c1cc3..6088c5cb0 100644
--- a/docs/rules/no-useless-escape.md
+++ b/docs/rules/no-useless-escape.md
@@ -41,8 +41,8 @@ Examples of **correct** code for this rule:
 "\371";
 "xs\u2111";
 `\``;
-`\${${foo}\}`;
-`$\{${foo}\}`;
+`\${${foo}}`;
+`$\{${foo}}`;
 /\\/g;
 /\t/g;
 /\w\$\*\^\./;
diff --git a/docs/user-guide/command-line-interface.md b/docs/user-guide/command-line-interface.md
index 8235f7b6c..39a297c79 100644
--- a/docs/user-guide/command-line-interface.md
+++ b/docs/user-guide/command-line-interface.md
@@ -30,8 +30,8 @@ The command line utility has several options. You can view the options by runnin
 eslint [options] file.js [file.js] [dir]
 
 Basic configuration:
-  -c, --config path::String      Use configuration from this file or shareable config
-  --no-eslintrc                  Disable use of configuration from .eslintrc
+  --no-eslintrc                  Disable use of configuration from .eslintrc.*
+  -c, --config path::String      Use this configuration, overriding .eslintrc.* config options if present
   --env [String]                 Specify environments
   --ext [String]                 Specify JavaScript file extensions - default: .js
   --global [String]              Define global variables
@@ -92,6 +92,14 @@ Example:
 
 ### Basic configuration
 
+#### `--no-eslintrc`
+
+Disables use of configuration from `.eslintrc.*` and `package.json` files.
+
+Example:
+
+    eslint --no-eslintrc file.js
+
 #### `-c`, `--config`
 
 This option allows you to specify an additional configuration file for ESLint (see [Configuring ESLint](configuring) for more).
@@ -110,13 +118,7 @@ Example:
 
 This example directly uses the sharable config `eslint-config-myconfig`.
 
-#### `--no-eslintrc`
-
-Disables use of configuration from `.eslintrc` and `package.json` files.
-
-Example:
-
-    eslint --no-eslintrc file.js
+If `.eslintrc.*` and/or `package.json` files are also used for configuration (i.e., `--no-eslintrc` was not specified), the configurations will be merged. Options from this configuration file have precedence over the options from `.eslintrc.*` and `package.json` files.
 
 #### `--env`
 
diff --git a/docs/user-guide/configuring.md b/docs/user-guide/configuring.md
index 44b823aeb..098fcdf43 100644
--- a/docs/user-guide/configuring.md
+++ b/docs/user-guide/configuring.md
@@ -3,7 +3,7 @@
 ESLint is designed to be completely configurable, meaning you can turn off every rule and run only with basic syntax validation, or mix and match the bundled rules and your custom rules to make ESLint perfect for your project. There are two primary ways to configure ESLint:
 
 1. **Configuration Comments** - use JavaScript comments to embed configuration information directly into a file.
-1. **Configuration Files** - use a JavaScript, JSON or YAML file to specify configuration information for an entire directory (other than your home directory) and all of its subdirectories. This can be in the form of an [.eslintrc.*](#configuration-file-formats) file or an `eslintConfig` field in a [`package.json`](https://docs.npmjs.com/files/package.json) file, both of which ESLint will look for and read automatically, or you can specify a configuration file on the [command line](command-line-interface).
+1. **Configuration Files** - use a JavaScript, JSON or YAML file to specify configuration information for an entire directory (other than your home directory) and all of its subdirectories. This can be in the form of an [`.eslintrc.*`](#configuration-file-formats) file or an `eslintConfig` field in a [`package.json`](https://docs.npmjs.com/files/package.json) file, both of which ESLint will look for and read automatically, or you can specify a configuration file on the [command line](command-line-interface).
 
     If you have a configuration file in your home directory (generally `~/`), ESLint uses it **only** if ESLint cannot find any other configuration file.
 
@@ -453,11 +453,15 @@ And in YAML:
 
 ## Using Configuration Files
 
-There are two ways to use configuration files. The first is to save the file wherever you would like and pass its location to the CLI using the `-c` option, such as:
+There are two ways to use configuration files.
+
+The first way to use configuration files is via `.eslintrc.*` and `package.json` files. ESLint will automatically look for them in the directory of the file to be linted, and in successive parent directories all the way up to the root directory of the filesystem (unless `root: true` is specified). This option is useful when you want different configurations for different parts of a project or when you want others to be able to use ESLint directly without needing to remember to pass in the configuration file.
+
+The second is to save the file wherever you would like and pass its location to the CLI using the `-c` option, such as:
 
     eslint -c myconfig.json myfiletotest.js
 
-The second way to use configuration files is via `.eslintrc.*` and `package.json` files. ESLint will automatically look for them in the directory of the file to be linted, and in successive parent directories all the way up to the root directory of the filesystem. This option is useful when you want different configurations for different parts of a project or when you want others to be able to use ESLint directly without needing to remember to pass in the configuration file.
+If you are using one configuration file and want ESLint to ignore any `.eslintrc.*` files, make sure to use `--no-eslintrc` along with the `-c` flag.
 
 In each case, the settings in the configuration file override default settings.
 
@@ -548,15 +552,15 @@ The complete configuration hierarchy, from highest precedence to lowest preceden
     1. `/*global*/`
     1. `/*eslint*/`
     1. `/*eslint-env*/`
-2. Command line options:
+1. Command line options (or CLIEngine equivalents):
     1. `--global`
     1. `--rule`
     1. `--env`
     1. `-c`, `--config`
-3. Project-level configuration:
+1. Project-level configuration:
     1. `.eslintrc.*` or `package.json` file in same directory as linted file
     1. Continue searching for `.eslintrc` and `package.json` files in ancestor directories (parent has highest precedence, then grandparent, etc.), up to and including the root directory or until a config with `"root": true` is found.
-    1. In the absence of any configuration from (1) thru (3), fall back to a personal default configuration in  `~/.eslintrc`.
+1. In the absence of any configuration from (1) thru (3), fall back to a personal default configuration in  `~/.eslintrc`.
 
 ## Extending Configuration Files
 
diff --git a/lib/options.js b/lib/options.js
index c8005d444..9265d151d 100644
--- a/lib/options.js
+++ b/lib/options.js
@@ -26,17 +26,17 @@ module.exports = optionator({
         {
             heading: "Basic configuration"
         },
-        {
-            option: "config",
-            alias: "c",
-            type: "path::String",
-            description: "Use configuration from this file or shareable config"
-        },
         {
             option: "eslintrc",
             type: "Boolean",
             default: "true",
-            description: "Disable use of configuration from .eslintrc"
+            description: "Disable use of configuration from .eslintrc.*"
+        },
+        {
+            option: "config",
+            alias: "c",
+            type: "path::String",
+            description: "Use this configuration, overriding .eslintrc.* config options if present"
         },
         {
             option: "env",
diff --git a/lib/rules/no-eq-null.js b/lib/rules/no-eq-null.js
index befb9d46f..22dbd49d4 100644
--- a/lib/rules/no-eq-null.js
+++ b/lib/rules/no-eq-null.js
@@ -31,7 +31,7 @@ module.exports = {
 
                 if (node.right.type === "Literal" && node.right.raw === "null" && badOperator ||
                         node.left.type === "Literal" && node.left.raw === "null" && badOperator) {
-                    context.report({ node, message: "Use ‘===’ to compare with ‘null’." });
+                    context.report({ node, message: "Use '===' to compare with null." });
                 }
             }
         };


Test patch:
diff --git a/tests/lib/rules/no-eq-null.js b/tests/lib/rules/no-eq-null.js
index 7fdb1e440..23d992dc5 100644
--- a/tests/lib/rules/no-eq-null.js
+++ b/tests/lib/rules/no-eq-null.js
@@ -18,14 +18,16 @@ const rule = require("../../../lib/rules/no-eq-null"),
 
 const ruleTester = new RuleTester();
 
+const MESSAGE = "Use '===' to compare with null.";
+
 ruleTester.run("no-eq-null", rule, {
     valid: [
         "if (x === null) { }",
         "if (null === f()) { }"
     ],
     invalid: [
-        { code: "if (x == null) { }", errors: [{ message: "Use ‘===’ to compare with ‘null’.", type: "BinaryExpression" }] },
-        { code: "if (x != null) { }", errors: [{ message: "Use ‘===’ to compare with ‘null’.", type: "BinaryExpression" }] },
-        { code: "do {} while (null == x)", errors: [{ message: "Use ‘===’ to compare with ‘null’.", type: "BinaryExpression" }] }
+        { code: "if (x == null) { }", errors: [{ message: MESSAGE, type: "BinaryExpression" }] },
+        { code: "if (x != null) { }", errors: [{ message: MESSAGE, type: "BinaryExpression" }] },
+        { code: "do {} while (null == x)", errors: [{ message: MESSAGE, type: "BinaryExpression" }] }
     ]
 });