Documentation
¶
Overview ¶
Package property parses and represents SpecScore Property artifacts.
A Property is a single markdown file at `spec/features/**/<slug>.property.md` whose YAML frontmatter declares a reusable, named business field — its `data_type` and a `checks` mapping. See `spec/features/property/README.md` in the meta-spec for the full artifact contract and `spec/features/cli/property/README.md` in this repo for the CLI's implementation contract.
This package provides discovery and parsing utilities only. The lint rules that enforce the schema live in `pkg/lint`.
Index ¶
Constants ¶
This section is empty.
Variables ¶
var CheckKeyApplicability = map[string]map[string]bool{ "required": {"string": true, "integer": true, "number": true, "boolean": true, "date": true, "datetime": true, "object": true, "array": true, "ref": true}, "enum": {"string": true, "integer": true, "number": true, "boolean": true, "date": true, "datetime": true, "object": true, "array": true, "ref": true}, "min": {"integer": true, "number": true, "date": true, "datetime": true}, "max": {"integer": true, "number": true, "date": true, "datetime": true}, "min_length": {"string": true, "array": true}, "max_length": {"string": true, "array": true}, "pattern": {"string": true}, "trim": {"string": true}, "lowercase": {"string": true}, "uppercase": {"string": true}, "items": {"array": true}, "json_schema": {"object": true}, "entity_ref": {"ref": true}, }
CheckKeyApplicability is the (check-key → applicable data_types) matrix from [property#req:checks-shape]. The `property-checks-shape` lint rule uses this to validate (data_type, check) pairs; keys NOT present here are "unknown" and reported at severity `warning`.
var LegalDataTypes = map[string]bool{ "string": true, "integer": true, "number": true, "boolean": true, "date": true, "datetime": true, "object": true, "array": true, "ref": true, }
LegalDataTypes mirrors the upstream enumeration in [property#req:data-type-values]. The parser surfaces the raw `data_type` string from frontmatter; lint compares against this map.
Functions ¶
func ValidateSlug ¶
ValidateSlug returns nil if slug matches `[a-z0-9]+(-[a-z0-9]+)*`.
func Walk ¶
Walk combines Discover and Parse: it discovers every property file under `<specRoot>/features/` and invokes `fn` with the parsed Doc for each one, in slug-sorted order.
Walk returns the first non-nil error from `fn` and stops iterating. I/O or parse errors abort with a wrapped error; callers that want to continue past a single bad file MUST handle the error inside `fn` and return nil. A missing `<specRoot>/features/` directory is a no-op.
Types ¶
type Discovered ¶
Discovered is a summary of a Property file found during discovery.
func Discover ¶
func Discover(specRoot string) ([]Discovered, error)
Discover walks `<specRoot>/features/**/*.property.md` and returns every property file found, sorted alphabetically by slug.
Discovery scope mirrors [cli/property#req:discovery-scope]:
- Hidden directories (any path segment starting with `.`) MUST be skipped.
- Reserved underscore-prefixed directories (e.g., `_tests/`) MUST be skipped.
- A missing `<specRoot>/features/` directory yields ([], nil) — Discover is not responsible for surfacing project-shape errors.
`specRoot` is the absolute path to the project's `spec/` directory (the caller resolves this from `specscore.yaml`); the function appends `features/` internally to match the meta-spec's property-location glob.
type Doc ¶
type Doc struct {
Path string
Slug string // derived from filename; the contract id
RawLines []string
Title string // full title line content after `# `
TitleName string // the `<id>` portion after `Property: `
TitleLine int // 1-based
HasTitle bool
Frontmatter *Frontmatter
FmRaw *yaml.Node // raw mapping node — used by `id`-rewrite autofix
Sections []Section
SectionByTitle map[string]*Section
}
Doc is a parsed Property artifact. Parse is resilient — Doc is non-nil even for malformed files; Frontmatter and FmRaw may be nil when the frontmatter block is missing or not the first block in the file.
func Parse ¶
Parse reads a property file and returns its parsed representation.
Parse is resilient: a non-nil *Doc is returned for every readable file, even when the frontmatter is missing, not first, or malformed. Callers (lint rules) MUST inspect Doc.Frontmatter / Doc.HasTitle / etc. to decide what is a violation. The only path that returns (nil, err) is an I/O failure opening or reading the file.
`Path` and `Slug` are always populated. `RawLines` is preserved byte- for-byte so the managed-section rewriter can edit specific line ranges without losing surrounding content. `FmRaw` is preserved as a `yaml.Node` so the `id`-rewrite autofix can round-trip frontmatter without losing comments or key order.
type Frontmatter ¶
type Frontmatter struct {
Kind string // MUST equal "property" — lint checks
ID string // MUST equal Doc.Slug — lint checks
DataType string // one of LegalDataTypes — lint checks
Description string // OPTIONAL but RECOMMENDED
Checks map[string]any // the raw mapping; MAY be empty but key MUST exist
}
Frontmatter mirrors [property#req:frontmatter-required-fields]. The parser fills these fields from a decoded YAML map; lint MUST verify required-ness and value legality (the parser surfaces values raw).