Coverage for src/rhiza_hooks/_config_schema.py: 100%

12 statements  

« prev     ^ index     » next       coverage.py v7.14.1, created at 2026-07-30 04:36 +0000

1#!/usr/bin/env python3 

2"""Canonical schema for ``.rhiza/template.yml`` — keys, aliases, normalization. 

3 

4This is the single source of truth for the shape of a rhiza template config. It 

5owns the canonical key sets (:data:`REQUIRED_KEYS`, :data:`OPTIONAL_KEYS`, 

6:data:`VALID_KEYS`), the :data:`KEY_ALIASES` map from accepted alias spellings to 

7their canonical names, and :func:`normalize_config`, which rewrites a raw mapping 

8so every alias becomes its canonical key. 

9 

10Both the config validator (:mod:`rhiza_hooks.check_rhiza_config`) and the 

11template-bundles reader (:mod:`rhiza_hooks._bundles_config`) import from here so 

12the alias handling never drifts between them. The module is a leaf: it imports 

13nothing from the rest of :mod:`rhiza_hooks`. 

14""" 

15 

16from __future__ import annotations 

17 

18from typing import Any 

19 

20REQUIRED_KEYS = {"template-repository", "template-branch"} 

21OPTIONAL_KEYS = {"include", "exclude", "templates"} 

22VALID_KEYS = REQUIRED_KEYS | OPTIONAL_KEYS 

23# Alternative (alias) key names mapped to their canonical spellings. 

24KEY_ALIASES = { 

25 "repository": "template-repository", 

26 "ref": "template-branch", 

27 "profiles": "templates", 

28} 

29 

30 

31def normalize_config(config: dict[str, Any]) -> dict[str, Any]: 

32 """Normalize configuration by replacing aliases with canonical keys. 

33 

34 Args: 

35 config: Raw configuration dictionary 

36 

37 Returns: 

38 Normalized configuration with aliases replaced 

39 """ 

40 normalized: dict[str, Any] = {} 

41 for key, value in config.items(): 

42 # Replace alias with canonical name if it exists 

43 canonical_key = KEY_ALIASES.get(key, key) 

44 normalized[canonical_key] = value 

45 return normalized