Required Frontmatter Structure for Lesson Markdown Files in AI Engineering from Scratch

Every lesson markdown file in the rohitg00/ai-engineering-from-scratch repository must include a strict YAML frontmatter block in docs/en.md containing Title, Type, Languages, Prerequisites, Time, and Learning Objectives to pass CI validation and power the curriculum site.

The ai-engineering-from-scratch curriculum enforces a machine-readable metadata contract for every lesson. This required frontmatter structure drives the README lesson table generator, the site/data.js catalog, and the automated quiz schema validation in scripts/audit_lessons.py.

Anatomy of the Required Frontmatter Block

According to the lesson contract defined in AGENTS.md (lines 70–84), the frontmatter must precede the body of docs/en.md and follow this exact sequence:


# <Title>

> <One‑line hook>

**Type:** <Learn | Build | Reference>
**Languages:** <comma‑list matching the main.* files in code/>
**Prerequisites:** <comma‑list of upstream lessons, or "None">
**Time:** ~<estimate in minutes>

## Learning Objectives

- <4‑6 bullet points starting with a verb>

The parser recognizes seven mandatory components:

  • Title — An H1 heading containing the human-readable lesson name.
  • One-line hook — A memorable tagline inside a blockquote (>) summarizing the core concept.
  • Type — Must be one of Learn (conceptual), Build (implementation-focused), or Reference (documentation-only).
  • Languages — A comma-separated list that must exactly match the programming languages for which a main.<ext> file exists under the lesson’s code/ directory (e.g., Python, TypeScript, Rust).
  • Prerequisites — A comma-separated list of upstream lesson identifiers (e.g., 01-math-basics, 02-gradient-descent) or the string "None" if the lesson is entry-level.
  • Time — An approximate duration prefixed with a tilde (e.g., ~45 minutes).
  • Learning Objectives — An H2 section containing 4–6 actionable bullets, each beginning with a strong verb such as Implement, Explain, or Compare.

CI Validation and Build Integration

The frontmatter is not merely decorative. The scripts/audit_lessons.py script parses every docs/en.md file to enforce the lesson contract; failures block the CI pipeline. Concurrently, site/build.js consumes valid frontmatter to generate site/data.js, which powers the learning-path explorer and populates the generated README tables.

New lessons should copy the skeleton from LESSON_TEMPLATE.md, which embeds a compliant frontmatter example to ensure immediate compatibility with the build tooling.

Frontmatter Examples by Lesson Type

Build Lesson with Python Only

The following example from a linear regression lesson demonstrates the Build type for a single-language implementation:


# Linear Regression from Scratch

> Build a simple linear regression model without using a library.

**Type:** Build
**Languages:** Python
**Prerequisites:** 01-math-basics, 02-gradient-descent
**Time:** ~45 minutes

## Learning Objectives

- Derive the closed‑form solution for linear regression.
- Implement the algorithm from first principles.
- Visualise the fitted line on a dataset.
- Evaluate model performance using mean‑squared error.

Learn Lesson with Multiple Languages

For conceptual lessons that provide code examples in several languages, list every supported language in the Languages field:


# Tokenizer Fundamentals

> Understand how tokenizers split text into tokens.

**Type:** Learn
**Languages:** Python, TypeScript, Rust, Julia
**Prerequisites:** None
**Time:** ~30 minutes

## Learning Objectives

- Define what a token is and why it matters for language models.
- Compare whitespace, subword, and character tokenizers.
- Show how to encode and decode text with each language's standard library.
- Discuss trade‑offs in vocabulary size and model efficiency.

Summary

  • Location: Every lesson’s metadata lives in docs/en.md inside the lesson folder.
  • Required Fields: Title, Hook, Type, Languages, Prerequisites, Time, and Learning Objectives.
  • Validation: scripts/audit_lessons.py enforces compliance; missing fields trigger CI failures.
  • Build Tooling: site/build.js reads valid frontmatter to generate site/data.js and README tables.
  • Languages Constraint: The Languages entry must mirror the main.* files present in the lesson’s code/ directory.
  • Template: Use LESSON_TEMPLATE.md as the authoritative starting point for new lessons.

Frequently Asked Questions

What happens if a required frontmatter field is missing?

The CI pipeline fails because scripts/audit_lessons.py validates the lesson contract defined in AGENTS.md. The script parsing the YAML block expects all seven fields to be present and correctly formatted; omissions cause immediate build errors.

How should I format the Languages field when a lesson supports multiple programming languages?

Provide a comma-separated list that exactly matches the extensions of main.* files located in the lesson’s code/ directory (e.g., Python, TypeScript, Rust). The validation script cross-references this list against actual source files to ensure consistency.

Can I use "None" for prerequisites if my lesson has no dependencies?

Yes. Explicitly set Prerequisites: to the string "None" rather than leaving the field blank or omitting it. This signals to the learning-path explorer that the lesson is entry-level and has no upstream dependencies.

Where is the frontmatter schema formally defined?

The schema is formally documented in the "Lesson contract" section of AGENTS.md (lines 70–84) and implemented in the validation logic of scripts/audit_lessons.py. Additionally, LESSON_TEMPLATE.md provides a working template that satisfies all schema requirements.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →