Storybookの基本
コンポーネントカタログとは何か、セットアップから最初のストーリーまでを学ぼう
Storybookとは?
Storybookは、UIコンポーネントをアプリケーションから独立した環境で 開発・テスト・ドキュメント化するためのオープンソースツールです。 React、Vue、Angular、Svelte、Web Componentsなど主要なフレームワークに対応しています。
Storybookがない場合
- コンポーネントの確認にアプリ全体の起動が必要
- 特定の状態の再現が手間(エラー状態、ローディング等)
- デザイナーとの認識合わせが難しい
- コンポーネントの一覧性がない
Storybookがある場合
- コンポーネント単体で即座に確認・操作できる
- あらゆる状態をストーリーとして定義・再現可能
- デザイナーもブラウザで確認できる
- コンポーネントカタログとして一覧管理
コンポーネント駆動開発(CDD)
コンポーネント駆動開発(Component-Driven Development)は、UIを小さなコンポーネントから ボトムアップで構築していく手法です。Storybookはこの開発スタイルの中核ツールです。
1. Atoms(原子)
ボタン、入力欄、アイコンなど最小単位のUI要素
2. Molecules(分子)
検索バー(入力欄+ボタン)のようなAtomsの組み合わせ
3. Organisms(有機体)
ヘッダー、サイドバーなどMoleculesを含む複合コンポーネント
4. Pages(ページ)
Organismsを配置したページ全体のレイアウト
Storybookでは各レイヤーのコンポーネントをストーリーとして登録し、 個別に開発・テストできます。
インストールとセットアップ
Storybookは既存のプロジェクトに1コマンドで追加できます。 フレームワークやビルドツールを自動検出して最適な設定を生成してくれます。
# 既存プロジェクトにStorybookを追加
npx storybook@latest init
# 実行すると以下が自動的に行われる:
# 1. フレームワーク(React, Vue等)を検出
# 2. 必要なパッケージをインストール
# 3. .storybook/ ディレクトリに設定ファイルを生成
# 4. サンプルストーリーを作成Next.jsプロジェクトの場合は、自動的に@storybook/nextjsが 選択され、Next.jsの機能(Image、Link、Router等)がStorybook内で動作するように設定されます。
# package.jsonに追加されるスクリプト
{
"scripts": {
"storybook": "storybook dev -p 6006",
"build-storybook": "storybook build"
}
}プロジェクト構造
Storybookの設定は.storybook/ディレクトリに格納されます。 主要なファイルの役割を理解しましょう。
プロジェクトルート/
├── .storybook/
│ ├── main.ts # Storybookの主設定ファイル
│ └── preview.ts # ストーリー表示の共通設定
├── src/
│ └── components/
│ ├── Button.tsx
│ └── Button.stories.tsx # ストーリーファイル
└── package.jsonmain.ts
ストーリーの検索パス、アドオン、フレームワーク設定を定義
// .storybook/main.ts
import type { StorybookConfig } from "@storybook/nextjs";
const config: StorybookConfig = {
stories: ["../src/**/*.stories.@(ts|tsx)"],
addons: [
"@storybook/addon-essentials",
],
framework: {
name: "@storybook/nextjs",
options: {},
},
};
export default config;preview.ts
すべてのストーリーに共通する設定(グローバルスタイル、デコレーター等)
// .storybook/preview.ts
import type { Preview } from "@storybook/react";
import "../src/app/globals.css"; // グローバルCSS
const preview: Preview = {
parameters: {
controls: {
matchers: {
color: /(background|color)$/i,
date: /Date$/i,
},
},
},
};
export default preview;最初のストーリーを書いてみよう
ストーリーファイルは*.stories.tsxという命名規則で作成します。 コンポーネントと同じディレクトリに置くのが一般的です。
// src/components/Button.tsx
interface ButtonProps {
label: string;
variant?: "primary" | "secondary";
size?: "sm" | "md" | "lg";
onClick?: () => void;
}
export function Button({
label,
variant = "primary",
size = "md",
onClick,
}: ButtonProps) {
const base = "rounded font-semibold transition-colors";
const variants = {
primary: "bg-blue-600 text-white hover:bg-blue-700",
secondary: "bg-gray-200 text-gray-800 hover:bg-gray-300",
};
const sizes = {
sm: "px-3 py-1.5 text-sm",
md: "px-4 py-2 text-base",
lg: "px-6 py-3 text-lg",
};
return (
<button
className={`${base} ${variants[variant]} ${sizes[size]}`}
onClick={onClick}
>
{label}
</button>
);
}// src/components/Button.stories.tsx
import type { Meta, StoryObj } from "@storybook/react";
import { Button } from "./Button";
const meta: Meta<typeof Button> = {
title: "Components/Button",
component: Button,
};
export default meta;
type Story = StoryObj<typeof Button>;
// 基本のストーリー
export const Primary: Story = {
args: {
label: "ボタン",
variant: "primary",
size: "md",
},
};
export const Secondary: Story = {
args: {
label: "キャンセル",
variant: "secondary",
},
};# Storybookを起動して確認
npm run storybook
# ブラウザで http://localhost:6006 が開く
# サイドバーに "Components / Button" が表示されるまとめ
- StorybookはUIコンポーネントを独立環境で開発・テスト・ドキュメント化するツール
- コンポーネント駆動開発(CDD)でボトムアップにUIを構築できる
npx storybook@latest initで既存プロジェクトに簡単に追加.storybook/ディレクトリにmain.tsとpreview.tsが設定の中心- ストーリーファイルは
*.stories.tsxの命名規則で作成する