Stop writing API docs by hand. Generate documentation from Python docstrings, CLI help text, and OpenAPI specs—kept in sync automatically.

Tip

Duration: ~60 min | Prerequisite: Python codebase or API spec to document

Section 1: Page Not Found

Could not find page:docs/extending/autodoc/_index

2

Content Collections

Validate frontmatter with typed schemas

Content Collections

Define typed schemas for your content to ensure consistency and catch errors early.

Do I Need This?

No. Collections are optional. Your site works fine without them.

Use collections when:

  • You want typos caught at build time, not in production
  • Multiple people edit content and need guardrails
  • You want consistent frontmatter across content types

Quick Setup

bengal collections init

This createscollections.pyat your project root. Edit it to uncomment what you need:

1
2
3
4
5
6
from bengal.collections import define_collection, BlogPost, DocPage

collections = {
    "blog": define_collection(schema=BlogPost, directory="blog"),
    "docs": define_collection(schema=DocPage, directory="docs"),
}

Done. Build as normal—validation happens automatically.

Built-in Schemas

Bengal provides schemas for common content types:

Schema Required Fields Optional Fields
BlogPost title, date author, tags, draft, description, image
DocPage title weight, category, tags, toc, deprecated
APIReference title, endpoint method, version, auth_required, rate_limit
Tutorial title difficulty, duration, prerequisites, series
Changelog title, date version, breaking, summary

Import any of these:

from bengal.collections import BlogPost, DocPage, APIReference

Custom Schemas

Define your own using Python dataclasses:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
from dataclasses import dataclass, field
from datetime import datetime
from typing import Optional

@dataclass
class ProjectPage:
    title: str
    status: str  # "active", "completed", "archived"
    started: datetime
    tech_stack: list[str] = field(default_factory=list)
    github_url: Optional[str] = None

collections = {
    "projects": define_collection(
        schema=ProjectPage,
        directory="projects",
    ),
}

Validation Modes

By default, validation warns but doesn't fail builds:

⚠ content/blog/my-post.md
  └─ date: Required field 'date' is missing

Strict Mode

To fail builds on validation errors, add tobengal.toml:

1
2
[build]
strict_collections = true

Lenient Mode (Extra Fields)

To allow fields not in your schema:

1
2
3
4
5
define_collection(
    schema=BlogPost,
    directory="blog",
    strict=False,  # Allow extra frontmatter fields
)

CLI Commands

1
2
3
4
5
6
7
8
# List defined collections and their schemas
bengal collections list

# Validate content without building
bengal collections validate

# Validate specific collection
bengal collections validate --collection blog

Migration Tips

Existing site with inconsistent frontmatter?

  1. Start withstrict=Falseto allow extra fields
  2. Runbengal collections validateto find issues
  3. Fix content or adjust schema
  4. Switch tostrict=Truewhen ready

Transform legacy field names:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
def migrate_legacy(data: dict) -> dict:
    if "post_title" in data:
        data["title"] = data.pop("post_title")
    return data

collections = {
    "blog": define_collection(
        schema=BlogPost,
        directory="blog",
        transform=migrate_legacy,
    ),
}

Remote Content

Collections work with remote content too. Use a loader instead of a directory:

1
2
3
4
5
6
7
8
9
from bengal.collections import define_collection, DocPage
from bengal.content_layer import github_loader

collections = {
    "api-docs": define_collection(
        schema=DocPage,
        loader=github_loader(repo="myorg/api-docs", path="docs/"),
    ),
}

See Content Sources for GitHub, Notion, REST API loaders.

Seealso

3

Deployment

Deploy your Bengal site to production

Deploy Your Site

Bengal generates static HTML, CSS, and JavaScript files. This means you can host your site anywhere that serves static files (e.g., GitHub Pages, Netlify, Vercel, AWS S3, Nginx).

The Production Build

When you are ready to ship, run the build command:

bengal build --environment production

This command:

  • Loads configuration fromconfig/environments/production.yaml(if it exists)
  • Minifies assets (if enabled)
  • Generates thepublic/directory with your complete site

Common Build Flags

Flag Description Use Case
--environment production Loads production config overrides. Always use for shipping.
--strict Fails the build on warnings (e.g., broken links). Highly Recommended for CI/CD.
--clean-output Cleans thepublic/directory before building. Recommended to avoid stale files.
--verbose Shows detailed logs. Useful for debugging CI failures.

Example full command for CI:

bengal build --environment production --strict --clean-output

GitHub Pages

Deploy using GitHub Actions. Create.github/workflows/deploy.yml:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
name: Deploy to GitHub Pages

on:
  push:
    branches: [main]

permissions:
  contents: read
  pages: write
  id-token: write

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Set up Python
        uses: actions/setup-python@v5
        with:
          python-version: '3.14'

      - name: Install Bengal
        run: pip install bengal

      - name: Build Site
        run: bengal build --environment production --strict

      - name: Upload artifact
        uses: actions/upload-pages-artifact@v3
        with:
          path: './public'

  deploy:
    environment:
      name: github-pages
      url: ${{ steps.deployment.outputs.page_url }}
    runs-on: ubuntu-latest
    needs: build
    steps:
      - name: Deploy to GitHub Pages
        id: deployment
        uses: actions/deploy-pages@v4

Netlify

Create anetlify.tomlin your repository root:

1
2
3
4
5
6
[build]
  publish = "public"
  command = "bengal build --environment production"

[build.environment]
  PYTHON_VERSION = "3.14"

Vercel

Configure your project:

  1. Build Command:bengal build --environment production
  2. Output Directory:public
  3. Ensure yourrequirements.txtincludesbengal.

Environment Variables

Bengal allows you to inject environment variables into your configuration using{{ env.VAR_NAME }}syntax in your YAML/TOML config files.

config/environments/production.yaml:

1
2
3
params:
  api_key: "{{ env.API_KEY }}"
  analytics_id: "{{ env.ANALYTICS_ID }}"

Then setAPI_KEYandANALYTICS_IDin your hosting provider's dashboard.

Pre-Deployment Checklist

Before you merge to main or deploy:

  1. Runbengal config doctor: Checks for common configuration issues.
  2. Runbengal build --strictlocally: Ensures no broken links or missing templates.
  3. Checkconfig/environments/production.yaml: Ensure yourbaseurlis set to your production domain.
1
2
3
# config/environments/production.yaml
site:
  baseurl: "https://example.com"

Seealso