# Blueprint reference

What this page covers

The `blueprint.yaml` curricular contract, `items/<id>/metadata.yaml` per-item
declaration, and the exact rules each file is validated against.

| File | Owner | Purpose |
| --- | --- | --- |
| `blueprint.yaml` | Global Skills | Domain, competencies, weights. |
| `items/<id>/metadata.yaml` | Item author | Item characterization. References a competency id. |

## File shapes

**blueprint.yaml**

**blueprint.yaml**

```
product_code: SC109
domain:
  id: containers-with-docker
  title: "Containers with Docker"
competencies:
  - id: build-images
    title: "Build images from Dockerfiles"
    weight: 15
  - id: configure-runtime
    title: "Configure container runtime settings"
    weight: 10
  # ...
# Σ weight = 100
```

| Field | Type | Constraint |
| --- | --- | --- |
| `product_code` | string | `^[A-Z][A-Z0-9]{2,9}$`. Immutable. Matches the dashboard product code; SkillCred repos are named `<product_code>-Exam`. |
| `domain.id` | string | Kebab-case (`^[a-z][a-z0-9-]*[a-z0-9]$`). Immutable once released. |
| `domain.title` | string | Non-empty. Rendered as the exam title. Mutable. |
| `competencies[].id` | string | Kebab-case. Unique within the file. Immutable once released. |
| `competencies[].title` | string | Non-empty. Mutable. |
| `competencies[].weight` | number | `> 0`. Σ across competencies = 100 (within 0.001). |

**metadata.yaml**

**items/<id>/metadata.yaml**

```
---
settings:
  nickname: [petname]
competency: build-images
difficulty: easy
title: "Build a greeting container image"
total_check_count: 2
revision: 1
```

| Field | Type | Constraint |
| --- | --- | --- |
| `competency` | string | Must equal a `blueprint.competencies[].id`. |
| `difficulty` | enum | One of `easy`, `medium`, `hard`. See [Difficulty tiers](https://skills.staging.lf-cert.cloud/docs/skillcred/author-workflow/#understand-the-skillcred-assignment) for what each tier means in practice. |
| `title` | string | Non-empty. |
| `total_check_count` | integer ≥ 1 | Must equal the aggregate count of `scoring::check` invocations across every `score.sh` for VMs declared in `sandbox.yaml`. |
| `revision` | integer ≥ 1 | Bump on material changes. |
| `settings.<key>` | array of strings | Optional. First list value is used at runtime. Outside the sandbox, set `SANDBOX_SETTING_<KEY_UPPER>` to override the metadata value when invoking the `sandbox` CLI. Inside the VM, the resolved value is injected as a plain shell variable `<KEY_UPPER>` (no `SANDBOX_SETTING_` prefix). No value may be the literal string `TODO`. |

Immutability

`product_code`, `domain.id`, and each `competencies[].id` are immutable once released.
Renaming a released id is a breaking change to every item that references it.

## How the files connect

| In | Field | Resolves against |
| --- | --- | --- |
| `items/<id>/metadata.yaml` | `competency` | A `competencies[].id` in `blueprint.yaml`. |
| `items/<id>/metadata.yaml` | `total_check_count` | The sum of `scoring::check` calls across every `host*/scripts/score.sh`. |

Every selected item resolves its `competency` against a blueprint id. Coverage rules then require every blueprint competency to be measured by at least one item.

## Rules enforced by `skills validate item`

The per-item commit-time hook checks these rules against each touched item:

| Rule | Effect |
| --- | --- |
| `metadata.competency-required` | `competency` must be present and non-empty. |
| `metadata.competency-resolves` | `competency` must resolve to a `blueprint.yaml` competency id. |
| `metadata.difficulty-enum` | `difficulty ∈ {easy, medium, hard}`. |
| `metadata.title-non-empty` | `title` must be a non-empty string. |
| `metadata.total-check-count-positive` | `total_check_count > 0`. |
| `metadata.total-check-count-matches-score-sh` | Must equal Σ `scoring::check` across all VM score scripts. |
| `metadata.revision-positive` | `revision > 0`. |
| `metadata.no-forbidden-keys` | Forbidden legacy keys must be absent. |
| TODO-placeholder rules | No `settings.<key>` value may be the literal string `TODO`. |

Coverage and weight-derivation rules run at `git push` and in CI, not on every commit.

## Related pages

- **[Author Workflow](https://skills.staging.lf-cert.cloud/docs/skillcred/author-workflow/index.md)**

Step-by-step contribution flow for an assigned SkillCred item.

- **[Quickstart](https://skills.staging.lf-cert.cloud/docs/quickstart/index.md)**

Practice the sandbox CLI and the item lifecycle end-to-end.
