Skip to main content

constitution-overlay

DOI License: MIT Python 3.11+

Kustomize-style merge of YAML rule layers + halt-on-reject enforced executor-side.

A small, framework-agnostic Python library (~300 lines) that gives agentic systems two things:

  1. A layered constitutionconstitution.yaml defines invariants; corrections.yaml overrides specific values for the current run. Rightmost-wins merge, same semantics as Kustomize.
  2. Executor-side enforcement@halt_on_reject wraps any function. When the check inside raises PolicyReject, the decorator propagates it unconditionally. The LLM cannot instruct the Python runtime to swallow a raise.

Why this matters: LLMs ignore system prompt instructions under task pressure. An executor-side decorator cannot be bypassed. See DESIGN.md for the full rationale.


Install

pip install git+https://github.com/arnoldwender/constitution-overlay@v0.1.1

Requires Python 3.11+. Only dependency: pyyaml.

Not on PyPI yet. pip install constitution-overlay will be the install line once the first release is published; until then this README states what actually works, because a package that promises an install command it cannot honour is the exact failure this library exists to prevent.


Quick start

from constitution_overlay import Constitution, PolicyReject, halt_on_reject

# 1. Build a merged constitution from two layers
constitution = Constitution.from_layers(
    {
        "brand": {"prohibited_terms": ["cheap", "cheapest"]},
        "limits": {"max_files_per_commit": 50},
    },
    {
        "limits": {"max_files_per_commit": 200},  # override for this run
    },
)

# 2. Enforce rules executor-side
@halt_on_reject(constitution)
def commit_files(files: list[str]) -> None:
    limit = constitution.get("limits.max_files_per_commit")
    if len(files) > limit:
        raise PolicyReject(f"too many files: {len(files)} > {limit}")

commit_files(["a.py", "b.py"])  # OK
commit_files(["x.py"] * 300)    # raises PolicyReject — cannot be bypassed

See examples/basic_usage.py for a complete runnable example.


Load from YAML

# constitution.yaml
brand:
  prohibited_terms:
    - cheap
    - cheapest
limits:
  max_files_per_commit: 50
  no_force_push: true
# corrections.yaml
limits:
  max_files_per_commit: 200   # override for this large-batch run
from constitution_overlay import Constitution

c = Constitution.from_layers(
    Constitution.from_yaml("constitution.yaml").rules,
    Constitution.from_yaml("corrections.yaml").rules,
)
print(c.get("limits.max_files_per_commit"))  # 200
print(c.get("limits.no_force_push"))          # True — inherited from base

API

# Load
Constitution.from_dict(d: dict) -> Constitution
Constitution.from_yaml(path: str | Path) -> Constitution
Constitution.from_layers(*layers: dict) -> Constitution   # rightmost-wins merge

# Query
c.rules                    # post-merge dict
c.get(key, default=None)   # dot-notation: "brand.prohibited_terms"
c.has(key) -> bool

# Enforce
@halt_on_reject(c)
def agent_action(...): ...   # PolicyReject raised inside propagates unconditionally

# Exceptions
class PolicyReject(Exception): ...

ConstitutionContext is also exported for use inside wrapped functions — a read-only view over c.rules with the same get/has interface.


Merge semantics

  • Dicts merge recursively — a later layer overrides specific keys without clobbering siblings.
  • Scalars and lists are replaced by the rightmost value (list-append directive is on the v0.2 roadmap).
  • None is a valid explicit value and survives the merge.
  • Type mismatches raise TypeError immediately rather than silently coercing.

Project layout

src/constitution_overlay/
    __init__.py       # public exports
    constitution.py   # Constitution class + YAML loading
    corrections.py    # deep_merge + merge_layers
    executor.py       # halt_on_reject, PolicyReject, ConstitutionContext
tests/
    test_constitution.py
    test_executor.py
    test_merge.py
    test_smoke.py
examples/
    basic_usage.py

Development

python -m venv .venv && source .venv/bin/activate
pip install -e ".[dev]"

.venv/bin/pytest tests/ -q          # 69 tests
.venv/bin/mypy --strict src/        # must be clean
.venv/bin/ruff check src/ tests/    # must be clean

See CONTRIBUTING.md for the full contribution guide.


License

MIT — see LICENSE.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

constitution_overlay-0.1.1.tar.gz (19.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

constitution_overlay-0.1.1-py3-none-any.whl (8.6 kB view details)

Uploaded Python 3

File details

Details for the file constitution_overlay-0.1.1.tar.gz.

File metadata

  • Download URL: constitution_overlay-0.1.1.tar.gz
  • Upload date:
  • Size: 19.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for constitution_overlay-0.1.1.tar.gz
Algorithm Hash digest
SHA256 c852f6502f02202d056adc6962cd3464bc355a25a2279543531ac7b941856195
MD5 78e1279a86fab602f9f250238e34a597
BLAKE2b-256 2b0698ba30c7990c65b2bf8b5973a24856e9f1ee4dbbf57bd57cf40c73932695

See more details on using hashes here.

Provenance

The following attestation bundles were made for constitution_overlay-0.1.1.tar.gz:

Publisher: release.yml on arnoldwender/constitution-overlay

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file constitution_overlay-0.1.1-py3-none-any.whl.

File metadata

File hashes

Hashes for constitution_overlay-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 cbf55697e100304d3084f5cbe2eb34014226e6b126202c2347d7723a623a31ad
MD5 fb81aa01535644eb1231ebafe64b1edc
BLAKE2b-256 97229ff37d179f7b4ffc4078c3a7bcaedf83a40a7645f120d43c9fa44f349e41

See more details on using hashes here.

Provenance

The following attestation bundles were made for constitution_overlay-0.1.1-py3-none-any.whl:

Publisher: release.yml on arnoldwender/constitution-overlay

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

0.1.2

2 files

This release

0.1.1 This release

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page