惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

WordPress大学
WordPress大学
D
Darknet – Hacking Tools, Hacker News & Cyber Security
Hacker News: Ask HN
Hacker News: Ask HN
N
News and Events Feed by Topic
Forbes - Security
Forbes - Security
The Last Watchdog
The Last Watchdog
TaoSecurity Blog
TaoSecurity Blog
Schneier on Security
Schneier on Security
SecWiki News
SecWiki News
V
Vulnerabilities – Threatpost
Project Zero
Project Zero
O
OpenAI News
W
WeLiveSecurity
Security Archives - TechRepublic
Security Archives - TechRepublic
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
H
Hacker News: Front Page
Cisco Talos Blog
Cisco Talos Blog
Spread Privacy
Spread Privacy
Help Net Security
Help Net Security
P
Privacy & Cybersecurity Law Blog
K
Kaspersky official blog
S
Security @ Cisco Blogs
Latest news
Latest news
AWS News Blog
AWS News Blog
U
Unit 42
Martin Fowler
Martin Fowler
阮一峰的网络日志
阮一峰的网络日志
S
Secure Thoughts
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
Application and Cybersecurity Blog
Application and Cybersecurity Blog
Know Your Adversary
Know Your Adversary
Scott Helme
Scott Helme
博客园 - 司徒正美
B
Blog RSS Feed
C
Check Point Blog
Hacker News - Newest:
Hacker News - Newest: "LLM"
D
Docker
Google Online Security Blog
Google Online Security Blog
Jina AI
Jina AI
aimingoo的专栏
aimingoo的专栏
Recent Commits to openclaw:main
Recent Commits to openclaw:main
Last Week in AI
Last Week in AI
月光博客
月光博客
C
CXSECURITY Database RSS Feed - CXSecurity.com
S
SegmentFault 最新的问题
NISL@THU
NISL@THU
T
The Blog of Author Tim Ferriss
C
Cisco Blogs
Attack and Defense Labs
Attack and Defense Labs
小众软件
小众软件

Все публикации подряд на Хабре

Ловим музу за клавиатуру: как айтишнику стать автором Что умеет Midjourney в 2026? Мой немного грустный разбор этого шикарного инструмента Никто не любит писать тесты, но ИИ может исправить это IPv8 выглядит как мечта. Поэтому почти наверняка не взлетит Производители вернули в продажу материнки с DDR3. Что происходит? Управление агентом с телефона через Telegram теперь в KodaCode От координации к лидерству: как меняется роль руководителя разработки Я сделала родителям бизнес вместо пенсии: зарабатываем 70 тысяч, мама не даёт продать В три раза быстрее приемка товара и оптимизация трудозатрат на 73%: как «РСТ-Инвент» помог Gulliver Group ИИ-шечный мир победил? О влиянии искусственного интеллекта на игропром Кремль снижает давление на Телеграмм пока Европа строит интернет по паспорту Как CEO, CTO и CIO за 8 часов собрали ИИ-директора, который умеет держать позицию под давлением Как (не) потерять домен за выходные Вместо 8 разных VPS: как я организовал практику студентам на одном сервере Почему твой Open Source проект не замечают? R&D: искусство управления неопределенностью в разработке AI-дефляция: вакансий для разработчиков больше, а рост зарплат — худший за 15 лет Мы отдали управление роботами OpenClaw. Что из этого вышло Галактический ID: система идентификации для всех форм разумной жизни Шесть основ бизнес-анализа: начинаем с вопроса «Кто в игре?» Код-ревью, в котором дело не в коде Данные переехали. Команда — нет Системной подход к сдаче OSWE в 2025 Почему комната управления реактором покрашена в цвет морской пены 4 YAML-файла вместо PySpark: как аналитикам строить пайплайны без разработчиков LLM-агент для поиска свободных доменов: автоматизируем подбор Когда, зачем и как правильно начинать новую сессию в Claude Code? Как я заставил нейросеть писать макросы для FreeCAD Анатомия ИИ‑агента для подбора персонала. От тысячи резюме к топ‑10 за минуты Опыт разработчика как экономика внимания Автономность как точка невозврата: кто будет субъектом в цифровом будущем Обучение ИИ в «диких» условиях: как рутинные действия превращаются в датасеты Как измерить LLM для задач кибербеза: обзор открытых бенчмарков Где хранить код? Сравнение GitHub, GitLab и Bitbucket Математика объясняет, почему нормальное распределение встречается повсюду Почему ваш FinOps не работает: 12 тезисов от практиков Как подписать проектную документацию УКЭП с использованием бесплатных лицензий Pilot Адаптивное администрирование Sigla Vision Я грузил уран в бочки, а потом 20 лет строил ИТ в атомной отрасли Чем позвонить с Эвереста? История и обзор спутниковой связи. Часть 2 Как языковая модель помогает контролировать качество инструктажей по охране труда в металлургии Как не передать на desktop свой IP в РКН Анатомия SAP Privileges: как устроено управление правами в macOS MoneyDev: Сказка про три главных слова Обновлённый токенизатор видео K-VAE 2.0 от Сбера Как сделать диспетчеризацию дома на 1284 квартиры почти бесплатно Как мы разогнали железную дорогу Мы дали агентам рутину. Теперь надо решить — что делать с освободившимся временем Токсичный контент, промпт-хакинг и защита ИИ — всё о Guardrails для LLM Умный город начинается с точного взгляда: как «Фалькон Тех» меняет пространство к лучшему Навайбкодил приложение для анализа графов Почему Дюну так интересно читать? Упрощаем работу с рутиной или как стать Гендальфом Белым Деконструкция Go: CPU, RAM и что там происходит. Go Assembler база. Часть 1.1 Какие профессии исчезнут из-за ИИ, а какие появятся? И что с этим делать Как мы построили IT-отдел, где хочется расти: архитектурные встречи, прозрачные метрики и книжные подарки Rufler: Делаем из Claude Code автономный рой через один YAML-конфиг Sing-box и белый список приложений Как построить надёжный обмен сообщениями в микросервисах: лучшие практики для enterprise OpenAI строит MLM-пирамиду, а McKinsey и Accenture помогают ей в этом Дом, который не построил Фишер (Часть 2) «Сверхзвуковой математик» против «Вдумчивого логиста»: битва алгоритмов 3D-упаковки Мультимодальные модели – грубый и дорогой инструмент Разговоры ничего не стоят. Код тоже Проверки физических лиц: с кого начнет ФНС Топ-10 бесплатных нейросетей для создания видео в 2026 году Первые слои кода: как наши решения сегодня определяют архитектуру ИИ на десятилетия Разработка нового статического анализатора: PVS-Studio JavaScript Поиск уязвимостей ПО: базовый минимум или роскошный максимум Почему оценка персонала не работает как инструмент управления Как мы разработали ИИ-ассистента и сократили рутину продуктовой команды на 50% Как я ушел из найма, нажарил косточек и продал на маркетплейсах на 168 млн в год Когда 1С:ERP уже внедрена, а нормального производственного плана всё ещё нет Как я сделал Claude мультимодальным, подключив к нему Qwen Omni Как приглашение на вакансию мечты превращается в атаку Infrastructure as Code: философия и лучшие практики IaC Тестируем Yandex Code Assistant на задаче, в которой нужно хранить секреты nxs-universal-chart v3.0: новое поколение универсального Helm-чарта Callback Injection: Техника, которая отправила Microsoft Defender в глухой нокаут «Все идеи на стол»: митап как способ вывести проект из тупика Сегодня я узнал нечто новое о GPU благодаря багу в своей игре Как заставить LLM ̶ ̶г̶а̶л̶л̶ю̶ ̶ эволюционировать Карта событий как фундамент аналитики: практический кейс для E-commerce Что выбрать для AI: x86, ARM или RISC-V? Дайджест железа за март Роль соматических мутаций в развитии аутоиммунных заболеваний: путь к избирательной терапии Mythos от Anthropic — тревожный сигнал для всех, а не только для банков Guardrails для LLM на Java: как приручить промпт‑инъекции и токсичные ответы Green-VLA: как мы собрали VLA-модель для реального антропоморфного робота и не потеряли обобщение Финансовая гонка вооружений: почему умные люди добровольно в ней участвуют Эра ИИ-агентов наступила: выбираем лучшего цифрового сотрудника # Практический опыт внедрения WinCC Redundancy на производственном предприятии Сделал MVP за 3 дня, а потом неделю прикручивал оплату. Оно того стоило? Физика против Маска: почему Starship V3 может оказаться ещё одной катастрофой Нефть Венесуэлы: крупнейшие запасы в мире, но не крупнейшая нефтяная держава JPA 4. Переосмысление Hibernate Почему зеркальная фотокамера Nikon D5 десятилетней давности идеально подошла для миссии «Артемида-2» Проект «Уровень-Спутник» или как мы сделали платформу для гидрологов «Замедлиться, чтобы ускориться»: почему ИИ повышает цену ошибок в требованиях и архитектуре Как с нуля поднять трафик IT-компании на 1657% при бюджете 55 тыс. и выжить Pixel-perfect Downsampling — идеальная отрисовка 50 миллионов точек без потерь
Линт проектов: собираем ESLint, Prettier и Stylelint в один пакет
Alex Dozmorov · 2026-05-23 · via Все публикации подряд на Хабре

Средний

11 мин

12K

Введение

В большинстве компаний линтинг со временем превращается в хаос: разные правила ESLint, устаревшие конфиги и копипаста между проектами.

Покажу, как навести порядок – собрать линт-инфраструктуру в один пакет и выстроить систему контроля кода для всех репозиториев.

Для кого эта статья

Статья будет полезна:

  • разработчикам, которые хотят навести порядок в линтинге нескольких проектов;

  • тимлидам и техлидам, которые строят единые стандарты кода в команде;

  • тем, кто планирует вынести конфигурации ESLint, Prettier и Stylelint в отдельный пакет.

Предполагается базовое знакомство с ESLintPrettier и экосистемой JavaScript.

Почему для компании стоит создавать свой lint пакет

Если в компании больше одного проекта, со временем почти всегда появляется одинаковая проблема: линт-конфиги начинают расползаться.

В одном репозитории ESLint настроен так, в другом – немного иначе. Где-то есть stylelint, где-то нет. В одном проекте используются recommended правила, в другом – половина из них отключена.

Через год это обычно выглядит примерно так:

  • одинаковые конфиги копируются из проекта в проект;

  • правила случайно расходятся;

  • при обновлении ESLint или плагинов каждый репозиторий приходится чинить отдельно;

  • новые проекты начинают, используя старые, устаревшие конфиги.

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

Решение у этой проблемы довольно простое – вынести всю линт-инфраструктуру в отдельный npm-пакет@company/lint.

После этого:

  • все проекты используют одни и те же правила;

  • обновление линта происходит в одном месте;

  • новые проекты получают готовую инфраструктуру за минуту;

  • команда может обновлять правила постепенно.

По сути, компания начинает относиться к линтингу как к части своей инженерной платформы, а не как к случайному набору файлов конфигов.

Содержимое lint пакета

Lint-пакет стоит рассматривать не просто как сборку конфигураций, а как централизованный гайдлайн по стандартам кода компании.

Помимо самих конфигов, здесь удобно описывать рекомендации по инструментам анализа кода и правила их использования. Такой пакет становится единым источником правды для всех проектов.

Пример реализованного пакета можно посмотреть в этом репозитории: https://github.com/Dozalex/lint-configs.

Рассмотрим инструменты, которые обычно входят в такую инфраструктуру, а далее разберем каждый подробнее.

ESLint

Это один из основных инструментов для поддержки качества кода. ESLint помогает находить потенциальные ошибки, логические проблемы и нарушения принятых в проекте правил.

Ранее вынос конфигурации ESLint в отдельный пакет был не очень удобным. Каждую зависимость, используемую в конфиге (плагины, парсеры, расширения), приходилось дублировать в package.json каждого проекта. Иначе возникали конфликты зависимостей и ошибки загрузки плагинов.

С выходом ESLint 9 ситуация изменилась. Плоский конфиг (Flat Config) перестал быть экспериментальным и позволил инкапсулировать все зависимости внутри одного пакета.

Теперь рабочие репозитории могут подключать только сам конфиг, не заботясь о его внутренних зависимостях.

Prettier

Prettier – это форматтер кода, который автоматически:

  • выравнивает отступы;

  • убирает лишние пустые строки;

  • расставляет переносы строк.

Stylelint

Stylelint выполняет ту же роль, что и ESLint, но для CSS.

Он помогает находить ошибки в стилях и следить за единообразием CSS-кода. Однако особенно полезным он становится при использовании плагина stylelint-order, который автоматически сортирует CSS-свойства в заданном порядке.

Это делает стили более предсказуемыми и упрощает навигацию по коду, что ускоряет разработку.

Madge

Madge – менее очевидный, но полезный инструмент анализа зависимостей.

Его основная задача – поиск циклических зависимостей между модулями. Такие зависимости могут приводить к трудноуловимым ошибкам и усложнять поддержку проекта, поэтому их важно выявлять как можно раньше.

Немного о новых инструментах

В последнее время появляются инструменты, которые пытаются объединить линтер и форматтер в одном решении. Одним из таких проектов является Biome.

Он написан на Rust, благодаря чему заявляется высокая скорость работы. Однако инструмент пока достаточно молодой и его экосистема значительно уступает ESLint по количеству плагинов и правил.

Также, начиная с Vite 8 и связанных проектов VoidZero, экосистема Vite движется в сторону единого toolchain’а: кроме сборки, в неё интегрируются задачи линтинга, форматирования и type-checking. Для линтинга используется Oxlint из экосистемы Oxc.

Возможно, со временем такие решения смогут заменить текущий набор инструментов и сократить время выполнения линтинга без потери качества проверки кода. Но, в любом случае, инструменты, работа с которыми описана в этой статье, будут существовать в экосистеме еще долгие годы, так как проверены временем и используюся в огромном числе компаний.

ESLint на практике

Содержимое конфига

Долгое время eslint-config-airbnb считался де-факто стандартом для фронтенд-проектов. Большинство команд просто брали его за основу и отключали или переопределяли отдельные правила. Однако со временем пакет перестал активно обновляться и сегодня он содержит большое количество легаси-правил, не соответствующих современному стеку разработки.

При создании собственного lint-пакета я решил детально разобрать правила из этого конфига. Там оказалось большое кол-во стилистического мусора, правил для классовых компонентов реакта и прочих древностей. Рекомендованные конфиги для React также содержат большое количество правил, которые существуют в основном для обратной совместимости.

В итоге стало очевидно, что переносить весь этот набор правил в собственный конфиг не имеет большого смысла, поэтому я отказался от recommended конфигов в пользу явного понимания того, какие правила попадут в мой конфиг. Однозначно, у этого подхода есть как плюсы, так и минусы.

Плюсы:

  • в конфиге нет ничего лишнего;

  • не нужно делать десятки выключений правил;

  • нужные правила не пропадут неожиданно при обновлении recommended конфига;

  • линт выполянется быстрее благодаря минимальному набору правил.

Минусы:

  • если хочется самому отфильтровать каждое правило, это займет довольно много времени;

  • когда появятся новые правила для нового синтаксиса языка или фреймворка, будет не достаточно просто обновить recommended конфиг, нужно будет найти эти новые правила, решить, нужны ли они, перенести в свой конфиг.

Было принято решение, что плюсы перевешивают минусы, поэтому все правила из eslint-airbnb-config прошли фильтрацию от легаси, изменены в соответствии с современными стандартами. Также были добавлены некоторые новые полезные правила.

Правила были разбиты на небольшие конфигурационные модули, на подобии тех, что используются в eslint-airbnb-config. Это позволяет гибко собирать уникальный конфиг для конкретного проекта.

eslint/
  core/ – содержит best-practices для js
  reactBase/ – содержит best-practices для react
  base.mjs – базовые настройки + объединение всех конфигов из core + typescript (потому что typescript это де-факто база)
  react.mjs – base.mjs + объединение всех конфигов из reactBase
  typescript.mjs – правила для typescript, подключение tsconfig.json
  webpack.mjs – подключение webpack.config.ts

Такая структура делает конфигурацию расширяемой. Например, можно добавить vue.mjs, подключить базовые правила и получить полноценный конфиг для Vue-проекта, не включая при этом правила, относящиеся к React.

Также, если бы мы зашили в единый конфиг логику для подключения webpack конфига, но не использовали его в проекте, eslint бы сразу выдал ошибку.

Из интересного в конфиге хочется выделить:

  1. Правило import/order.

    Раньше часто сталкивался с тем, что некоторым разработчикам все равно, что у них там в импортах. Как IDE автоматически добавила импорт, так они и оставили – вперемешку импорты библиотек, относительные импорты, алиасы.

    Прекрасно понимаю, что вручную их корректировать это безумие, но единый порядок способствует лучшей нафигации по коду, а следовательно ускорению разработки (еще и глазу приятнее). Поэтому данное правило позволяет всем оставаться довольными без применения усилий, так как автоматически сортирует и группирует импорты. Можно сделать максимально гибко, но базовых настроек уже будет хватать.

  2. Использование eslint-config-flat-gitignore.

    Этот конфиг помогает ESLint обходить ненужные для индексации и проверки файлы и директории. За основу берет .gitignore файл проекта. Соответственно, если все настроено корректно, линтер не будет ходить в build, dist, node_modules и прочие папки.

Использование

  1. Устанавливаем зависимости

    pnpm i -D @company/lint eslint

    Этих зависимостей достаточно, чтобы все заработало. Это возможно благодаря тому, что все плагины и дополнительные зависимости инкапсулированы внутри @company/lint и будут корректно зарезолвлены без конфликтов.

  2. Добавляем файл конфига

    // eslint.config.js
    import eslintReactConfig from '@company/lint/eslint/react';
    
    export default eslintReactConfig;
  3. Добавляем скрипт

    // package.json
    "scripts": {
      "lint:eslint": "eslint . --fix",
    }

Prettier на практике

Prettier – простой и надёжный инструмент форматирования кода, который автоматически приводит файлы к единому стилю.

Иногда форматирование пытаются реализовать через ESLint, поскольку его правила позволяют гибко управлять стилем кода. Однако у такого подхода есть несколько недостатков:

  • авторы ESLint официально отказались от поддержки форматирующих правил (их поддержка перешла в проект ESLint Stylistic);

  • Prettier работает быстрее, чем форматирование через ESLint;

  • большое количество настроек форматирования в ESLint приводит к избыточной конфигурации.

Prettier, наоборот, придерживается минималистичной философии: небольшое количество настроек, которых достаточно для поддержания читаемого и единообразного кода.

Ранее распространённым подходом было использование Prettier вместе с ESLint через eslint-config-prettier и eslint-plugin-prettier.

  • eslint-config-prettier отключал стилистические правила ESLint, которые конфликтовали с Prettier;

  • eslint-plugin-prettier позволял запускать Prettier как правило ESLint.

От этой практики отказались, теперь рекомендуется запускать эти инструменты отдельно, так как это более производительно и независимо.

Использование

  1. Устанавливаем зависимости

    pnpm i -D @company/lint prettier
  2. Добавляем файл конфига

    // .prettierrc
    "@company/lint/prettier"
  3. Добавляем скрипт

    // package.json
    "scripts": {
      "lint:prettier": "prettier . -w --log-level error --ignore-unknown",
    }

    Флаг --ignore-unknown позволяет пропускать файлы, которые Prettier не умеет форматировать.

  4. Добавляем файл для игнора

    // .prettierignore
    pnpm-lock.yaml

    Если используется pnpm, рекомендуется добавить pnpm-lock.yaml в список игнорируемых файлов. В противном случае Prettier может пытаться форматировать его при каждом запуске. В остальном, Prettier по умолчанию смотрит в .gitignore, находящийся в папке запуска, и не сканирует файлы и папки, которые там перечислены.

Stylelint на практике

Использование

  1. Устанавливаем зависимости

    pnpm i -D @company/lint stylelint
  2. Добавляем файл конфига

    // stylelint.config.js
    module.exports = {
      extends: ['@company/lint/stylelint'],
    };
  3. Добавляем скрипт

    // package.json
    "scripts": {
      "lint:style": "stylelint \"{src,packages/*/src}/**/*.css\" --fix",
    }

Madge на практике

С этим инстурументом все просто – установил, добавил конфиг, запустил и получил в консоль ошибки, если они есть.

Использование

  1. Устанавливаем зависимости

    pnpm i -D madge
  2. Добавляем файл конфига

    // .madgerc
    {
      "detectiveOptions": {
        "ts": {
          "skipTypeImports": true
        },
        "tsx": {
          "skipTypeImports": true
        }
      },
      "fileExtensions": ["ts", "tsx"],
      "tsConfig": "./tsconfig.json"
    }

    По желанию можно удалить из конфига игнорирование импортов типов, если вы хотите, чтобы для них тоже не было рекурсии, но в рамках типов обычно это допускается, если мы делаем их через import type.

  3. Добавляем скрипт

    // package.json
    "scripts": {
      "lint:madge": "madge --circular src packages/*/src",
    }

Typescript на практике

Инструмент линтинга кода номер один. Обязателен в современном мире веб разработки. Если вы его не используете, значит полагаетесь на волю случая, ибо одно только использование typescript избавляет вас от 90% багов (субъективная оценка, основанная на прошлом опыте), которые могли бы быть, если бы вы использовали только javascript.

Использование

  1. Устанавливаем зависимости

    pnpm i -D typescript
  2. Добавляем файл конфига tsconfig.json с настройками для вашего проекта

  3. Добавляем скрипт

    // package.json
    "scripts": {
      "lint:ts": "tsc --noEmit",
    }

Lint-staged на практике

Инструмент, который запускает команды только для файлов, изменённых в git staging area (то есть добавленных через git add).

Обычно используется с Husky (разберем далее) в pre-commit hook:

  1. Меняем файлы

  2. Делаем git add.

  3. Перед git commit запускается lint-staged.

  4. Он прогоняет линтеры/форматтеры только по staged-файлам.

  5. Если всё ок – коммит проходит.

Использование

  1. Устанавливаем зависимости

    pnpm i -D lint-staged
  2. Добавляем конфиг

    // package.json
    "lint-staged": {
      "*.{css,ts,tsx}": ["stylelint --fix"],
      "*.{js,jsx,ts,tsx,mjs,cjs}": ["eslint --fix --quiet"],
      "*": ["prettier -w --log-level error --ignore-unknown"]
    }

    Команды для разных масок запускаются параллельно. Если файл подходит под несколько масок – для него выполнятся все подходящие команды.

Husky на практике

Инструмент, который позволит автоматически запускать реализованные выше скрипты, непосредственно перед коммитом изменений.

Использование

  1. Устанавливаем зависимости

    pnpm i -D husky
  2. Добавляем файл конфига

    // .husky/pre-commit
    pnpm lint:madge
    pnpm lint-staged
    pnpm lint:ts

    Важные моменты:

    • запуск lint:madge добавляем сюда, а не в lint-staged, потому что в lint-staged идет работа с каждым файлом отдельно, а здесь один раз сделает прогон и все, экономит время.

    • запуск lint:ts добавляем сюда, а не в lint-staged, потому что в противном случае рискуем закоммитить код, который содержит ошибки. Например, если мы обновили только зависимости в package.jsonlint-staged проверит только сам packages.json и lock файл, но не обнаружит typescript ошибок, которые могли возникнуть из за обновления этих зависимостей.

  3. Добавляем скрипт

    // package.json
    "scripts": {
      "prepare": "husky",
    }

    Этот скрипт сработает автоматически, в момент установки зависимостей (pnpm i), и настроит husky для работы в проекте.

Теперь, когда разработчик решит сделать коммит изменений, то husky автоматически запустит указанные в pre-commit команды.

Конечно, разработчик может отключить запуск Git хуков и проигнорировать проверку, но это уже будет на его совести. Правильным решением здесь будет добавить линтинг в процесс CI, чтобы как только был создан коммит в ветку, запускалась джоба, которая выполнит все проверки и убедится в том, что предоставленный код удовлетворяет всем условиям.

Итоговый пример package.json со всеми реализванными настройками и зависимостями

{
  "scripts": {
    "prepare": "husky",
    "lint:ts": "tsc --noEmit",
    "lint:eslint": "eslint . --fix",
    "lint:madge": "madge --circular src packages/*/src",
    "lint:prettier": "prettier . -w --log-level error --ignore-unknown",
    "lint:style": "stylelint \"{src,packages/*/src}/**/*.css\" --fix",
    "lint": "yarn lint:madge && yarn lint:style && yarn lint:eslint && yarn lint:ts && yarn lint:prettier"
  },
  "lint-staged": {
    "*.{css,ts,tsx}": ["stylelint --fix"],
    "*.{js,jsx,ts,tsx,mjs,cjs}": ["eslint --fix --quiet"],
    "*": ["prettier -w --log-level error --ignore-unknown"]
  },
  "devDependencies": {
    "@company/lint": "^1.0.0",
    "eslint": "^9.39.4",
    "husky": "^9.1.7",
    "lint-staged": "^13.0.3",
    "madge": "^8.0.0",
    "prettier": "^3.8.1",
    "stylelint": "^17.4.0",
    "typescript": "^5.9.3",
  }
}

Удобно, во время разработки, запустить все проверки одной командой pnpm lint. Важно запускать их в правильном корядке, чтобы скрипты не конфликтовали после автоматических правок.

Заключение

Создание пакета с конфигами для линта сильно облегчило мою работу:

  • cтало меньше бойлерплейтного кода в проектах;

  • правила линтинга инкапсулировались в одном месте;

  • удобно обновлять их в одном месте и постепенно применять в каждом проекте обновлением одной зависимости.

Если вы захотите иметь подобный набор инструментов у себя в проектах, чтобы было от чего отталкиваться, можете воспользоваться моим репозиторием https://github.com/Dozalex/lint-configs и пакетом @dozalex/lint.

Конструктивные замечания всегда приветствуются. Буду рад полезному фидбеку, чтобы сделать код еще более качественным и надежным.