export type StageId = 'structure' | 'live' | 'forecast' | 'closed-loop'; /** 판정에 쓰는 사실. `null` = **계측되지 않았다**(0 이 아니다). */ export interface StageEvidence { /** 이 트윈이 든 자리 수. */ locationCount: number; /** 자리에 놓인 물품 수(비직렬 수량 물품 포함 — 식품·화학은 개수가 아니라 총량으로 온다). */ itemCount: number; /** * 마스터를 옮기며 **못 옮긴 값의 수**. `null` = 세지 않았다. * * 0 이면 통과이고 n 이어도 통과다 — 이 판정이 요구하는 것은 「없다」가 아니라 **「말할 수 있다」**다. * 못 옮긴 값을 세지 않은 구조 인제스트는 도크를 랙으로 바꿔 놓고도 성공이라 답하면서 아무 일도 하지 않는다. */ masterWarnings: number | null; /** * 이 축이 이 트윈에 **해당하나**. 레퍼런스 없이 템플릿으로 세운 트윈에는 옮겨 온 마스터가 없으므로 * 「못 옮긴 값」을 물을 대상이 아니다 — 그걸 미측정으로 처리하면 영원히 배선을 기다린다. */ masterWarningsApplicable?: boolean; /** 인제스트 누적 건수. */ liveIngestTotal: number; /** **반출(remove)을 계산한 누적 건수.** `null` = 계측되지 않음. 0 = 세었으나 없었다(→ 스냅샷 의심). */ removalsObserved: number | null; /** 이 트윈에서 예측이 한 번이라도 돌았나. */ forecastRan: boolean; /** 선언 적재량 — `declared`/`total`. `null` = 알 수 없음. */ specCoverage: { declared: number; total: number; } | null; /** * 이 트윈이 **무엇인가** — 시뮬레이션은 원천에서 받는 것이 없다. * * 시뮬에 라이브를 요구하면 영원히 빨갛고, 그 빨강은 결함이 아니다. 도입 단계는 **연결된 트윈**의 * 축이므로 시뮬은 라이브 이후를 「해당 없음」으로 말한다(달성으로도, 미측정으로도 계산하지 않는다). */ subject?: 'live' | 'sim'; /** 피드 성격 — `snapshot-poll` 이면 반출 0 은 「아직」이 아니라 **구조적으로 불가**다. */ feed?: 'push' | 'delta-poll' | 'snapshot-poll' | 'none' | 'unknown'; /** 원본이 **선언∩구현**으로 액추에이션 능력을 갖나(`capabilitiesOf`). */ actuateCapability: boolean; /** 내 명령의 효과가 인바운드로 **상관되어** 돌아온 누적 건수. `null` = 계측되지 않음. */ correlatedEffectObserved: number | null; } export interface StageVerdict { id: StageId; achieved: boolean; /** 아직 아닌 이유 — 언어중립 코드(화면이 옮긴다). 달성이면 빈 배열. */ blockedBy: string[]; /** 판정할 수 없었던 신호 — **배선되지 않은 계측**. 있으면 달성이 아니다. */ unmeasured: string[]; } export interface StagePath { stages: StageVerdict[]; /** 지금 서 있는 칸 — 연속으로 달성된 마지막 단계. 하나도 없으면 `null`. */ reached: StageId | null; /** * 다음 한 걸음 — 사람이 오늘 할 수 있는 일 하나. 없으면(전부 달성) `null`. * 「무엇이 부족한지」의 목록이 아니라 **다음 하나**다. 목록은 사람을 멈추게 한다. */ next: { stage: StageId; blockedBy: string[]; unmeasured: string[]; } | null; } /** * 증거로 단계를 판정한다. * * **단계는 앞선 단계를 전제한다**(구조 없이 라이브를 달성했다고 말할 수 없다). 앞이 막히면 뒤는 * 자기 조건을 따지지 않고 `prerequisite` 으로 막는다 — 뒤 단계의 조건을 나열하면 사람이 순서를 * 건너뛴다. */ export declare function assessStagePath(e: StageEvidence): StagePath; /** * 이 단계에 이르지 못했다면 **쓰지 않기로 한 말**. * * 근거 수준 규율(`connector-developer-guide` §8)을 판정과 같은 자리에 둔다. 문장이 문서에만 있으면 * 제안서를 쓰는 사람이 그 문서를 읽지 않는다. 값이 되면 화면이 그 자리에서 말할 수 있다. */ export declare const CLAIM_GATE: Record; /** 아직 쓸 수 없는 주장들 — 도달하지 못한 단계의 게이트 전부. */ export declare function forbiddenClaims(path: StagePath): string[];