---
layout: ~/layouts/MdxDocLayout.astro
title: "Contributing"
description: "Learn how to contribute to Kumo by adding new components and features."
---

import CodeBlock from "~/components/docs/CodeBlock.astro";
import Callout from "~/components/docs/Callout.astro";

## Contributing to Kumo

We welcome contributions to Kumo! This guide will help you get started with adding new components and blocks to the library.

## Components vs Blocks vs Layouts

**Components** — Atomic, reusable UI elements

- Single responsibility
- Highly reusable
- Minimal dependencies
- Style-focused

Examples: Button, Input, Badge, Tabs

**Blocks** — Composed patterns for page layouts

- Compose multiple components
- Implement common patterns
- Layout-focused
- May include business logic

Examples: Breadcrumbs, PageHeader, Empty

**Layouts** — Page-level structure patterns

- Full-page composition
- Consistent structure
- Responsive patterns
- Application-wide use

Examples: DashboardPage

## Creating New Components

Kumo includes a scaffolding tool that automates component creation. This ensures all components follow the same structure and are properly configured.

### Run the Scaffolding Tool

From the workspace root, run:

<CodeBlock code={`pnpm --filter @cloudflare/kumo new-component`} lang="bash" />

## What the Scaffolding Tool Does

The tool automatically creates and updates several files:

- **Component file** — `src/components/{name}/{name}.tsx`
- **Index file** — `src/components/{name}/index.ts`
- **Story file** — `src/components/{name}/{name}.stories.tsx`
- **Test file** — `src/components/{name}/{name}.test.tsx`
- **Main exports** — Updates `src/index.ts`
- **Build config** — Updates `vite.config.ts`
- **Package exports** — Updates `package.json`

## Example

Here's what the scaffolding process looks like:

<CodeBlock
  code={`? Component name: Alert Banner

✅ Component scaffolded successfully!

📁 Files created:

- src/components/alert-banner/alert-banner.tsx
- src/components/alert-banner/index.ts
- src/components/alert-banner/alert-banner.stories.tsx
- src/components/alert-banner/alert-banner.test.tsx

📝 Files updated:

- src/index.ts
- vite.config.ts
- package.json

💡 Import examples:
import { AlertBanner } from "@cloudflare/kumo";
import { AlertBanner } from "@cloudflare/kumo/components/alert-banner";`}
lang="bash"
/>

## Component Naming

The scaffolding tool handles naming automatically. You can input the name in any format:

- **Spaces** — "Alert Banner" → `alert-banner` directory, `AlertBanner` component
- **PascalCase** — "AlertBanner" → `alert-banner` directory, `AlertBanner` component
- **kebab-case** — "alert-banner" → `alert-banner` directory, `AlertBanner` component

## Creating New Blocks

Blocks are higher-level components that compose multiple base components. Use the block scaffolding tool to create them:

### Run the Block Scaffolding Tool

From the workspace root, run:

<CodeBlock code={`pnpm --filter @cloudflare/kumo new-block`} lang="bash" />

### What It Creates

The block scaffolding tool creates the same structure as components, but in the `src/blocks` directory:

- **Block file** — `src/blocks/{name}/{name}.tsx`
- **Index file** — `src/blocks/{name}/index.ts`
- **Story file** — `src/blocks/{name}/{name}.stories.tsx`
- **Test file** — `src/blocks/{name}/{name}.test.tsx`
- **Main exports** — Updates `src/index.ts` (Blocks section)
- **Build config** — Updates `vite.config.ts`
- **Package exports** — Updates `package.json`

### Example

<CodeBlock
  code={`? Block name: Navigation Bar

✅ Block scaffolded successfully!

📁 Files created:

- src/blocks/navigation-bar/navigation-bar.tsx
- src/blocks/navigation-bar/index.ts
- src/blocks/navigation-bar/navigation-bar.stories.tsx
- src/blocks/navigation-bar/navigation-bar.test.tsx

📝 Files updated:

- src/index.ts
- vite.config.ts
- package.json

💡 Import examples:
import { NavigationBar } from "@cloudflare/kumo";
import { NavigationBar } from "@cloudflare/kumo/blocks/navigation-bar";`}
lang="bash"
/>

## Creating New Layouts

Layouts are page-level components that provide consistent structure for common page patterns. Use the layout scaffolding tool:

### Run the Layout Scaffolding Tool

From the workspace root, run:

<CodeBlock code={`pnpm --filter @cloudflare/kumo new-layout`} lang="bash" />

### What It Creates

The layout scaffolding tool creates the same structure as components and blocks, but in the `src/layouts` directory:

- **Layout file** — `src/layouts/{name}/{name}.tsx`
- **Index file** — `src/layouts/{name}/index.ts`
- **Story file** — `src/layouts/{name}/{name}.stories.tsx`
- **Test file** — `src/layouts/{name}/{name}.test.tsx`
- **Main exports** — Updates `src/index.ts` (Layouts section)
- **Build config** — Updates `vite.config.ts`
- **Package exports** — Updates `package.json`

### Example

<CodeBlock
  code={`? Layout name: Dashboard Page

✅ Layout scaffolded successfully!

📁 Files created:

- src/layouts/dashboard-page/dashboard-page.tsx
- src/layouts/dashboard-page/index.ts
- src/layouts/dashboard-page/dashboard-page.stories.tsx
- src/layouts/dashboard-page/dashboard-page.test.tsx

📝 Files updated:

- src/index.ts
- vite.config.ts
- package.json

💡 Import examples:
import { DashboardPage } from "@cloudflare/kumo";
import { DashboardPage } from "@cloudflare/kumo/layouts/dashboard-page";`}
lang="bash"
/>

## Development Workflow

After scaffolding a component, block, or layout, use the watch build setup to develop with the documentation site:

### Watch Build Setup

Run these commands in separate terminals for development with HMR:

<CodeBlock
  code={`# Terminal 1: Watch mode for kumo package
pnpm --filter @cloudflare/kumo dev

# Terminal 2: Documentation site dev server

pnpm dev`}
lang="bash"
/>

- Fast rebuild time (~400ms)
- Validates bundle exports/imports
- Tests actual build output
- See components in real documentation context

### Implementation Steps

1. **Implement the component/block/layout** — Edit the generated `.tsx` file in the kumo package.

2. **Create demo file** — Add a `{Name}Demo.tsx` file in `kumo-docs-astro/src/components/demos/` to showcase component variants.

3. **Write tests** — Add tests to the generated `.test.tsx` file. Run tests in watch mode while developing.

<CodeBlock code={`pnpm --filter @cloudflare/kumo test`} lang="bash" />

4. **Build the package** — Before committing, do a full production build to ensure everything works:

<CodeBlock code={`pnpm --filter @cloudflare/kumo build`} lang="bash" />

5. **Regenerate registry** — Update the component registry to include examples from your demo file:

<CodeBlock
  code={`pnpm --filter @cloudflare/kumo codegen:registry`}
  lang="bash"
/>

6. **Add documentation page** — Create a documentation page in `kumo-docs-astro/src/pages/` showing real-world usage examples.

## Testing

The test suite automatically validates your component, block, or layout configuration:

- Main entry point exports the component/block/layout
- Deep import paths work correctly (`@cloudflare/kumo/components/*`, `@cloudflare/kumo/blocks/*`, or `@cloudflare/kumo/layouts/*`)
- Package.json exports are properly configured
- Build configuration is correct
- All files exist in the correct locations

Run the test suite to ensure everything is configured correctly:

<CodeBlock code={`pnpm --filter @cloudflare/kumo test:run`} lang="bash" />

The tests will provide helpful error messages with exact code snippets if any configuration is missing.

## Component Guidelines

When implementing components, follow these guidelines:

- **Accessibility** — Include proper ARIA attributes and keyboard navigation
- **TypeScript** — Export prop types and use proper type annotations
- **Styling** — Use Tailwind CSS classes and the `cn` utility
- **Consistency** — Follow existing component patterns and naming conventions
- **Documentation** — Add clear JSDoc comments and usage examples
- **Testing** — Include unit tests for component behavior
- **Single Responsibility** — Keep components focused on one task

## Block Guidelines

When implementing blocks, follow these additional guidelines:

- **Composition** — Compose existing components rather than reimplementing functionality
- **Framework Agnostic** — Use `LinkProvider` for routing to remain framework-agnostic
- **Flexible Props** — Accept both simple and complex props to support various use cases
- **Common Patterns** — Focus on patterns that appear in multiple applications
- **Documentation** — Include JSDoc explaining the block's purpose and when to use it
- **Examples** — Provide clear usage examples showing composition

### When to Create a Block

- Pattern appears in multiple places across applications
- Combines 2+ base components
- Implements a common layout or page structure
- Has specific business logic or behavior

### When NOT to Create a Block

- Single component with styling variations (use component variants instead)
- Application-specific logic (keep in application code)
- One-off patterns (wait for reuse before abstracting)

## Additional Resources

For more detailed information, refer to:

- [GitHub Repository](https://github.com/cloudflare/kumo)
- [Base UI Documentation](https://base-ui.com/)
