wicked-crew-api-types 0.77.0 → 0.86.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/index.d.ts +439 -4
  2. package/package.json +1 -1
package/index.d.ts CHANGED
@@ -364,6 +364,17 @@ export interface AgentSession {
364
364
  * work. ABSENT on every other run (and on a daemon before the field).
365
365
  */
366
366
  outcome?: 'text_only';
367
+ /**
368
+ * (crew#762; api-types 0.79.0) Was delivery ASKED FOR on this run? A durable fact, so a skin can
369
+ * tell a run kept locally as asked from one whose delivery was attempted and did not land, also
370
+ * after a reload or a daemon restart. `stranded` with no deliver unit covers both.
371
+ * - `true`: the launch resolved `deliver: 'pr'`, OR a post-hoc `POST /runs/:id/deliver` was
372
+ * attempted (recorded before the script runs, whatever came of it), OR a delivery is on record.
373
+ * - `false`: the launch resolved `deliver: 'none'` and nothing was attempted since.
374
+ * - ABSENT: this daemon holds no launch record for the run and no attempt (a pre-field run, or a
375
+ * daemon before the field). Never fabricated.
376
+ */
377
+ deliver_requested?: boolean;
367
378
  /**
368
379
  * The delivered PR's URL (crew#393; api-types 0.18.0) — present exactly when
369
380
  * `delivery === 'delivered'`; absent otherwise (absence is the one spelling, never `null`).
@@ -1164,6 +1175,12 @@ export interface CoreEvent {
1164
1175
  elicitationId?: string;
1165
1176
  /** `elicitationCreated`: an ordered set of valid responses; `null` / absent = free-text. */
1166
1177
  options?: string[] | null;
1178
+ /**
1179
+ * `elicitationCreated` (C3; wicked-core-ts >= 0.7.35, api-types 0.83.0): the index into `options`
1180
+ * of the option the PRODUCER of the options recommends (the field's JSON Schema `default`).
1181
+ * ABSENT ⇒ nothing is preselected.
1182
+ */
1183
+ recommended?: number;
1167
1184
  /** PTY terminal frames (`terminalOpened`/`terminalOutput`/`terminalExited`): the terminal id. */
1168
1185
  id?: string;
1169
1186
  /**
@@ -4501,6 +4518,13 @@ export interface ElicitationInfo {
4501
4518
  message: string;
4502
4519
  /** Ordered set of valid responses; `null` means free-text. */
4503
4520
  options: string[] | null;
4521
+ /**
4522
+ * (C3, api-types 0.83.0) The index into `options` the producer of the options recommends —
4523
+ * relayed from the engine's `elicitationCreated.recommended`, kept only when it names one of
4524
+ * `options`. ABSENT ⇒ nothing is preselected (and a skin's Enter stays inert until a choice has
4525
+ * focus, DESIGN-interaction rule 6).
4526
+ */
4527
+ recommended?: number;
4504
4528
  receivedAt: string;
4505
4529
  }
4506
4530
 
@@ -5209,7 +5233,8 @@ export type ChatSeatRefusedFrame = {
5209
5233
  // verdicts; the seat's TEXT is never edited — a skin MARKS it from these items.
5210
5234
 
5211
5235
  /** What class of thing a citation is. */
5212
- export type ChatCitationKind = 'path' | 'line' | 'symbol' | 'sha';
5236
+ /** `rule` (api-types 0.85.0, DC-S7): a `[rule:<id>]` the reply wrote — "cited by the step — unchecked", never a followed count. */
5237
+ export type ChatCitationKind = 'path' | 'line' | 'symbol' | 'sha' | 'rule';
5213
5238
 
5214
5239
  /**
5215
5240
  * The verdict on one citation.
@@ -5315,7 +5340,21 @@ export type ChatTranscriptRecord =
5315
5340
  corrected: number;
5316
5341
  unchecked: number;
5317
5342
  items: ChatCitationItem[];
5318
- };
5343
+ }
5344
+ /**
5345
+ * The decisions recorded from the operator's message of `turnId` (api-types 0.84.0, DC-S4b) — a
5346
+ * SEPARATE record, like `citations`, because derivation runs after the seats' replies are stored. A
5347
+ * reader folds it onto the turn's `user` record; a skin that does not know this kind ignores it.
5348
+ * The live frame is {@link ChatDecisionsFrame}. The seats' `wicked-decisions` blocks themselves
5349
+ * never reach the transcript (they are cut from the reply before it is persisted or broadcast).
5350
+ */
5351
+ | { at: number; turnId: string; kind: 'decisions'; items: DecisionView[] }
5352
+ /**
5353
+ * A crew-authored preface the seats received with the operator's message of `turnId` (api-types
5354
+ * 0.85.0, DC-S7): the rules remembered since they last heard from crew. Disclosed here so the
5355
+ * operator sees exactly what crew added; the `user` record keeps the operator's own words.
5356
+ */
5357
+ | { at: number; turnId: string; kind: 'system'; text: string };
5319
5358
 
5320
5359
  /** `GET /chats/:id` → 200. */
5321
5360
  export interface ChatDetailResponse {
@@ -5935,6 +5974,8 @@ export interface DiagnosticsResponse {
5935
5974
  * `DiagnosticsStateHome`. `null` on a daemon booted without the watch (some tests); ABSENT on a
5936
5975
  * daemon before this field. */
5937
5976
  stateHome?: DiagnosticsStateHome | null;
5977
+ /** The studio chat recorder's per-CLI format compliance (api-types 0.84.0, DC-S4b); `null` without the chat host. */
5978
+ decisions?: DiagnosticsDecisions | null;
5938
5979
  }
5939
5980
 
5940
5981
  // ── Diagnostics — governance store + dead letters (api-types 0.31.0, crew#495 / F-022) ─────────
@@ -6079,7 +6120,12 @@ export interface DiagnosticsSkillsFinding {
6079
6120
  * an `error` under `'require'` (the engine refuses every launch at intake); cleared by a publish
6080
6121
  * that hands it. Also carried as `DiagnosticsSkills.baseSkill.finding`; `skills.phase-skill`
6081
6122
  * (`warning`, crew#661) = a subsystem's phases declare a skill the published snapshot did not hold
6082
- * when it armed, so they run without it — one per `DiagnosticsSkills.phaseSkillGaps` entry. */
6123
+ * when it armed, so they run without it — one per `DiagnosticsSkills.phaseSkillGaps` entry;
6124
+ * `skills.garden` (`error`, api-types 0.78.0, crew#753) = the installed wicked-garden is older
6125
+ * than the daemon requires (`GardenRequiredBody.required`), so it is not used: found at seed,
6126
+ * the runtime is `config-error` and the engine is handed a refusal path. Rides
6127
+ * `/health.warnings` too; launches and onboarding answer 422
6128
+ * `garden_required` until a newer garden is installed and published. */
6083
6129
  kind:
6084
6130
  | 'skills.fallback'
6085
6131
  | 'skills.blocked'
@@ -6088,11 +6134,25 @@ export interface DiagnosticsSkillsFinding {
6088
6134
  | 'skills.manifest'
6089
6135
  | 'skills.stale-rules'
6090
6136
  | 'skills.base-skill'
6091
- | 'skills.phase-skill';
6137
+ | 'skills.phase-skill'
6138
+ | 'skills.garden';
6092
6139
  severity: 'warning' | 'error';
6093
6140
  message: string;
6094
6141
  }
6095
6142
 
6143
+ /**
6144
+ * The 422 `POST /runs`, `POST /repos` and `POST /repos/:id/onboard` answer while the installed
6145
+ * wicked-garden is older than the daemon requires (api-types 0.78.0, crew#753). `error` names the
6146
+ * version found, where, the version required and the install command. Nothing was launched or
6147
+ * registered. A daemon with NO garden answers the base skill's 422 `base_skill_refused` instead.
6148
+ */
6149
+ export interface GardenRequiredBody {
6150
+ code: 'garden_required';
6151
+ error: string;
6152
+ /** The minimum wicked-garden version, e.g. `"12.40.0"`. */
6153
+ required: string;
6154
+ }
6155
+
6096
6156
  /**
6097
6157
  * `GET /diagnostics` → `skills`: whether the engine is being handed a verified snapshot, and if not,
6098
6158
  * why — the one read-only answer to "why do launches refuse the skills snapshot". `disabled` is a
@@ -6710,6 +6770,50 @@ export interface RunAcceptanceWalkthrough {
6710
6770
  steps: WalkthroughStepState[];
6711
6771
  }
6712
6772
 
6773
+ /**
6774
+ * `GET /runs/:id/acceptance` → `summary` (WT-W3, DES-walkthrough-proof §4.8/§7; api-types 0.82.0): the
6775
+ * deliver card's ONE acceptance line, computed at the same read as the gate. `line` is plain words
6776
+ * ("Checked by a walkthrough: 3 of 3 steps at a1b2c3d."); it cites counts and the tree, never a path.
6777
+ */
6778
+ export interface RunAcceptanceSummary {
6779
+ /** The run had something to prove (`gate.required`). */
6780
+ required: boolean;
6781
+ /** Deny-dominates across the repo ledger and every walkthrough (`gate.satisfied`). */
6782
+ satisfied: boolean;
6783
+ line: string;
6784
+ /** From the newest walkthrough; `null` when the requirement names none. */
6785
+ walkthrough: {
6786
+ checked: number;
6787
+ failed: number;
6788
+ ownedByYou: number;
6789
+ /** Creator steps with a check state. */
6790
+ steps: number;
6791
+ /** Every walkthrough seal held. */
6792
+ sealed: boolean;
6793
+ /** The tree the newest seal binds; `null` with no seal. */
6794
+ tree: string | null;
6795
+ } | null;
6796
+ }
6797
+
6798
+ /**
6799
+ * `PUT /runs/:id/walkthrough/storyline?step=` body (WT-W3, §4.8 "Edit the check"): the whole storyline
6800
+ * module text. Accepted only while that walkthrough's escalation gate is open (409
6801
+ * `no_open_escalation` otherwise), only from a human actor (403), at most 256 KB (413).
6802
+ */
6803
+ export interface PutStorylineBody {
6804
+ storyline: string;
6805
+ }
6806
+
6807
+ /** `PUT /runs/:id/walkthrough/storyline` → 200: crew wrote `author/<planStepId>/storyline.mjs`, marked `edited_by: human`. */
6808
+ export interface PutStorylineResponse {
6809
+ runId: string;
6810
+ planStepId: string;
6811
+ sha256: string;
6812
+ edited_by: 'human';
6813
+ /** ISO-8601. */
6814
+ at: string;
6815
+ }
6816
+
6713
6817
  /** `POST /proposals/:id/reject` → 200. */
6714
6818
  export interface RejectProposalResponse {
6715
6819
  ok: true;
@@ -7487,6 +7591,12 @@ export interface WatchEntry {
7487
7591
  version: number;
7488
7592
  /** See {@link WatchEntrySource}. A `bus` type is a 4-segment `wicked.<domain>.<noun>.<verb>` type. */
7489
7593
  on: { source: WatchEntrySource; type: string };
7594
+ /**
7595
+ * (api-types 0.81.0, TR-W5b) The key points the check JOINS to its trigger — "the same unit's
7596
+ * `repoChecksEvaluated`", "the cursor unit's latest `unitOutputCaptured`". They reach the check
7597
+ * unfiltered so it can fold them; only `on` (with `filter`) triggers a row. Absent = none.
7598
+ */
7599
+ join?: Array<{ source: Exclude<WatchEntrySource, 'internal'>; type: string }>;
7490
7600
  /** JSON-path equality, AND of keys; an array means "any of". */
7491
7601
  filter: Record<string, unknown>;
7492
7602
  check: string;
@@ -8511,3 +8621,328 @@ export interface McpUsageResponse {
8511
8621
  /** Lines of `calls.ndjson` that did not parse as a call record. */
8512
8622
  skipped: number;
8513
8623
  }
8624
+
8625
+ // ── Decision capture (DES-decision-capture §4.2.1 / §4.6; DC-S4a, api-types 0.80.0) ──────────────
8626
+
8627
+ /** The laya codebook's decision types. `none` is crew's label for "no decision". */
8628
+ export type DecisionType = 'rule' | 'correction' | 'scope' | 'exception' | 'choice' | 'confirmation' | 'none';
8629
+
8630
+ /** Where the operator's words entered crew. S4a records the three structured hosts. */
8631
+ export type DecisionHost = 'studio-chat' | 'gate' | 'elicitation' | 'inject' | 'capture' | 'claude-code';
8632
+
8633
+ /** The deterministic templates (`derive.ts`). Only `T1-always` and `T2-never` can auto-remember. */
8634
+ export type DecisionTemplateId =
8635
+ | 'T1-always'
8636
+ | 'T2-never'
8637
+ | 'T3-before'
8638
+ | 'T4-prefer'
8639
+ | 'T5-must'
8640
+ | 'T6-only'
8641
+ | 'in-your-words';
8642
+
8643
+ /** How the derivation routed a decision (§4.4): the first that applies wins. */
8644
+ export type DecisionRoute = 'ledger' | 'offer' | 'auto' | 'restated' | 'maybe-restated' | 'conflict';
8645
+
8646
+ /** The latest outcome of a decision. `recorded` = no outcome yet (ledger-only, or still landing). */
8647
+ export type DecisionState =
8648
+ | 'recorded'
8649
+ | 'offered'
8650
+ | 'remembered'
8651
+ | 'undone'
8652
+ | 'dismissed'
8653
+ | 'restated'
8654
+ | 'widened'
8655
+ | 'landing_failed';
8656
+
8657
+ /** Why an offered decision was dismissed (a label for the laya v3 flywheel). */
8658
+ export type DecisionDismissReason = 'not-a-rule' | 'one-off' | 'wrong-type' | 'wrong-scope' | 'not-the-same' | 'undone';
8659
+
8660
+ /**
8661
+ * One decision as studio renders it (`GET /decisions`, operator+). ORIGIN (`origin.words`) comes
8662
+ * ONLY from crew's ledger: a proposal payload carries just the decision id, so a forged payload
8663
+ * has no ORIGIN. Words are never on the bus.
8664
+ */
8665
+ export interface DecisionView {
8666
+ id: string;
8667
+ /** Epoch ms the words were recorded. */
8668
+ at: number;
8669
+ project_id: string | null;
8670
+ host: DecisionHost;
8671
+ origin: {
8672
+ actor: { id: string; kind: 'human'; trust: TrustLevel };
8673
+ auth_mode: 'off' | 'required';
8674
+ run_id?: string;
8675
+ ord?: number;
8676
+ gate_id?: string;
8677
+ elicitation_id?: string;
8678
+ chat_id?: string;
8679
+ turn_id?: string;
8680
+ /** The verbatim words (masked where a secret was found; then `redacted: true`). */
8681
+ words: string;
8682
+ /** A bare gate approve/reject or a picked elicitation option, when there were no words. */
8683
+ choice?: string;
8684
+ words_source: 'typed' | 'operator-files' | 'cli-transcript';
8685
+ redacted: boolean;
8686
+ };
8687
+ /** The derived rule: the statement crew would remember, never the model's paraphrase. */
8688
+ derived: {
8689
+ statement: string | null;
8690
+ polarity: 'do' | 'dont' | null;
8691
+ key: string | null;
8692
+ scope: 'project' | 'everywhere';
8693
+ steering_type: SteeringType;
8694
+ template: DecisionTemplateId | null;
8695
+ exclusions: string[];
8696
+ };
8697
+ route: DecisionRoute;
8698
+ state: DecisionState;
8699
+ /** How it was remembered (present once `remembered`). */
8700
+ how?: 'auto' | 'chip' | 'needs-you';
8701
+ proposal_id?: string;
8702
+ rule_id?: string;
8703
+ /** The in-force rule this restates (`restated`) or contradicts (`conflict`). */
8704
+ restates_rule_id?: string;
8705
+ conflicts_rule_id?: string;
8706
+ /** Edits the operator made at Remember; ORIGIN keeps the original words. */
8707
+ edits?: { statement?: string; scope?: 'project' | 'everywhere'; steering_type?: SteeringType };
8708
+ /** The loud reason a landing failed (`landing_failed`). */
8709
+ error?: string;
8710
+ /** B8: the same rule decided in ≥ 2 projects — "Make it apply everywhere". */
8711
+ widen?: { projects: string[] };
8712
+ }
8713
+
8714
+ /** `GET /decisions?project=&chat=&run=&state=&since=` (operator+). Newest first. */
8715
+ export interface ListDecisionsResponse {
8716
+ decisions: DecisionView[];
8717
+ /** `off` | `ledger` | `on` — the `WICKED_DECISIONS` switch this daemon runs under. */
8718
+ mode: 'off' | 'ledger' | 'on';
8719
+ }
8720
+
8721
+ /** `POST /decisions/:id/remember` body. An edited `statement` is recorded in `edits`. */
8722
+ export interface RememberDecisionBody {
8723
+ scope?: 'project' | 'everywhere';
8724
+ steering_type?: SteeringType;
8725
+ statement?: string;
8726
+ }
8727
+
8728
+ /** `POST /decisions/:id/remember` → the landed rule. */
8729
+ export interface RememberDecisionResponse {
8730
+ rule_id: string;
8731
+ proposal_id: string;
8732
+ project?: string;
8733
+ }
8734
+
8735
+ /** `POST /decisions/:id/dismiss` body. */
8736
+ export interface DismissDecisionBody {
8737
+ reason: DecisionDismissReason;
8738
+ }
8739
+
8740
+ /** `POST /decisions/:id/same` body — resolves a `maybe-restated` decision. */
8741
+ export interface SameDecisionBody {
8742
+ same: boolean;
8743
+ }
8744
+
8745
+ /** `/ws` frame: a decision's state changed (no words). */
8746
+ export interface DecisionChangedFrame {
8747
+ type: 'decisionChanged';
8748
+ id: string;
8749
+ state: DecisionState;
8750
+ rule_id?: string;
8751
+ project_id: string | null;
8752
+ }
8753
+
8754
+ /**
8755
+ * `/ws` frame (api-types 0.84.0, DC-S4b): the decisions recorded from ONE chat turn's operator
8756
+ * message, once every seat of the turn has answered (or the turn went stale). Mirrors
8757
+ * {@link ChatCitationsFrame}; the same items land in the transcript as a `decisions` record.
8758
+ */
8759
+ export interface ChatDecisionsFrame {
8760
+ type: 'chatDecisions';
8761
+ chat: string;
8762
+ turn_id: string;
8763
+ items: DecisionView[];
8764
+ project_id?: string;
8765
+ }
8766
+
8767
+ /**
8768
+ * `GET /diagnostics.decisions` (api-types 0.84.0, DC-S4b): the studio chat recorder's format
8769
+ * compliance per seat CLI — how often a seat ended its reply with a well-formed `wicked-decisions`
8770
+ * block (§4.3.3 measures the rate per CLI). `null` on a daemon without the chat host.
8771
+ */
8772
+ export interface DiagnosticsDecisions {
8773
+ /** The `WICKED_DECISIONS` switch this daemon runs under. */
8774
+ mode: 'off' | 'ledger' | 'on';
8775
+ /** Per `cliKey`: replies seen, well-formed blocks, malformed blocks. */
8776
+ recorder: Record<string, { replies: number; blocks: number; malformed: number }>;
8777
+ /** Turns whose recorder seat posted no usable block. The words were still recorded, unlabelled. */
8778
+ unclassified_turns: number;
8779
+ /** Turns that produced at least one decision record. */
8780
+ recorded_turns: number;
8781
+ }
8782
+
8783
+ // ── Considered · set aside · cited (unchecked) (DES-decision-capture §4.7; DC-S7, api-types 0.85.0) ──
8784
+
8785
+ export interface ConsiderationRule {
8786
+ id: string;
8787
+ statement: string;
8788
+ severity: 'info' | 'warn' | 'error' | 'critical';
8789
+ steering_type?: SteeringType;
8790
+ /** Present on a project-scoped rule. */
8791
+ project?: string;
8792
+ }
8793
+
8794
+ export interface ConsiderationSetAside {
8795
+ id: string;
8796
+ statement: string;
8797
+ /** The engine's reasons, plus crew's `not_confirmed`: a decision offered for this project, not yet remembered. */
8798
+ reason: 'out_of_scope' | 'replaced' | 'retired' | 'not_confirmed';
8799
+ }
8800
+
8801
+ /**
8802
+ * A `[rule:<id>]` the reply or step wrote. `unchecked` = the id is in force and the step cited it —
8803
+ * whether it FOLLOWED it is not checked (DES-rule-check will say); `unverified` = not an in-force
8804
+ * rule here (invented, or another project's). Never summed into a "followed" count.
8805
+ */
8806
+ export interface ConsiderationCitation {
8807
+ id: string;
8808
+ /** The seat (`cliKey`) or the unit id that wrote it. */
8809
+ by: string;
8810
+ status: 'unchecked' | 'unverified';
8811
+ label: string;
8812
+ }
8813
+
8814
+ /**
8815
+ * `GET /chats/:id/turns/:turnId/considered` and `GET /runs/:id/units/:unitKey/considered?attempt=`
8816
+ * (operator+): what the seats were given to consider, what was set aside, and what they cited.
8817
+ */
8818
+ export interface Consideration {
8819
+ subject: { kind: 'chat'; chat_id: string; turn_id: string } | { kind: 'unit'; run_id: string; ord: number; attempt: number };
8820
+ /** `considered:<chat>:<turn>` or `considered:<run>:<ord>:<attempt>` — the bus fact's idempotency key. */
8821
+ key: string;
8822
+ project_id: string | null;
8823
+ /** Severity-ordered (critical → info). */
8824
+ considered: ConsiderationRule[];
8825
+ set_aside: ConsiderationSetAside[];
8826
+ cited: ConsiderationCitation[];
8827
+ /** `considerRules` (the engine's project-aware read), `global-only` (an engine without it), or `unavailable`. */
8828
+ source: 'considerRules' | 'global-only' | 'unavailable';
8829
+ }
8830
+
8831
+ // ── Artifact editors (DES-artifact-editor-plugins §5.2, §6, §8.2; EP-C1, api-types 0.86.0) ───────
8832
+
8833
+ /** What a plugin can ask for (§6.1). There is no permission for network calls, agents or gates. */
8834
+ export type EditorPermission =
8835
+ | 'artifact.read'
8836
+ | 'artifact.write'
8837
+ | 'selection.chip'
8838
+ | 'composer.draft'
8839
+ | 'checks.read'
8840
+ | 'checks.contribute'
8841
+ | 'sources.read'
8842
+ | 'media.read'
8843
+ | 'artifact.export'
8844
+ | 'ui.fullscreen'
8845
+ | 'network.media';
8846
+
8847
+ /**
8848
+ * One registered editor, as Settings → Editors renders it. No path is on the wire: the bundle is
8849
+ * fetched at `entry_url` (`GET /editors/:id/:version/entry`, the §8.2 headers, re-hashed per serve).
8850
+ * First-party editors ship inside studio's bundle (`<studio dist>/editors/<id>/editor.json` +
8851
+ * `index.html`, ids `wicked-*`) and are discovered at boot; third-party editors arrive as garden
8852
+ * packs and cannot be installed before the install-time conformance run (EP-C8).
8853
+ */
8854
+ export interface EditorView {
8855
+ id: string;
8856
+ title: string;
8857
+ version: string;
8858
+ /** wicked.editor protocol versions it speaks. */
8859
+ protocol: number[];
8860
+ /** Artifact kinds it can open. */
8861
+ kinds: string[];
8862
+ sizes: Array<'inline' | 'pane' | 'full'>;
8863
+ panels?: Array<'checks'>;
8864
+ /** Each with the reason shown at install. The GRANTED set is `GET /editors/:id/grants`. */
8865
+ permissions: Array<{ id: EditorPermission; why: string }>;
8866
+ /** The full sha256 of the entry file, pinned when the registry read it. */
8867
+ sha256: string;
8868
+ bytes: number;
8869
+ first_party: boolean;
8870
+ enabled: boolean;
8871
+ source: 'studio-bundle';
8872
+ entry_url: string;
8873
+ }
8874
+
8875
+ /** `GET /editors` (operator+). */
8876
+ export interface ListEditorsResponse {
8877
+ editors: EditorView[];
8878
+ /** Why `POST /editors` answers 501 today: third-party installs wait on EP-C8. */
8879
+ installs: 'refused_until_conformance';
8880
+ }
8881
+
8882
+ /** `POST /editors` body (human-only): a pack directory holding `wicked-pack.json`. */
8883
+ export interface InstallEditorBody {
8884
+ packRoot: string;
8885
+ }
8886
+
8887
+ /** One finding of garden's `pack check --json`. */
8888
+ export interface PackCheckFinding {
8889
+ level: 'error' | 'warn';
8890
+ code: string;
8891
+ message: string;
8892
+ path?: string;
8893
+ }
8894
+
8895
+ /** The verdict of garden's `pack check --json` (the fail-closed gate every install runs first). */
8896
+ export interface PackCheckResult {
8897
+ ok: boolean;
8898
+ errors: PackCheckFinding[];
8899
+ warnings: PackCheckFinding[];
8900
+ }
8901
+
8902
+ /**
8903
+ * `POST /editors` → 501: the pack passed garden's gate, and this is what the install WOULD ask the
8904
+ * operator to approve (§3.2 "Add these") once third-party installs open (EP-C8). Nothing was written.
8905
+ */
8906
+ export interface InstallEditorRefusal {
8907
+ code: 'third_party_editors_not_available';
8908
+ error: string;
8909
+ check: PackCheckResult;
8910
+ pack: {
8911
+ name: string;
8912
+ vendor: string;
8913
+ version: string;
8914
+ editors: Array<{ id: string; title: string; version: string; kinds: string[]; permissions: Array<{ id: string; why: string }> }>;
8915
+ blocks: Array<{ id: string; label: string; produces_kind: string; skills: string[] }>;
8916
+ /** The pack's skill directories, approved together with its editors and blocks. */
8917
+ skills: string[];
8918
+ };
8919
+ }
8920
+
8921
+ /** `POST /editors/:id/enabled` body (human-only). */
8922
+ export interface SetEditorEnabledBody {
8923
+ enabled: boolean;
8924
+ }
8925
+
8926
+ /** One decided permission (the engine's `evaluate_editor_grants`, EP-K1). */
8927
+ export interface EditorGrant {
8928
+ permission: EditorPermission | string;
8929
+ decision: 'allow' | 'ask' | 'deny';
8930
+ /** The steering rules that decided it. */
8931
+ ruleIds: string[];
8932
+ /** The ledger entry an operator's "allow" adds to `EDITOR-GRANTS.excludes` (`editor:<id>@<version>#<sha256>/<permission>`). */
8933
+ token: string;
8934
+ }
8935
+
8936
+ /**
8937
+ * `GET /editors/:id/grants?project=` (operator+): the engine's decided set for this editor's version
8938
+ * and hash (a changed hash is a new token and asks again), deny dominating. The host fetches it
8939
+ * before `host.hello` and on every settings/rule change, and enforces it on every request.
8940
+ */
8941
+ export interface EditorGrantsResponse {
8942
+ editorId: string;
8943
+ version: string;
8944
+ sha256: string;
8945
+ project: string | null;
8946
+ firstParty: boolean;
8947
+ grants: EditorGrant[];
8948
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "wicked-crew-api-types",
3
- "version": "0.77.0",
3
+ "version": "0.86.0",
4
4
  "description": "The wire contract of the wicked-crew daemon's /api/v1 REST surface and /ws CoreEvent frames \u2014 types only, zero runtime",
5
5
  "type": "module",
6
6
  "types": "./index.d.ts",