Rapporten paasto at de tre stoerste postene "deler aarsak: alle tre baerer navigatoerens read_file". Det var aldri maalt. Ved aa maale det kom TO ting fram. 1. Aarsaken stemmer, og er naa dekomponert: verktoeyRESULTATENE utgjoer 87-93 % av hver av de tre stoerste promptene (6 527 tok), og enkeltvis er det read_file 4 043 (62 %), read_bundle 2 354 (36 %), list_bundles 130 (2 %). read_file er 4 043 baade i prompten og maalt isolert, saa det som rir med er hele returverdien - ikke en forkortet form. 2. MITT EGET INSTRUMENT VAR FEIL. Sonden summerte Message.text OG hvert Content.text, men Message.text ER sammenkjedingen av tekst-innholdet - altsaa ble tekstdelen talt to ganger. Totalen 45 643 er forkastet; riktig tall er 40 320 over 13 prompter (manager 61 %, navigator 23 %, hypotesiser 16 %), og de tre stoerste er 7 532 / 7 468 / 7 037 = 55 %, ikke 8 572 / 8 444 / 7 582. Feilen var IKKE synlig i totalen. Den ble synlig foerst da sammensetningen ble brutt ned - som er hele grunnen til at en total ingen har dekomponert er en total ingen har kontrollert. Begge instrumentfeilene staar naa i SS 0. Ogsaa: SS 1c skilte ikke maalt faktum fra min tolkning av hva 1 500-tegns-taket "er". Faktumet staar (K2s read_bundle er 6 244 tegn mot en gate skrevet for 3-dokuments baser); lesningen av hva taket er ment aa binde tilhoerer den som eier gaten. Ingen produksjonskode. Doc-gatene gronne (25 passed). Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
388 lines
20 KiB
Markdown
388 lines
20 KiB
Markdown
# Syretest S7a — K2 → kunnskapsbase → utforskning → revise
|
||
|
||
**Dato:** 2026-09-03 · **Ordre:** `20260902T233842Z-2955810469-from-.claude` ·
|
||
**Grunnlag:** `~/.claude/docs/helhetlig-plan-okf-og-portfolio-optimiser.md` § 0, § 5, § 9.1
|
||
|
||
Dette er en **måling**. Ingen produksjonskode er endret; hele måleoppsettet ligger utenfor treet
|
||
(`scratchpad/s7a/`, utracket) og hver tabell under er produsert av en kommando som står i teksten.
|
||
**Ingen validert besparelse er forventet eller funnet** — K2 er pre-award og prisskjemaet er
|
||
uutfylt (plan § 9.1). Det som måles er navigasjonen, dialogen, revise-sløyfa, falsifiseringen mot
|
||
proveniens og tokenprofilen.
|
||
|
||
---
|
||
|
||
## 0. Instrumentet, validert mot en kjent positiv FØR bruk
|
||
|
||
Alle tokentall er `tiktoken` `o200k_base` over den fulle prompt-blobben (tekst + `function_call` +
|
||
`function_result`), kjørt med `uv run --with tiktoken` — `tiktoken` er fortsatt ikke en
|
||
prosjektavhengighet.
|
||
|
||
| Kjent-positiv sjekk | Publisert fasit | Målt nå |
|
||
|---|---|---|
|
||
| `read_bundle` over `tunnel-hauglia` | 259 tok (`docs/2026-09-02-read-bundle-kontekstkostnad.md`) | **259 tok** |
|
||
| `bundle_context` over `tunnel-hauglia` | 12 595 tok (samme) | **12 595 tok** |
|
||
|
||
Instrumentet reproduserer begge eksakt. Først etter det er K2-tallene under lest som tall.
|
||
|
||
**To instrumentfeil ble fanget underveis, og begge er skrevet ned fordi de er samme klasse som
|
||
misjonsreview v2 rapporterte.** (i) Første prompt-sonde leste `repr(Content)` og fikk
|
||
`<agent_framework._types.Content object at 0x…>` for **hver** melding — en prompt som så tom ut
|
||
mens den bar 108 000 tegn. Sonden henter nå `text`/`result`/`arguments` ut av hvert `Content`.
|
||
(ii) Den rettede sonden summerte så `Message.text` **og** hvert `Content.text`, altså tekstdelen
|
||
to ganger. Den feilen ble ikke synlig i totalen — den ble synlig først da § 5s sammensetning ble
|
||
målt, og det er hele grunnen til at sammensetningen ble målt i det hele tatt: en total ingen har
|
||
brutt ned er en total ingen har kontrollert.
|
||
|
||
---
|
||
|
||
## 1. Kunnskapsbasen slik den faktisk er levert
|
||
|
||
Bygget av `llm-ingestion-okf` 02.09 (`tools/okf_corpus_run.py`, steg 17) til `/tmp/k2-trinn1-bundle`;
|
||
kopiert til `scratchpad/s7a/k2-bundle` og målt der (`/tmp` er flyktig).
|
||
|
||
| Egenskap | Målt |
|
||
|---|---|
|
||
| Konseptfiler (`context_files`) | **39** |
|
||
| Filer totalt (`files`) | 40 (39 + `index.md`) |
|
||
| `type: verdict`-lag | 0 |
|
||
| Ufulgte kryss-lenker (`skipped`) | **0** |
|
||
| `bundle_id` / opphav | `k2-bundle` / **`mount-derived`** |
|
||
| `index.md`-body | 6 044 tegn, ingen frontmatter, ren lenkeliste |
|
||
| `log.md` (OKF § 7) | **finnes ikke** |
|
||
|
||
**Ordrens `N=43, merged 39` er delvis verifiserbart.** `merged = 39` er målt direkte (39
|
||
konseptfiler). `N = 43` er produsentens tall og kan **ikke** verifiseres fra bundelen: den bærer
|
||
ingen `log.md` og ingen manifest-oppføring som teller inn-dokumentene. Det står som produsentens
|
||
påstand, ikke som en måling gjort her.
|
||
|
||
### `adjudication`-nøkkelen: fraværende, med nevner
|
||
|
||
```
|
||
cd scratchpad/s7a/k2-bundle && grep -l '^adjudication:' *.md | wc -l # 0
|
||
grep -l '^type:' *.md | wc -l # 39 (kjent-positiv kontroll)
|
||
```
|
||
|
||
Frontmatter-folketellingen over alle 39, med sifre i nøkkelnavnet tatt med:
|
||
|
||
| Nøkkel | Antall (av 39) |
|
||
|---|---|
|
||
| `type`, `title`, `source_file`, `source_sha256`, `ingested_at`, `generated`, `derived` | 39 |
|
||
| `references` | 20 |
|
||
| **`adjudication`** | **0** |
|
||
| **`verified`** | **0** |
|
||
| **`sources`** | **0** |
|
||
|
||
**Ordrens premiss om «den nye profilen (`adjudication`)» holder ikke mot det som ble levert.**
|
||
Bundelen bærer ingen `adjudication`-nøkkel og ingen provenienss-nøkkel i det hele tatt. Det er et
|
||
faktum om bundelen, ikke om leseren — se § 4, der gaten bevises å kunne si ja.
|
||
|
||
### Navigasjonskostnad, per kall
|
||
|
||
| Kall | Tegn | o200k-tokens |
|
||
|---|---|---|
|
||
| `list_bundles` (1 base) | 352 | **127** |
|
||
| `read_bundle("k2-bundle")` | 6 244 | **2 312** (39 oppføringer) |
|
||
| `read_file` × 39, sum | — | **684 236** |
|
||
| `read_file`, median / min / maks | — | 6 709 / 541 / **121 462** |
|
||
| `bundle_context` (formen før MAJOR-3) | — | **682 303** |
|
||
|
||
Tre ting følger av tabellen.
|
||
|
||
**(a) MAJOR-3 er det som gjør K2 navigerbar i det hele tatt.** Den gamle `read_bundle`-kroppen
|
||
returnerte `bundle_context` — 682 303 tokens for denne basen, altså mer enn noe kontekstvindu
|
||
tar, og den ville ridd med i hver senere prompt. Den nye formen koster 2 312. Reduksjonen er
|
||
**99,7 %**, og forskjellen her er ikke «billigere», den er «mulig mot umulig».
|
||
|
||
**(b) Katalogtaket holder på et 39-dokuments korpus.** `list_bundles` koster 127 tokens, og
|
||
`index_truncated` kommer tilbake `true` — de 6 044 tegnene i indeksen blir til et 200-tegns
|
||
utdrag. Det bekrefter det `docs/2026-08-26-katalogkostnaden.md` forutså for maskin-importerte
|
||
baser: utdraget er nesten innholdsløst (første lenkelinje), men det er *bundet*, og hele indeksen
|
||
er ett `read_file(id, "index.md")` unna.
|
||
|
||
**(c) `read_bundle` er O(dokumenter), og på 39 dokumenter er det 2 312 tokens.** Det målte
|
||
faktumet: `tests/test_read_bundle_cost_loadbearing.py` setter taket til 1 500 **tegn** mot
|
||
3-dokuments baser, og K2s `read_bundle` er 6 244 tegn. Det er ikke et brudd — gaten måler sine
|
||
egne baser — men tallet er verdt å legge fram for den som eier gaten. Hva taket *er ment* å
|
||
binde, er deres avgjørelse, ikke min lesning her.
|
||
|
||
**(d) To dokumenter sprenger § 5s tokenkriterium hvis de leses hele.** Kriteriet er «ingen
|
||
enkeltpost > 100 000 tok uten en navngitt grunn». To av 39 passerer det som `read_file`:
|
||
|
||
| Dokument | Tokens |
|
||
|---|---|
|
||
| `inbox-del-ii-bilag-3-1-milj-teknisk-rapport-med-tiltaksplan.md` | 121 462 |
|
||
| `inbox-del-ii-bilag-9-1-avtale-som-tiltransporteres-norconsult-as.md` | 119 909 |
|
||
|
||
Grunnen er navngitt her: begge er enkeltdokumenter fra korpuset som ikke er delt opp i konsepter.
|
||
De ble **ikke** lest i kjøringene under — men en navigatør som velger dem, betaler det.
|
||
|
||
---
|
||
|
||
## 2. Dialogen: én offline utforskning med verktøyspor
|
||
|
||
```bash
|
||
PYTHONIOENCODING=utf-8 uv run python -m portfolio_optimiser.run K2-STANGE \
|
||
--docs-dir scratchpad/s7a/k2-bundle --bundle-dir scratchpad/s7a/k2-bundle \
|
||
--explore "Finn kostnadsbesparelser i Stange skole-anbudet" \
|
||
--explore-config scratchpad/s7a/explore-config.json \
|
||
--scripted-replies scratchpad/s7a/scripted-replies.json \
|
||
--outbox-dir scratchpad/s7a/outbox --run-id s7a-offline
|
||
```
|
||
|
||
MAJOR-1s trinn-manus er brukt: navigatøren får `{"call": …}`-steg, manageren én tekst per stadium
|
||
(fakta, plan, tre ledgere, sluttsvar). Uten manager-manuset avslutter kjøringen etter én runde uten
|
||
å gi noen deltaker en tur — det er MAJOR-1s egen måling, og den er grunnen til at manageren er
|
||
skriptet i stadier.
|
||
|
||
`{run_id}-exploration.json`:
|
||
|
||
| Felt | Målt |
|
||
|---|---|
|
||
| `completed` | `true` |
|
||
| `stop` | `null` |
|
||
| `tool_calls` | **`list_bundles` → `read_bundle(k2-bundle)` → `read_file(k2-bundle)`**, i kallrekkefølge |
|
||
| `rounds` | 3, alle med `speaker_known: true` og en ekte deltaker som `next_speaker` |
|
||
| `approaches` (i mandatet) | 1 — `hypothesis-1 — SENTINEL-ALFA prisskjema-post 82` |
|
||
|
||
**Plan § 5s dialog-rad er oppfylt og målt:** ≥ 1 `read_bundle`/`read_file`-kall er logget i
|
||
artefaktet. Kjøringen er ikke-vakuøs i den forstand MAJOR-1 definerte: tre runder, kjent taler
|
||
hver gang, tre verktøykall, ett mandat.
|
||
|
||
### Kjøringen ender likevel rc = 1, og det er S7bs skarpeste funn
|
||
|
||
```
|
||
run refused: IR projection not found in bundle: 'validator-input.json'
|
||
```
|
||
|
||
Utforskningen fullførte, mandatet ble kunngjort — og så nektet pipelinen. Bundelen bærer ingen
|
||
`validator-input.json`, så `run_project`s bundle-arm kan ikke slå opp prosjektet. Artefaktet
|
||
overlevde fordi det skrives fra en `finally`, som er nøyaktig hva den konstruksjonen finnes for.
|
||
|
||
Dette er et **mer spesifikt** S7b-gap enn «K2 har ingen priser»: selv med priser ville kjøringen
|
||
stoppet her. Ingesterings-profilen emitterer ingen IR-projeksjon. **Kryss-repo-funn for
|
||
`llm-ingestion-okf`.**
|
||
|
||
### Levende kjøring: ikke kjørt
|
||
|
||
Ordrens escape-klausul fyrer. Målt, ikke antatt:
|
||
|
||
| Variabel / fil | Tilstand |
|
||
|---|---|
|
||
| `PORTFOLIO_FOUNDRY_PROJECT_ENDPOINT` | tom/usatt |
|
||
| `FOUNDRY_PROJECT_ENDPOINT` | tom/usatt |
|
||
| `PORTFOLIO_MODEL_MAP` | tom/usatt |
|
||
| `OPENAI_API_KEY` / `AZURE_OPENAI_API_KEY` | tom/usatt |
|
||
| `data/model_map.json` | finnes ikke |
|
||
|
||
`az account show` svarer riktignok med en konto, men Fase 4e målte at AZURE-armen slår opp et
|
||
deployment-navn i modell-mappet **før** noen klient bygges — uten mappet er en innlogget CLI
|
||
ikke nok. **Levende kjøring ikke gjort, mangler nøkkel og modell-map.** Ingen konflikt med
|
||
STATE-ens `IKKE RØR AZURE` oppsto.
|
||
|
||
---
|
||
|
||
## 3. Revise-sløyfa
|
||
|
||
```bash
|
||
printf 'revise SENTINEL-BRAVO: …\napprove\n' | uv run python -m portfolio_optimiser.run K2-STANGE \
|
||
… --explore-config scratchpad/s7a/explore-config-review.json --plan-review \
|
||
--outbox-dir scratchpad/s7a/outbox-review --run-id s7a-review
|
||
```
|
||
|
||
| Egenskap | Målt |
|
||
|---|---|
|
||
| Plan-reviewer stilt | **2** (`#1` besvart `revise`, `#2` besvart `approve`) |
|
||
| Manageren replanla mellom dem | ja — plan `#1` 1 115 tegn, plan `#2` 1 132 tegn, ulik tekst |
|
||
| Tilbakemelding i artefaktet | **ordrett**, `SENTINEL-BRAVO: …` |
|
||
| `"object at"` i artefakt eller stdout | **0 forekomster** (BLOCKER-1 bekreftet lukket på begge dørene) |
|
||
| `current_progress` | `"(no progress ledger yet)"` — ikke ordet `None` (PM-tillegg 4 bekreftet lukket) |
|
||
|
||
### Mandat-diffen er TOM, og grunnen er instrumentet — ikke systemet
|
||
|
||
Mandatet bygges av hypotesiserens `HYPOTHESIS:`-merkede turer. Under et **konstant** manus sier
|
||
hypotesiseren det samme uansett hva revisjonen sa, så før/etter er identiske ved konstruksjon. Å
|
||
rapportere den tomme diffen som et funn ville vært å lese et instrumentresultat som et faktum om
|
||
verden. Det som *kan* måles offline er **kjeden**: hvilke prompter bærer operatørens
|
||
tilbakemelding? Med to ASCII-sentineler (norske tegn serialiseres escaped i prompten og ville gitt
|
||
falske nuller — samme felle misjonsreview v2 rapporterte):
|
||
|
||
| Ledd | Bærer | Målt |
|
||
|---|---|---|
|
||
| 1. Operatørens revise-tekst → managerens prompt | `SENTINEL-BRAVO` | **6 av 8** manager-kall |
|
||
| 1b. Samme tekst → deltakernes prompt | `SENTINEL-BRAVO` | **0 av 4** navigatør, **0 av 1** hypotesiser |
|
||
| 2. Managerens post-revise-output → hypotesiserens prompt | `SENTINEL-CHARLIE` i `instruction_or_question` | **1 av 1** |
|
||
| 2b. Samme, via plan-TEKSTEN | revidert plan-streng | **0 av 1** hypotesiser, **0 av 4** navigatør |
|
||
| 3. Endret hypotese ut av deltakeren | — | **ikke målbar offline** |
|
||
|
||
**Mekanismen, uttalt:** operatørens tilbakemelding når **manageren**, aldri deltakerne direkte.
|
||
Den når deltakerne bare gjennom det manageren selv skriver i neste rundes
|
||
`instruction_or_question` — og det er bevist diskriminerende: sentinelen manageren skrev *etter*
|
||
revisjonen står i hypotesiserens prompt, mens plan-teksten (verken den opprinnelige eller den
|
||
reviderte) gjør det ikke.
|
||
|
||
Sløyfa er altså hel, men leddet som faktisk former hypotesen er managerens **omskriving** av
|
||
tilbakemeldingen. Under et skriptet manus er den omskrivingen min, ikke en modells. **At en revise
|
||
endrer hva hypotesiseren foreslår er derfor ikke bevist her, og kan ikke bevises offline** — det
|
||
krever en levende manager. Det er S7bs andre åpne krav.
|
||
|
||
---
|
||
|
||
## 4. Falsifisering mot proveniens (K5-terskelen)
|
||
|
||
Ordren ber om et K2-konsept med `adjudication: proposed`. **Det finnes ikke: 0 av 39.** Terskelen
|
||
er derfor kjørt på det korpuset faktisk bærer, mot en påstand om den ene prisede posten:
|
||
|
||
> «Post 82 *Prosjektering (tiltransport av prosjekterende)* i Bilag 7 Prisskjema er priset til
|
||
> 5 647 500 NOK og er derfor en kandidat for kostnadskutt.»
|
||
|
||
| | K2 slik den er levert | Kjent-positiv kontroll (patchet kopi) |
|
||
|---|---|---|
|
||
| `adjudication_for` | `unknown` | `adjudicated` |
|
||
| `(state, reason, items_seen)` | `(absent, None, 0)` | `(present, None, 1)` |
|
||
| `trust_tier` | `None` | `human-reviewed` |
|
||
| `admits_falsification` | **`False`** | **`True`** |
|
||
|
||
Over alle 39, med nevner: `adjudication` `unknown` 39/39 · `evidence.state` `absent` 39/39 ·
|
||
`tier` `None` 39/39 · `admits_falsification` `False` **39/39**.
|
||
|
||
**Kontrollen er bærende.** Uten den er «alle 39 diskontert» ikke til å skille fra «funksjonen
|
||
diskonterer alltid» — repoets vakuøs-gate-klasse. Kontrollen er en kopi under
|
||
`scratchpad/s7a/k2-control/` der ett konsept har fått
|
||
`verified: { by: human:…, at: … }` + `adjudication: adjudicated`; gaten flipper `False → True`.
|
||
Den leverte bundelen er aldri skrevet til.
|
||
|
||
**Dommen, slik skillen krever den:** `undecided`, aldri `survived`. Diskonteringen sies eksplisitt
|
||
med trippelen, ordrett fra `evidence_notice`:
|
||
|
||
```
|
||
provenance absent in …/inbox-del-ii-bilag-7-prisskjema.md; items_seen=0
|
||
```
|
||
|
||
Og med skillens egen regel: en gjendrivelse som ikke navngir en gjendriver er ingen gjendrivelse —
|
||
her finnes ingen kilde som klarerer terskelen, så «vi kan ikke bekrefte» må aldri skrives om til
|
||
«påstanden er gal».
|
||
|
||
---
|
||
|
||
## 5. Tokenprofil
|
||
|
||
Ekte `usage` finnes ikke: `ScriptedChatClient` rapporterer 8 tokens per svar, så artefaktets
|
||
`tokens_spent` (88 offline, 104 med review) er **syntetisk** og sier ingenting om kostnad. Profilen
|
||
under er derfor instrument-målt over de faktiske prompt-blobbene i revise-kjøringen.
|
||
|
||
> **Instrumentfeil funnet og rettet før dette tallet ble stående.** Første sonde summerte
|
||
> `Message.text` **og** deretter hvert `Content.text` — men `Message.text` *er* sammenkjedingen av
|
||
> meldingens tekst-innhold, så tekstdelen ble talt to ganger. Feilen kom for dagen først da
|
||
> sammensetningen under ble målt, ikke da totalen ble lest. Tallene i denne seksjonen er fra den
|
||
> rettede sonden (`m5_prompt_composition.py`); det forkastede tallet var 45 643.
|
||
|
||
**13 prompter, 40 320 o200k-tokens.**
|
||
|
||
| Rolle | Prompter | Tokens | Andel |
|
||
|---|---|---|---|
|
||
| manager | 8 | 24 465 | 61 % |
|
||
| navigator | 4 | 9 251 | 23 % |
|
||
| hypothesiser | 1 | 6 604 | 16 % |
|
||
|
||
De tre største postene — til sammen 22 037 tokens, **55 % av hele kjøringen**:
|
||
|
||
| # | Post | Tokens |
|
||
|---|---|---|
|
||
| 1 | manager-kall 6 (ledger etter at navigatøren hadde lest prisskjemaet) | 7 532 |
|
||
| 2 | manager-kall 5 (samme, runden før) | 7 468 |
|
||
| 3 | manager-kall 7 (sluttsvar) | 7 037 |
|
||
|
||
**Hva de består av — målt, ikke antatt.** Hver av de tre er brutt ned per innholdstype:
|
||
|
||
| Del | manager #6 | manager #5 | manager #7 |
|
||
|---|---|---|---|
|
||
| verktøy**resultater** | 6 527 (87 %) | 6 527 (87 %) | 6 527 (93 %) |
|
||
| tekst (fakta, plan, ledger-historikk) | 965 (13 %) | 901 (12 %) | 470 (7 %) |
|
||
| verktøy**argumenter** | 40 (0 %) | 40 (0 %) | 40 (0 %) |
|
||
|
||
Og de 6 527 tokenene enkeltvis, i den rekkefølgen navigatøren hentet dem:
|
||
|
||
| Verktøyresultat | Tokens i prompten | Andel av de 6 527 |
|
||
|---|---|---|
|
||
| `list_bundles` | 130 | 2 % |
|
||
| `read_bundle` | 2 354 | 36 % |
|
||
| **`read_file` (Bilag 7 Prisskjema)** | **4 043** | **62 %** |
|
||
|
||
`read_file`-resultatet er altså 4 043 tokens i prompten og 4 043 tokens målt isolert — samme tall,
|
||
så det som rir med er hele returverdien, ikke en forkortet form. (`read_bundle` er 2 354 i prompten
|
||
mot 2 312 isolert; differansen er JSON-innrammingen meldingen legger rundt.)
|
||
|
||
**Mekanismen er den samme som MAJOR-3 målte, ett trinn ned på stigen.** Utforskningens deltakere
|
||
deler **én** samtalehistorikk, så ett `read_file` betales av hver senere prompt i kjøringen. Her
|
||
utgjør de tre verktøyresultatene 87–93 % av hver av de tre største postene, og prisskjemaet alene
|
||
er 62 % av dem. Ingen enkeltpost passerer § 5s 100 000-tak i denne kjøringen; de to dokumentene som
|
||
*ville* gjort det (§ 1d) ble ikke åpnet.
|
||
|
||
---
|
||
|
||
## 6. Hva som mangler for S7b (validert besparelse)
|
||
|
||
Tre krav, alle målt her, i den rekkefølgen de blokkerer:
|
||
|
||
**1. Kunnskapsbasen mangler en IR-projeksjon.** `run_project`s bundle-arm nekter med
|
||
`IR projection not found in bundle: 'validator-input.json'` (§ 2). Uten den stopper kjøringen etter
|
||
utforskningen uansett hva prisskjemaet inneholder. Ingesterings-profilen emitterer den ikke.
|
||
**Kryss-repo-krav mot `llm-ingestion-okf`** — ingen brief i dette repoet kan lukke det.
|
||
|
||
**2. Prisskjemaet er uutfylt, og MAJOR-4 nekter — korrekt.** Kjørt mot det ekte K2-prisskjemaet:
|
||
|
||
```
|
||
CostBaselineDerivationError: no cost table found in bundle 'scratchpad/s7a/k2-bundle':
|
||
no concept file carries a markdown table whose header names all three of
|
||
['code', 'quantity', 'unit_cost']
|
||
```
|
||
|
||
Kontroll: samme funksjon mot `tests/fixtures/k2-prisskjema-SYNTETISK` gir **3 kostlinjer**, så
|
||
avlederen virker — nekten er en egenskap ved K2, ikke ved koden.
|
||
|
||
Formen er målt presist: K2s Bilag 7 er **ett** ark (`## Prissammenstilling`), en pandoc SIMPLE table
|
||
med kolonneparet `Post … SUM`. Ordet `Enhetspris` forekommer **0 ganger** i hele filen, og
|
||
`Mengde`/`Timepris` står bare i prosa — de tilhørende cellene er tomme, fordi totalentreprenøren
|
||
skal fylle dem. Den **eneste** prisede raden i hele skjemaet er
|
||
`82 Prosjektering (tiltransport av prosjekterende) = 5 647 500`.
|
||
|
||
S7b trenger altså den syntetisk utfylte kopien plan § 9.1 anbefaler. MAJOR-4 har allerede formen:
|
||
`okf.derive_cost_baseline` (eier B) og fixturparet
|
||
`tests/fixtures/k2-prisskjema-SYNTETISK` / `…-uprisert-SYNTETISK`, med
|
||
`--derive-cost-baseline` som CLI-døra.
|
||
|
||
**3. `adjudication` mangler i hele korpuset (0/39).** K5-terskelen diskonterer derfor hvert konsept
|
||
(§ 4). En validert besparelse kan formelt sett fortsatt produseres — terskelen gjelder
|
||
falsifiseringsdommen, ikke validatoren — men den kan ikke *hvile* på noe i basen. **Kryss-repo-krav
|
||
mot `llm-ingestion-okf`**, samme klasse som punkt 1.
|
||
|
||
Ett krav er **ikke** blokkerende og bør ikke telles med: at en revise endrer hypotesen (§ 3). Det
|
||
krever en levende manager, ikke en endring i noe av dette.
|
||
|
||
---
|
||
|
||
## 7. Verifiseringslogg
|
||
|
||
| # | Påstand | Kommando → resultat |
|
||
|---|---|---|
|
||
| 1 | Instrumentet reproduserer publisert fasit | `uv run --with tiktoken python scratchpad/s7a/m1_navigation.py` → tunnel `read_bundle` 259, `bundle_context` 12 595 |
|
||
| 2 | 39 konsepter, 0 `adjudication`, kjent-positiv 39 `type` | `grep -l '^adjudication:' *.md \| wc -l` → 0; `grep -l '^type:'` → 39 |
|
||
| 3 | `N=43` ikke verifiserbart | ingen `log.md` i bundelen (`Path(base)/'log.md').exists()` → `False`) |
|
||
| 4 | Navigasjonstall | samme skript → § 1-tabellen |
|
||
| 5 | Verktøysporet | `outbox/s7a-offline-exploration.json` → `tool_calls` = 3, i rekkefølge |
|
||
| 6 | Pipelinen nekter på manglende IR | stderr → `IR projection not found in bundle` |
|
||
| 7 | Levende ikke kjørbar | alle fem env-variabler tomme; `data/model_map.json` finnes ikke |
|
||
| 8 | Revise → replan → nytt spørsmål | `outbox-review/s7a-review-exploration.json` → 2 `plan_reviews`, ulik `plan` |
|
||
| 9 | Ingen `object at` | `grep -c 'object at'` over artefakter + stdout → 0 |
|
||
| 10 | Kjeden, tre ledd | `uv run --with tiktoken python scratchpad/s7a/m3_revise_chain.py` → § 3-tabellen |
|
||
| 11 | K5 diskriminerer | `uv run python scratchpad/s7a/m4b_falsification.py` → `False` vs `True` |
|
||
| 12 | MAJOR-4 nekter mot ekte K2, godtar syntetisk | `uv run python scratchpad/s7a/m6_derive.py` → feilmelding vs 3 kostlinjer |
|
||
| 13 | Tokenprofil + sammensetning | `uv run --with tiktoken python scratchpad/s7a/m5_prompt_composition.py` → § 5-tabellene |
|
||
|
||
**Ikke verifisert her:** at en levende modell kaller verktøyene eller velger godt (samme grense som
|
||
structured-output-raden); at `N=43` stemmer; at leverandørens caching treffer prefiksene; K2s
|
||
Prisskjema slik en utfylt versjon faktisk ville sett ut (fixturen er syntetisk).
|
||
|
||
**Premisser som ble felt av målingen, og som er rapportert i stedet for omgått:** ordrens
|
||
«ny profil med `adjudication`» (0/39), ordrens punkt 4 (ingen `proposed`-konsept finnes), og
|
||
antakelsen om at mandat-diffen ville vise revisjonens virkning (tom ved konstruksjon).
|