I have created an app with create-react-app and I have applied the airbnb rules. The app also contains redux and flow.
The following code is throwing the no-unused-expressions error in eslint:
const reducer = (state: string = '', action: Action) => {
switch (action.type) {
// cases
default:
(action: empty); // this is throwing eslint/no-unused-expressions
return state;
}
};
I am trying to switch off the rule in eslintrc in order to replace it with flowtype/no-unused-expressions
content of my .eslintrc.yml
extends:
- airbnb
parser: babel-eslint
env:
browser: true
jest: true
globals:
SyntheticEvent: true,
rules:
no-unused-expressions: off
react/prefer-stateless-function: off
react/jsx-filename-extension: off
react/jsx-one-expression-per-line: off
With this settings, the no-unused-expressions error is not shown anymore in the editor (vscode). However as soon as I compile with npm run start
the error is still there:
Expected an assignment or function call and instead saw an expression no-unused-expressions
causing it to fail to compile.
Of course if I disable locally eslint for that rule for example with
// eslint-disable-line no-unused-expressions
Everything is working in both the editor and the browser. However, as I said I am trying to replace the eslint rule with the flowtype one exactly to avoid to be obliged to disable eslint every time I am using a flow type assertion.
Any idea what I am doing wrong?
package.json content:
{
"name": "would-you-rather",
"version": "0.1.0",
"private": true,
"dependencies": {
"eslint-config-airbnb": "17.1.0",
"eslint-config-flowtype-essential": "^1.0.0",
"eslint-plugin-flowtype": "^3.2.0",
"flow-bin": "0.89.0",
"flow-typed": "2.5.1",
"immutable": "4.0.0-rc.12",
"prop-types": "15.6.2",
"react": "16.6.3",
"react-dom": "16.6.3",
"react-icons": "3.2.2",
"react-redux": "6.0.0",
"react-redux-loading-bar": "4.1.0",
"react-router-dom": "4.3.1",
"react-scripts": "2.1.1",
"redux": "4.0.1",
"redux-immutable": "4.0.0",
"redux-thunk": "2.3.0",
"semantic-ui-css": "2.4.1",
"semantic-ui-react": "0.84.0"
},
"devDependencies": {
"docdash": "1.0.1",
"jsdoc": "3.5.5"
},
"scripts": {
"start": "react-scripts start",
"build": "react-scripts build",
"test": "react-scripts test",
"eject": "react-scripts eject",
"jsdoc": "jsdoc --configure jsdoc.conf.json --recurse --private",
"flow": "$(npm bin)/flow",
"flow-typed": "$(npm bin)/flow-typed",
"postinstall": "$(npm bin)/flow-typed install"
},
"browserslist": [
">0.2%",
"not dead",
"not ie <= 11",
"not op_mini all"
]
}
Link of the project on github if you want to play with it
Best Answer
The scripts included with react-scripts specifically do not read overrides from eslintrc files. The reasoning is explained in an issue comment:
I think the idea is that you are free to use your own eslint configuration to add style rules specific to your project that you check during development; but the
build
andstart
will not look at it, and will stick to the conservative rule set bundled with react-scripts instead. The fact that you have found a case where those conservative rules interfere with your workflow probably deserves an issue report with create-react-app.I think that the easiest solution is to use the
// eslint-disable-line no-unused-expressions
line, as you mentioned. But there are a couple of other options. You can modify the expression to convince eslint that it is not unused, or you can use a tool like patch-package to modify react-scripts' Webpack configuration so that it reads your custom eslint configuration.Convince eslint that the expression is used
The eslint configuration that react-scripts uses is in
node_modules/eslint-config-react-app/index.js
. You can see that it sets some exceptions to the no-unused-expressions rule:Ternary expressions are allowed. You can combine the type assertion with a function call (which should never run because
action
should always be truthy):Patch react-scripts' Webpack configuration
You can see the code that react-scripts uses to run eslint in
node_modules/react-scripts/config/webpack.config.dev.js
and again innode_modules/react-scripts/config/webpack.config.dev.js
:To use your custom configuration you need to change the line
useEslintrc: false
touseEslintrc: true
in both files. Then use patch-package to automatically reapply that change whenever react-scripts is installed or updated. Add this script to the scripts section inpackage.json
:Install patch-package, and postinstall-prepare to make sure that yarn runs the that
prepare
script:After editing the Webpack configuration files run this command to save a patch (note that the yarn commands above will have reverted your changes, so make the same changes again before running this step):
That will create a file with a name like
patches/react-scripts+2.1.1.patch
. You should check this file into version control.