npm package: @itcase/lint
Description: Code style linter configuration presets
Author: ITCase
Latest version: 1.1.104

# ITCase Lint 

Presets of linter configurations

## Installation

```bash
 $ npm i -D @itcase/lint eslint stylelint prettier
```

## Setting up sorting configuration

The sorting configuration is located in the `perfectionist` folder along the path: `eslint/perfectionist`.

> Example: Setting up sortJSXProps

Sorting rules are defined in `eslint/perfectionist/sortJSXProps.ts` and use shared data from `eslint/perfectionist/sort/`:

1. **`sort/props.ts`** — array of prop names in the desired sort order. The order of names in this array defines the order in which props will be sorted.

2. **`sort/customGroup.ts`** — custom group rules when sort order depends on a pattern (regex) rather than the exact name. Each key is a group name, the value is a pattern that property names must match.

Example of the structure:

```ts
// sort/props.ts — order of props
const props = ['id', 'className', 'callback', 'children']

// sort/customGroup.ts — patterns for groups
const customGroups = {
  callback: '^on.*',
}
```

The same `props` and `customGroups` are used for `sortJSXProps` and `sortObjects` (objects are sorted with the same group order).

## Usage

### ESLint

Create a `eslint.config.mjs` configuration file in the root of your project with the following content:

```js
import eslint from '@itcase/lint/eslint/index.js'

export default eslint
```

### ESLint with MobX

Create a `eslint.config.mjs` configuration file in the root of your project with the following content:

```js
import eslint from '@itcase/lint/eslint/index.js'
import eslintMobx from '@itcase/lint/eslint/mobx/index.js'

export default [...eslint, ...eslintMobx]
```

### ESLint with React Native

Create a `eslint.config.mjs` configuration file in the root of your project with the following content:

```js
import eslint from '@itcase/lint/eslint/index.js'
import eslintReactNative from '@itcase/lint/eslint/react-native/index.js'

export default [...eslint, ...eslintReactNative]
```

### ESLint with MobX, React Native

Create a `eslint.config.mjs` configuration file in the root of your project with the following content:

```js
import eslint from '@itcase/lint/eslint/index.js'
import eslintMobx from '@itcase/lint/eslint/mobx/index.js'
import eslintReactNative from '@itcase/lint/eslint/react-native/index.js'

export default [...eslint, ...eslintMobx, ...eslintReactNative]
```

### Плагины ESLint

В пакет входят кастомные плагины, которые подключаются отдельно:

| Плагин | Описание | Подключение |
|--------|----------|-------------|
| **itcase-lint/react-data-test-id** | Требует атрибут `data-test-id` / `dataTestId` у указанных компонентов | Входит в базовый `@itcase/lint/eslint`, правило включается вручную для нужных путей |
| **itcase-lint/storybook-meta-parameters-design** | Требует в Storybook-сториз ссылку на Figma в `parameters.design` | `import eslintStorybook from '@itcase/lint/eslint/storybook'` и `...eslintStorybook` в конфиге |

Ниже — подробное описание и примеры для каждого плагина.

---

### ESLint with itcase-lint/react-data-test-id

`itcase-lint/react-data-test-id` принимает опции:

```ts
appendElementNamesToCheck?: string[] | null
overrideElementNamesToCheck?: string[] | null
overrideElementNamesToIgnore?: string[] | null
```

**Defaults**

- `overrideElementNamesToIgnore`: `['IgnoredElement', 'Html']`
- `overrideElementNamesToCheck`: `['Group', 'Modal', 'Drawer', 'ModalSheetBottom', 'Grid', 'Flex']`
- `appendElementNamesToCheck`: `[]`

**Behavior**

- `overrideElementNamesToIgnore`: replaces the default ignore list.
- `overrideElementNamesToCheck`: replaces the default check list.
- `appendElementNamesToCheck`: adds to the current check list (default or overridden).
- `null` or `undefined`: keep the default behavior for that option.

**Minimal setup (defaults):**

```js
import eslint from '@itcase/lint/eslint'

export default [
  ...eslint,
  {
    ignores: ['./**/*.stories.*'],
    files: ['./packages/*.{ts,tsx,js,jsx}'],
    rules: {
      'itcase-lint/react-data-test-id': 'warn',
    },
  },
]
```

**Customized setup:**

```js
import eslint from '@itcase/lint/eslint'

export default [
  ...eslint,
  {
    ignores: ['./**/*.stories.*'],
    files: ['./packages/*.{ts,tsx,js,jsx}'],
    rules: {
      'itcase-lint/react-data-test-id': [
        'warn',
        {
          overrideElementNamesToIgnore: ['IgnoredElement', 'Html', 'SkipMe'],
          overrideElementNamesToCheck: ['Modal', 'Drawer'],
          appendElementNamesToCheck: ['Card', 'Panel'],
        },
      ],
    },
  },
]
```

### ESLint with Storybook (itcase-lint/storybook-meta-parameters-design)

The `itcase-lint/storybook-meta-parameters-design` rule checks that Storybook stories include a `parameters.design` block with `type: 'figma'` and a non-empty `url` containing `figma.com`.

**Setup**

Add the Storybook config to `eslint.config.mjs`:

```js
import eslint from '@itcase/lint/eslint'
import eslintStorybook from '@itcase/lint/eslint/storybook'

export default [...eslint, ...eslintStorybook]
```

The rule `itcase-lint/storybook-meta-parameters-design` is enabled by default with level `warn` for files `**/*.stories.{ts,tsx,js,jsx,mjs,cjs}`.

**Meta requirements**

If the story’s default export has `parameters`, it must include a `parameters.design` object with `type: 'figma'` and a non-empty `url` containing `figma.com`. Example:

```js
export default {
  component: MyComponent,
  parameters: {
    design: {
      type: 'figma',
      url: 'https://www.figma.com/design/...',
    },
  },
}
```

### Stylelint

Create a `eslint.config.mjs` configuration file in the root of your project with the following content:

```js
export default {
  extends: ['@itcase/lint/stylelint/index.js'],
}
```

### Prettier

Create a `prettier.config.mjs` configuration file in the root of your project with the following content:

```js
import prettier from '@itcase/lint/prettier/index.js'

export default prettier
```

### git-hook

1. Use `husky` and `lint-staged`

```bash
npm i -D husky lint-staged
```

2. Create a `.lintstagedrc` configuration file in the root of your project with the following content:

```json
{
  "*.css": ["npx stylelint --fix"],
  "*.(js|jsx|ts|tsx)": ["npx eslint --fix"]
}
```

3. Add **pre-commit** hook in `.husky/pre-commit`

```bash
#!/bin/bash

if grep --include=*.{json,css,html} --exclude-dir={dist,node_modules,.git} -nri --color -B 1 -A 1 '<\{7\} HEAD\|^\=\.{7\}\|>\.{7\}' .; then
  echo 'Fix conflicts'
  exit 1
else ./node_modules/lint-staged/bin/lint-staged.js; fi
```