Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to configure Prettier to format Styled Components conditional rendering

I'm using Prettier, Eslint and Styled components - backtick style declaration. It works so far but Prettier formats the conditional rendering of the Styled components in the way that Eslint doesn't allow and after the formatting Eslint starts to complain and the build fails.

Let me show you the problem via code.

Initial code before Prettier handling:

// styled components styles apply
const TextInputStyled = styled(TextInputThemed)`
  ${(props: StyledProps) => {
    const {
      theme: { theme10x },
      disabled,
      success,
      error,
    } = props;
    return `
      ${success && `
        border-color: ${theme10x.palette.common.success};
      `};

      ${error && `
        background-color: ${theme10x.palette.common.error};
      `};

      ${disabled && `
        background-color: ${theme10x.palette.background.disabled};
      `};
    `;
  }}

After Prettier Handling:

// styled components styles apply
const TextInputStyled = styled(TextInputThemed)`
  ${(props: StyledProps) => {
    const {
      theme: { theme10x },
      disabled,
      success,
      error,
    } = props;
    return `
      ${
        success &&
        `
        border-color: ${theme10x.palette.common.success};
      `
      };

      ${
        error &&
        `
        background-color: ${theme10x.palette.common.error};
      `
      };

      ${
        disabled &&
        `
        background-color: ${theme10x.palette.background.disabled};
      `
      };
    `;
  }}
`;

After that Eslint starts to complain:

  133:1   error    Expected indentation of 2 spaces but found 8        indent
  133:19  error    '&&' should be placed at the beginning of the line  operator-linebreak
  137:1   error    Expected indentation of 0 spaces but found 6        indent
  140:1   error    Expected indentation of 2 spaces but found 8        indent
  140:17  error    '&&' should be placed at the beginning of the line  operator-linebreak
  144:1   error    Expected indentation of 0 spaces but found 6        indent
  147:1   error    Expected indentation of 2 spaces but found 8        indent
  147:20  error    '&&' should be placed at the beginning of the line  operator-linebreak
  151:1   error    Expected indentation of 0 spaces but found 6        indent

I wouldn't like to change Eslint rules because they are really useful in the 'real' use cases. So is there exists any way to solve this problem correctly? Thanks for any help!

Update:

My .eslintrc.json

{
  "extends": [
    "airbnb",
    "eslint:recommended",
    "plugin:jsx-a11y/recommended",
    "plugin:@typescript-eslint/recommended"
  ],
  "plugins": ["@typescript-eslint"],
  "parser": "@typescript-eslint/parser",
  "rules": {
    "@typescript-eslint/no-explicit-any": 0, 
    "react/static-property-placement": 0,

    "quotes": [2, "single"],
    "import/no-unresolved": 0,
    "comma-dangle": 0,
    "linebreak-style": 0,
    "react/state-in-constructor": 0,
    "no-underscore-dangle": 0,
    "react/jsx-props-no-spreading": 0,
    "semi": 1,
    "comma-dangle:": 0,
    "import/prefer-default-export": 0,
    "import/extensions": 0,
    "react/jsx-filename-extension": [
      1,
      {
        "extensions": [".jsx", ".tsx"]
      }
    ],
    "@typescript-eslint/explicit-function-return-type": 0
  }
}

My Prettier config (it's a part of the package.json)

  "prettier": {
    "trailingComma": "es5",
    "semi": true,
    "singleQuote": true
  }

I'm running it as a git hook via husky in a chain with lint:fix

  "husky": {
    "hooks": {
      "pre-commit": "npm run lint:fix && pretty-quick --staged"
    }
  },
like image 663
Velidan Avatar asked Apr 08 '20 08:04

Velidan


1 Answers

Have you considered trying eslint-config-prettier?

From the Prettier install docs:

If you use ESLint, install eslint-config-prettier to make ESLint and Prettier play nice with each other. It turns off all ESLint rules that are unnecessary or might conflict with Prettier.

Looking at the source, it appears it would turn off the indent and operator-linebreak rules ESLint is complaining about.


I see you noted:

I wouldn't like to change Eslint rules because they are really useful in the 'real' use cases.

Are these two rules truly useful? They seem to fall into the category of "formatting rules" rather than "code-quality rules", and so I wonder what the harm is in allowing Prettier to do what it's built for. (Reference)

It seems to me your problem comes from using ESLint and Prettier, but leaving them with an overlap in their responsibilities (which eslint-config-prettier could address).

Alternate Solution

If you really want to go the other direction and modify Prettier's behavior, perhaps you can ignore the files or use inline comments: https://prettier.io/docs/en/ignore.html

like image 122
mcy Avatar answered Oct 23 '22 05:10

mcy