Files
settled-reach/pyproject.toml
T
jpmschweitzerandClaude Opus 5 8d64800fe9 feat(config): T-1259 — reach is a real command, and Typer vendors Click
`reach --help` runs from the console entrypoint in 80 ms. typer 0.27.1 and
pydantic 2.13.4 join the dependencies, both CVE-checked against NVD, OSV and
the GitHub Advisory Database.

The design in the ticket did not survive contact. It specified a click.Group
root, on the reasoning that it would keep typer off the --help path — but
typer vendors Click as of 0.26.0, so there is no top-level click package to
import and no supported way to extract typer's internal one. A click.Group
root hosting Typer sub-apps would put two Click implementations in one
process. The root is therefore a typer.Typer, and lazy registration will go
through the supported typer.Typer(cls=...) surface with a TyperGroup
subclass. T-1260 is corrected to match.

The callback is not decoration: a Typer root with no commands AND no callback
raises at build time, and lazy registration means no command is ever eager.
The ticket claimed a zero-command root always raises — half right, and the
half that matters is that a callback makes it legal.

rich_markup_mode=None is load-bearing rather than cosmetic. It takes an empty
--help from 168 ms to 74 ms, and keeps rich and pygments off the import path
entirely rather than merely skipping the render. It also stops typer drawing
box-art help, which it does even when stdout is a pipe — that would have put
box-drawing characters into every hook log and agent capture. typer-slim was
considered and rejected: deprecated since 0.22.0, now a shallow wrapper that
installs all of typer.

D-263 amended: the feels-instant ceiling goes from 250 ms to 500 ms. A ceiling
is not a typical and most invocations sit far below it; the tighter number was
buying discipline that the import-graph assertion enforces better. Stay smart
about what loads, stop worrying about tightness.

Security, checked 2026-08-23. typer has no advisories on record. pydantic
2.13.4 clears PYSEC-2026-1812 (email-regex ReDoS, fixed in 2.4.0) — and the
2026 SSRF advisories CVE-2026-25580 and CVE-2026-54249 are against
pydantic-ai, a different package that is not a dependency here, recorded in
pyproject so the next sweep does not re-panic. Transitively, pygments 2.21.0
clears CVE-2026-4539.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 14:01:32 +02:00

82 lines
3.9 KiB
TOML
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
[project]
name = "settled-reach-tooling"
version = "0.1.0"
requires-python = ">=3.11"
dependencies = [
"PyYAML",
"jsonschema",
"numpy",
# scipy 1.17.1 — checked clean against NVD + OSV, no CVEs on record (2026-04-06)
"scipy==1.17.1",
# Pillow 12.2.0 — checked clean against NVD + OSV (2026-04-06)
# CVE-2026-25990 fixed in 12.1.1, CVE-2025-48379 fixed in 11.3.0
"Pillow==12.2.0",
# typer 0.27.1 — the CLI transport (D-263). Checked clean against NVD, OSV
# and the GitHub Advisory Database: no advisories on record for typer at all
# (2026-08-20). Its transitive set was checked too, since typer pulls in
# rich -> pygments: pygments 2.21.0 clears CVE-2026-4539 (archetype-lexer
# ReDoS, fixed in 2.20.0); rich and click have no advisories on record.
#
# Plain `typer`, not `typer-slim`: slim is deprecated as of typer 0.22.0 and
# is now a shallow wrapper that installs all of typer, so it buys nothing.
# rich therefore ships as a transitive dependency — but `rich_markup_mode=None`
# in tooling/main.py keeps it off the import path entirely (verified: `rich`
# and `pygments` are absent from sys.modules after loading the CLI).
"typer==0.27.1",
# pydantic 2.13.4 — data shapes for domain schemas (D-263). Checked clean
# against NVD + OSV (2026-08-20). PYSEC-2026-1812 / CVE-2024-3772 (email
# regex ReDoS) is fixed in 2.4.0. NOTE the 2026 SSRF advisories
# CVE-2026-25580 and CVE-2026-54249 are against *pydantic-ai*, a different
# package that is not a dependency here — do not confuse the two on the
# next sweep.
"pydantic==2.13.4",
]
[project.scripts]
# The whole point of D-263: one bare command, so one permission-rule entry
# covers every tool.
#
# `cli` is a typer.Typer instance (callable), NOT the click.Group that T-1259
# originally specified: typer vendors click as of 0.26.0, so there is no
# top-level `click` to import and no supported way to extract typer's internal
# one. Lazy domain registration therefore goes through `typer.Typer(cls=...)`
# with a TyperGroup subclass (T-1260) rather than a click Group.
reach = "tooling.main:cli"
[tool.setuptools.packages.find]
# Explicit, not flat-layout auto-discovery. The repo root holds client/, server/,
# docs/, wiki/, db/ and tests/ alongside tooling/, and auto-discovery either
# errors on the ambiguity or quietly ships something unintended (T-1258).
#
# Nothing needs excluding yet: the hyphenated directories (planet-gen,
# economy-db, garment-fit, pql-migrate) are invisible to package discovery
# because a hyphen is not a valid Python identifier, and tooling/econ-sim is a
# Rust crate with no __init__.py. That changes in T-1250, which renames them —
# at which point they become real packages and this include starts matching them.
include = ["tooling*"]
[project.optional-dependencies]
dev = [
# ruff 0.15.9 — checked clean against NVD + OSV, no CVEs on record (2026-04-05)
"ruff==0.15.9",
]
[tool.ruff]
line-length = 100
target-version = "py311"
[tool.ruff.lint]
# Widened from {E9, F401, F811, F821} to the full ruff-default tiers + W (T-1066).
# E4: import placement/style
# E7: statement-level pitfalls (== None, bare except, lambda assignment, ...)
# E9: runtime syntax/encoding errors
# F: all pyflakes (unused imports/names, undefined names, f-string misuse, ...)
# W: whitespace + invalid escape sequences (zero violations at adoption)
select = ["E4", "E7", "E9", "F", "W"]
# Rules excluded at adoption because the existing violation count was not
# trivially fixable (T-1066) — re-enable per-rule as the debt is paid down:
# E402 (43×): module-import-not-at-top — script-style sys.path.insert before import
# E702 (41×): semicolon-paired assignments, deliberate style in planet-gen noise math
# F841 (21×): unused locals, mostly in numeric/diagnostic code — needs manual review
ignore = ["E402", "E702", "F841"]