Storybook — это инструмент для разработки и документирования пользовательских интерфейсов. Он позволяет изолированно создавать, тестировать и демонстрировать компоненты, что особенно удобно при работе с современными фреймворками, такими как Lit. Storybook строится вокруг концепции историй (stories) — отдельных примеров использования компонентов с конкретными состояниями и данными.
Для интеграции Storybook с проектом на Lit необходимо выполнить установку основных пакетов:
npm install @storybook/web-components @storybook/addon-essentials --save-dev
Инициализация Storybook происходит через команду:
npx sb init
В процессе инициализации выбирается вариант для Web Components, что позволяет корректно работать с Lit-компонентами. После этого создается структура каталогов, включая:
stories — каталог с историями компонентов..storybook — конфигурационные файлы Storybook, такие
как main.js и preview.js.В файле main.js необходимо указать поддержку
web-компонентов:
module.exports = {
stories: ['../src/**/*.stories.@(js|ts)'],
addons: ['@storybook/addon-essentials'],
framework: '@storybook/web-components',
};
Предположим, есть простой компонент на Lit:
import { LitElement, html, css } from 'lit';
export class MyButton extends LitElement {
static properties = {
label: { type: String },
disabled: { type: Boolean },
};
static styles = css`
button {
padding: 8px 16px;
font-size: 16px;
}
button[disabled] {
background-color: #ccc;
cursor: not-allowed;
}
`;
render() {
return html`<button ?disabled=${this.disabled}>${this.label}</button>`;
}
}
customElements.define('my-button', MyButton);
Для него создается файл истории
my-button.stories.js:
import './my-button.js';
export default {
title: 'Components/MyButton',
component: 'my-button',
argTypes: {
label: { control: 'text' },
disabled: { control: 'boolean' },
},
};
const Template = ({ label, disabled }) => {
const el = document.createElement('my-button');
el.label = label;
el.disabled = disabled;
return el;
};
export const Default = Template.bind({});
Default.args = {
label: 'Click Me',
disabled: false,
};
export const Disabled = Template.bind({});
Disabled.args = {
label: 'Cannot Click',
disabled: true,
};
Ключевой момент — использование argTypes и
args, которые позволяют динамически изменять свойства
компонента через интерфейс Storybook.
Storybook поддерживает аддоны, которые улучшают визуализацию и документацию компонентов:
Пример подключения аддонов в main.js:
module.exports = {
addons: [
'@storybook/addon-essentials',
'@storybook/addon-a11y',
'@storybook/addon-actions',
],
};
Использование Actions для события кнопки:
import { action } from '@storybook/addon-actions';
const Template = ({ label, disabled }) => {
const el = document.createElement('my-button');
el.label = label;
el.disabled = disabled;
el.addEventListener('click', action('button-click'));
return el;
};
Истории удобно группировать по категориям, например:
Components/
├─ Buttons/
│ ├─ my-button.stories.js
│ └─ icon-button.stories.js
├─ Inputs/
│ └─ text-input.stories.js
Использование иерархии title позволяет создавать
древовидное отображение в боковой панели Storybook:
export default {
title: 'Components/Buttons/MyButton',
component: 'my-button',
};
Каждая история должна демонстрировать отдельное состояние компонента. Например, для кнопки:
Storybook Docs автоматически формирует превью и описание компонентов, если они имеют JSDoc-комментарии:
/**
* Компонент кнопки.
*
* @prop {string} label - Текст кнопки
* @prop {boolean} disabled - Отключает кнопку
*/
Документация включает:
props) и их типы.Lit-компоненты поддерживают:
Storybook полностью поддерживает эти возможности. Например, для компонента с slot:
import { LitElement, html } from 'lit';
export class CardComponent extends LitElement {
render() {
return html`
<div class="card">
<slot></slot>
</div>
`;
}
}
customElements.define('card-component', CardComponent);
История:
export const WithContent = () => {
const el = document.createElement('card-component');
el.innerHTML = '<p>Содержимое карточки</p>';
return el;
};
Storybook предоставляет:
Запуск:
npm run storybook
После чего компоненты доступны по адресу
http://localhost:6006.
Storybook в связке с Lit позволяет строить полный каталог UI-компонентов, который легко поддерживать и расширять, обеспечивая высокую модульность и прозрачность интерфейсов.