CONTRIBUTING

August 31, 2026 · View on GitHub

Библиотека компонентов Konur UI — это открытый проект и результат совместных усилий большого количества людей. Мы очень ценим вклад каждого и приглашаем всех желающих принять участие в его развитии. Этот гайд призван помочь новым участникам познакомиться с проектом и ответить на основные вопросы касательно его разработки.

Содержание

Общие сведения

Технологии

  • JS: React, TypeScript;
  • CSS: Emotion (css-in-js);
  • Сборка: Babel;

Дизайн

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

Краткая инструкция

После настройки и клонирования проекта работа над задачей в общем случае выглядит так:

  1. Выполнить задачу в отдельной ветке
  2. Добавить тесты и документацию
  3. Прогнать unit-тесты и линтеры
  4. Оформить pull request

Команды, доступные в проектах:

  • yarn workspace @skbkontur/react-ui <command> - контролы
    • test — unit-тесты Vitest + React Testing Library
    • creevey:ui — скриншотные тесты Creevey
    • lint — tsc --noEmit + oxlint + oxfmt
    • creevey:ci — CI-режим скриншотных тестов
    • lint — tsc --noEmit + oxlint + oxfmt
    • build — сборка библиотеки
    • storybook — Storybook
    • storybook:test — Storybook со стилями для тестов
    • fix — форматирование кода по правилам oxlint и oxfmt
  • yarn workspace react-ui-testing <command> - интеграционные тесты
    • start — старт приложения для интеграционных тестов (используется собранная версия библиотеки)
    • test — интеграционные тесты с использованием SeleniumTesting (работает только во внутренней сети Контура)
  • yarn workspace react-ui-validations <command> - валидации
    • start:docs — документация
    • test — unit-тесты
    • lint — линтеры + oxfmt
    • storybook — Storybook
    • fix — форматирование кода по правилам oxlint и oxfmt
  • yarn workspace react-ui-smoke-test test - smoke-тест сборки и запуска тестового приложения
  • yarn set-testing-package-versions - подменить версии зависимостей для matrix-прогона
  • yarn reset-testing-package-versions - вернуть версии зависимостей к состоянию репозитория
    • fix — форматирование кода по правилам oxlint и oxfmt

Начало работы

Настройка

Для начала необходимо иметь установленными следующие инструменты:

Репозиторий

Вся разработка ведется на GitHub. Монорепозиторий на базе lerna помимо самой библиотеки контролов содержит также библиотеку валидаций и инструменты тестирования.

Права на запись в репозиторий имеет ограниченный круг разработчиков. Информацию о том, как стать одним из них, вы найдете разделе помощь. А пока можно сделать Fork и работать через него.

Клонирование

Перейдите в выбранную директорию для клонирования и выполните команду:

git clone git@github.com:skbkontur/retail-ui.git

Или, в случае форка:

git clone git@github.com:%YOUR_USER_NAME%/retail-ui.git

Работая с форком, полезно добавить upstream в качестве удаленного репозитория:

 git remote add upstream git@github.com:skbkontur/retail-ui.git

Теперь легко можно синхронизировать свой форк с основным репозиторием:

 git fetch upstream
 git checkout master
 git merge upstream/master

Ветки

Начиная работу над задачей, создайте для нее отдельную ветку. Если задачей является фикс критичной проблемы в стабильной версии, то ветку нужно делать от master. В остальных случаях — от next.

Коммиты

Особое внимание стоит уделить коммитам. В проекте используется commitlint с конфигурацией config-conventional. Это означает, что сообщения ваших коммитов должны соответствовать следующему формату:

type(scope?): short description

Например:

feat(ComboBox): new prop 'searchOnFocus'
fix(Button): fix icon padding
chore: update dependencies

тип должен быть одним из следующих ключевых слов:

  • feat: новая функциональность
  • fix: исправление бага
  • test: добавление и корректировка тестов
  • refactor: рефакторинг
  • docs: изменение документации
  • build: изменения в системе сборки или внешних зависимостях
  • perf: улучшение производительности кода
  • style: изменение стиля кода (именование, форматирование и прочее)
  • ci: изменения конфигурационных файлов и скриптов CI
  • chore: прочие изменения

scope - опциональный параметр, указывающий на область изменений. Это может быть имя компонента или пакета.

short description - минимальное сообщение на английском языке, отражающее суть внесенных изменений.

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

fix(RenderLayer): add touchstart handling

iOS mouse events don't bubble up, use touchstart event instead

Closes #1439

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

Также, для составления правильного сообщения коммита можно воспользоваться интерактивной командой yarn commit.

Важно! Все коммиты типа feat и fix попадают в changelog. Поэтому, желательно, чтобы их краткое описание являлось информативным для широкого круга пользователей. По этой же причине, не стоит создавать более одного коммита этих типов на одну решенную задачу, иначе все они попадут в changelog. Для дополнительных коммитов, которые неизбежно возникают в процессе, можно использовать тип refactor, chore или любой другой из вышеописанных, который подойдет лучше.

Кодовая база

Структура файлов

packages/
├── ...
├── react-ui-validations/
└── react-ui/
    ├── .creevey/
    ├── .storybook/
    ├── ...
    └── components/
        ├── ...
        └── Button/
            ├── __stories__/
            ├── __tests__/
            ├── Button.tsx
            ├── Button.styles.ts
            ├── ...
            └── README.md
Директория / ФайлОписание
react-ui-validations/Библиотека валидаций
react-ui/Библиотека контролов
react-ui/.creevey/Скриншотные тесты
react-ui/.storybook/Конфиг Storybook
react-ui/components/Компоненты контролов
react-ui/components/ButtonКомпонент кнопки
react-ui/components/Button/__stories__/Stories для Storybook
react-ui/components/Button/__tests__/Unit-тесты
react-ui/components/Button/Button.tsxКод компонента
react-ui/components/Button/Button.styles.tsКастомизируемые стили
react-ui/components/Button/README.mdДокументация

Code style

Для контроля над стилем и форматированием кода в проекте используются .editorconfig, oxlint и oxfmt. По возможности, рекомендуем установить соответствующие плагины в свою IDE, чтобы получать от нее предупреждения в режиме реального времени. Но запускать линтеры можно и вручную, с помощью команды yarn workspace @skbkontur/react-ui lint. Советуем делать это перед каждым коммитом или пользоваться командой yarn commit. PR, не прошедший проверку линтеров, не может быть принят.

Тесты

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

Unit-тесты

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

Для unit-тестирования в проекте используются Vitest и React Testing Library. Тесты находятся в поддиректориях __tests__ внутри почти каждого компонента. Для их запуска служат команды yarn workspace @skbkontur/react-ui test и yarn workspace @skbkontur/react-ui-validations test. Их желательно выполнять перед отправкой своих изменений, чтобы убедиться в том, что они не сломали существующие сценарии.

В проекте также может присутствовать некоторое количество тестов на Enzyme. В будущем они будут переписаны с использованием React Testing Library. Для новых тестов стоит сразу использовать RTL.

Storybook

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

Запускается командой yarn workspace @skbkontur/react-ui storybook.

Создание story

Все story находятся в файлах __stories__/[ComponentName].stories.tsx, в директориях своих компонентов. Просто добавьте новое состояние и оно появится в storybook:

export const ButtonWithError = () => <Button error>Error</Button>;

Скриншотные тесты

Скриншотные тесты пишут для проверки верстки и отдельной функциональности в различных браузерах (Chrome, Firefox). В проекте они построены на основе Creevey и Storybook. Для удобства поддержки нужно разделять статичные и интерактивные тесты и выносить в отдельные файлы стори. Статичные тесты — те, в которых рендерятся элементы и не производятся никакие действия над ними. Интерактивные — те, где производятся разные пользовательские манипуляции. Интерактивные тесты необходимо выделить в __stories__/[ComponentName].creevey.stories.tsx, а статичные в __stories__/[ComponentName].stories.tsx

Скриншоты являются сравнительно дорогим видом тестирования. Используйте их, если unit-тестов недостаточно.

Конфиг для Creevey ожидает переменные окружения GRID_URL и GET_IP_URL. Поэтому, для локального запуска добавьте их в файл .env в корне репозитория. Ребята из Контура могут использовать значения для переменных отсюда.

Запуск

yarn workspace @skbkontur/react-ui storybook:test - запуск storybook со стилями для тестов

yarn workspace @skbkontur/react-ui creevey:ui - запуск creevey с web-интерфейсом

Создание скриншотного теста

  1. Создать или выбрать готовую story
  2. Добавить сценарий в параметры story
ButtonWithError.parameters = {
  creevey: {
    tests: {
      async idle() {
        await this.expect(await this.takeScreenshot()).to.matchImage('idle');
      },
    },
  },
};
  1. Через gui запустить добавленный тест
  2. Принять новые скриншоты в интерфейсе или с помощью команды yarn workspace @skbkontur/react-ui creevey --update

Существующие тесты обновляются тем же образом (шаги 3 и 4).

Matrix-совместимость

Matrix-тесты проверяют не только текущий стек репозитория, но и совместимость библиотеки с несколькими версиями React. Для этого перед прогоном временно переписываются версии зависимостей, затем выполняется yarn install, а после установки проверяется, что в node_modules действительно оказались ожидаемые версии пакетов.

Что именно проверяется

  • @skbkontur/react-ui: unit-тесты, сборка, screenshot-тесты
  • @skbkontur/react-ui-validations: unit-тесты, сборка, screenshot-тесты
  • react-ui-smoke-test: smoke-тест сборки и запуска тестового приложения

Локальный прогон matrix-окружения

  1. Выберите целевое окружение. Сейчас поддерживаются REACT_VERSION=16|17|18|19 и TYPESCRIPT_VERSION=4|5.
  2. Установите переменные окружения, например:
export REACT_VERSION=18
export TYPESCRIPT_VERSION=5
  1. Подмените версии зависимостей под выбранное окружение:
yarn set-testing-package-versions
  1. Переустановите зависимости:
yarn install
  1. Убедитесь, что в node_modules действительно установились ожидаемые версии:
node scripts/testing/verify-installed-package-versions.mts
  1. Прогоните нужные проверки:
yarn workspace @skbkontur/react-ui test
yarn workspace @skbkontur/react-ui-validations test
yarn workspace react-ui-smoke-test test
  1. Для screenshot-тестов используйте тот же стек зависимостей:
yarn workspace @skbkontur/react-ui storybook:build
yarn workspace @skbkontur/react-ui creevey:ci

yarn workspace @skbkontur/react-ui-validations storybook:build
yarn workspace @skbkontur/react-ui-validations creevey:ci
  1. После завершения matrix-прогона обязательно верните репозиторий к штатным версиям:
yarn reset-testing-package-versions
yarn install

Как правильно интерпретировать результаты

  • Проверка verify-installed-package-versions.mts читает версии из реально установленных пакетов, а не из package.json. Это источник истины для matrix-прогона.
  • Matrix-прогон проверяет runtime-совместимость. Для старых версий React в matrix-режиме допускается пропуск tsc, потому что кодовая база типизирована под актуальные React types.
  • Для React 16 и React 17 вместе с React меняются и версии testing-library. Если падает unit-тест, сначала проверьте, не завязан ли он слишком жёстко на форму synthetic event или timing тестового раннера.
  • Для React 18 и React 19 частая причина падений — асинхронность, act(...), portal/render timing и поведение concurrent rendering.
  • Локальный успех screenshot-теста не гарантирует успех в CI. Финальный baseline для screenshot-тестов нужно проверять и при необходимости переаппрувливать в том же CI-окружении, где тест реально падает.

Документация

JSDoc

Для документирования отдельных утилит и хелперов в проекте используется jsdoc.

Простейший пример выглядит так:

/** This is a description of the foo function. */
function foo() {}

Комментарии в коде

В неочевидных и сложных для понимания местах кода следует оставлять поясняющие комментарии.

Pull Request

После отправки изменений на сервер появится возможность создать pull request (PR) в основной репозиторий. Опишите сделанные вами изменения по специальному шаблону, чтобы проверяющим было проще в нем ориентироваться. PR следует делать в ту ветку, от которой была создана рабочая ветка.

Работа над PR

В проекте приняты следующие соглашения и правила работы над PR:

  1. Перед запросом ревью PR должен быть оформлен по шаблону
  2. После начала ревью и внесения последующих правок, ревью следует перезапрашивать
  3. Резолв тредов во время ревью осуществляется их автором
  4. Все договоренности и результаты ревью, даже если они происходили вне github, следует зафиксировать в PR
  5. После запроса ревью делать force-push уже нежелательно

Соглашения

Соглашения по фича-флагам

Добавление нового флага реализуется по алгоритму:

  1. Сформируйте название флага по правилу [Название компонента или области]+[Описание изменения]. Стоит избегать общих слов, таких как "change". Вместо этого опишите в чем конкретно произошло изменение.

    Примеры:

    • tokenInputRemoveWhitespaceFromDefaultDelimiters - В TokenInput изменили разделитель по умолчанию
  2. Добавьте флаг в ReactUIFeatureFlags в файл ReactUIFeatureFlagsContext.tsx и в документацию FEATUREFLAGSCONTEXT.md

Помощь

По любым возникающим вопросам можно обращаться в канал поддержки в Маттермосте - #infra_front_support