6.4 KiB
llm-security-commons
Kontekst
Runtime-nøytral kjerne for LLM/agent-sikkerhetsdeteksjon: detektor-data, normative kontrakter og en conformance-korpus som flere uavhengige runtimes kan kjøre mot og få identisk verdikt fra. Repoet er delt kjerne, ikke et produkt.
Kjente konsumenter (vendorer dette repoet, endrer det ikke):
llm-security— Claude Code-plugin, Node/ESM-scannere.- et Python-guard-repo — samme deteksjon i en annen runtime.
- en wiki/advisory-flate — konsumerer samme lexicon og mapping.
Å dele én identisk kjerne er hele poenget: to implementasjoner som gir ulikt verdikt på samme input er per definisjon en bug i én av dem — ikke en meningsforskjell.
Charter (HARD — bryter du denne, er endringen feil uansett hvor god den er)
Ingen engine-kode. Ingenting her kjører.
- ❌ Ingen
.mjs,.js,.ts,.py,.shsom implementerer deteksjon, scanning, normalisering, scoring eller I/O. - ❌ Ingen
package.json,pyproject.toml, lockfiler, dependencies, build-steg. - ❌ Ingen import fra — eller kjennskap til — noe rammeverk, SDK eller runtime.
- ❌ Ingen nettverk, ingen modellkall, ingen tidsavhengighet, ingen tilfeldighet. Alt her er offline og deterministisk.
- ✅ Kun: JSON-data, normative spesifikasjoner (Markdown), og fixtures
(
input+expected).
Regelen finnes fordi kjernen skal være fork-and-own: en konsument på en runtime vi
ikke har tenkt på skal kunne vendore dette uten å arve et eneste teknologivalg.
Mønsteret er kopiert fra søsterrepoet portfolio-optimiser-commons (samme harde charter:
«nothing here may import/depend on a framework»).
Stack
Ingen. Data + prosa. Filformater: JSON (data + schema), Markdown (spec), rå tekst (conformance-input).
Konvensjoner
Data (JSON)
- Hver JSON-fil har et topnivå
"version"-felt (semver-streng). Uten unntak. - Hver JSON-fil har et topnivå
"$comment"eller"description"som sier hva filen er og hvor dataene kom fra (provenance). - 2 mellomrom indentering, LF, avsluttende newline. UTF-8 uten BOM.
- Kodepunkter skrives som
"U+200B"-strenger (lesbare i review), aldri som rå usynlige tegn i JSON-kilden — bortsett fra iconformance/*/input.txt, som per definisjon inneholder de faktiske tegnene. - Nøkler er stabile identifikatorer. Å endre en nøkkel er en breaking change — konsumenter matcher på dem.
Spec (Markdown)
- Hver normativ spec har en
**Status: normative**-markør øverst. - RFC 2119-språk (MUST / MUST NOT / SHOULD / MAY) i store bokstaver, brukt bevisst.
- Informative dokumenter (
docs/) har**Status: informative**og er aldri ground truth.
Conformance
- Én katalog per case:
conformance/<case-id>/input.txt+conformance/<case-id>/expected.json. <case-id>er stabil og beskrivende. Å endre en case-id er en breaking change.expected.jsoner ground truth. Er en runtime uenig medexpected.json, er runtimen feil — med mindre fixturen selv bevises feil, og da endres fixturen i eget commit med begrunnelse.
Sikkerhetskritiske tabeller — aldri fra hukommelse
codepoints/carriers.json (inkl. homoglyph-map), signatures/secret-egress.json,
signatures/malware-signatures.json og signatures/active-content.json er
deteksjonsdata. Et gjettet kodepunkt eller et regex med feil escaping er en stille
falsk negativ — en detektor som ser ut som den virker.
Disse filene endres KUN fra verifisert kildedata (dump fra konsument-repo,
Unicode-standarden, publisert leverandør-doc). Aldri fra egen hukommelse, aldri
«fylt ut for konsistens». Kan en oppføring ikke verifiseres: utelat den, eller marker
den eksplisitt uverifisert i $comment.
Behaviour preservation (v0.1.0-invariant)
v0.1.0 er en ekstraksjon, ikke en revisjon. Data som er hentet ut av en konsument
skal gi eksakt samme funn når konsumenten senere leser dem herfra. Ser du noe du
mener er feil i seed-dataene: ikke fiks det her. Dokumentér avviket, send det til
konsumenten via coord-send, og la beslutningen tas der dataene er testet.
Kommandoer
Repoet har ingen build og ingen test-runner (charter). Validering er ad hoc:
# Alle JSON-filer er velformet
find . -name '*.json' -not -path './.git/*' -print0 | xargs -0 -n1 python3 -m json.tool > /dev/null
# Hver JSON-fil har topnivå "version"
for f in $(find . -name '*.json' -not -path './.git/*' -not -path './conformance/*'); do
python3 -c "import json,sys; d=json.load(open('$f')); sys.exit(0 if 'version' in d else 1)" \
|| echo "MANGLER version: $f"
done
# Hver spec har normativ-markør
grep -L 'Status: normative' spec/*.md
# Charter-guard: ingen kjørbar kode har sneket seg inn
find . -type f \( -name '*.mjs' -o -name '*.js' -o -name '*.ts' -o -name '*.py' -o -name '*.sh' \) \
-not -path './.git/*' | grep . && echo 'CHARTER-BRUDD: kjørbar kode i commons'
Arbeidsflyt
- Versjonering: semver på repo-nivå (tag
vX.Y.Z). Hver JSON-fils"version"er filens egen semver og bumpes når den filen endres — de er ikke låst til repo-taggen. Nytt datafelt eller ny oppføring = minor. Endret/fjernet nøkkel, case-id eller disposisjon = major (konsumenter bryter). - Versjonssync før commit: endrer du en JSON-fil, bump dens
"version"; endrer du repoets kontrakt, bump repo-taggen + CHANGELOG. - Konsumenter varsles via
coord-send, ikke via antakelse. Et repo som vendorer denne kjernen får ikke vite at kontrakten endret seg med mindre du sier det. - Aldri jobb i konsument-repoene fra en økt her. Vendoring, oppgradering og behaviour-verifisering skjer i konsumentens egen økt, med konsumentens tester.
- Forgejo only (
git.fromaitochitta.com). Aldri GitHub, aldrighCLI. STATE.mder LOCAL-ONLY (gitignored) — remote er en offentlig flate.
Communication patterns
Linking to local files
When pointing to local files in responses, always use markdown link syntax with a descriptive name:
- Use
[Human-friendly name](file:///absolute/path)— never barefile:///...URLs or autolinks<file://...>. - Always use absolute paths. Never
~/or relative paths. - For multiple files, render as a bullet list of named markdown links.
Why: bare file:// URLs only render the first as clickable across multiple lines. Named markdown links make each entry independently clickable and look cleaner.
Example: