@intutic/gate 2.1.0 → 2.3.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 (74) hide show
  1. package/README.md +29 -12
  2. package/dist/actions.d.ts.map +1 -1
  3. package/dist/actions.js +20 -6
  4. package/dist/actions.js.map +1 -1
  5. package/dist/client.d.ts +19 -1
  6. package/dist/client.d.ts.map +1 -1
  7. package/dist/client.js +48 -4
  8. package/dist/client.js.map +1 -1
  9. package/dist/dsh.d.ts +1 -1
  10. package/dist/dsh.js +1 -1
  11. package/dist/errors.d.ts +25 -2
  12. package/dist/errors.d.ts.map +1 -1
  13. package/dist/errors.js +53 -0
  14. package/dist/errors.js.map +1 -1
  15. package/dist/eve.d.ts +11 -11
  16. package/dist/eve.d.ts.map +1 -1
  17. package/dist/eve.js +10 -10
  18. package/dist/eve.js.map +1 -1
  19. package/dist/gate.d.ts +34 -1
  20. package/dist/gate.d.ts.map +1 -1
  21. package/dist/gate.js +135 -9
  22. package/dist/gate.js.map +1 -1
  23. package/dist/harness.d.ts +28 -20
  24. package/dist/harness.d.ts.map +1 -1
  25. package/dist/harness.js +165 -26
  26. package/dist/harness.js.map +1 -1
  27. package/dist/hold.d.ts +69 -0
  28. package/dist/hold.d.ts.map +1 -0
  29. package/dist/hold.js +127 -0
  30. package/dist/hold.js.map +1 -0
  31. package/dist/imagecheck.d.ts +14 -7
  32. package/dist/imagecheck.d.ts.map +1 -1
  33. package/dist/imagecheck.js +3 -3
  34. package/dist/imagecheck.js.map +1 -1
  35. package/dist/index.d.ts +8 -3
  36. package/dist/index.d.ts.map +1 -1
  37. package/dist/index.js +4 -2
  38. package/dist/index.js.map +1 -1
  39. package/dist/limits.d.ts +26 -0
  40. package/dist/limits.d.ts.map +1 -0
  41. package/dist/limits.js +45 -0
  42. package/dist/limits.js.map +1 -0
  43. package/dist/managedAgents.d.ts +3 -3
  44. package/dist/managedAgents.d.ts.map +1 -1
  45. package/dist/managedAgents.js +2 -2
  46. package/dist/mcpRegistryRecord.d.ts +143 -0
  47. package/dist/mcpRegistryRecord.d.ts.map +1 -0
  48. package/dist/mcpRegistryRecord.js +217 -0
  49. package/dist/mcpRegistryRecord.js.map +1 -0
  50. package/dist/openai.d.ts +3 -3
  51. package/dist/openai.d.ts.map +1 -1
  52. package/dist/openai.js +9 -8
  53. package/dist/openai.js.map +1 -1
  54. package/dist/phrases.d.ts +87 -0
  55. package/dist/phrases.d.ts.map +1 -0
  56. package/dist/phrases.js +236 -0
  57. package/dist/phrases.js.map +1 -0
  58. package/dist/sequence.d.ts +52 -0
  59. package/dist/sequence.d.ts.map +1 -0
  60. package/dist/sequence.js +121 -0
  61. package/dist/sequence.js.map +1 -0
  62. package/dist/snapshot.d.ts +58 -36
  63. package/dist/snapshot.d.ts.map +1 -1
  64. package/dist/snapshot.js +106 -48
  65. package/dist/snapshot.js.map +1 -1
  66. package/dist/ssoGroups.d.ts +50 -0
  67. package/dist/ssoGroups.d.ts.map +1 -0
  68. package/dist/ssoGroups.js +101 -0
  69. package/dist/ssoGroups.js.map +1 -0
  70. package/dist/workflow.d.ts +5 -3
  71. package/dist/workflow.d.ts.map +1 -1
  72. package/dist/workflow.js +8 -4
  73. package/dist/workflow.js.map +1 -1
  74. package/package.json +1 -1
@@ -0,0 +1,121 @@
1
+ /**
2
+ * Sequence rules: a gate rule `A.*B` run as "find A, then find B after it" in
3
+ * linear time.
4
+ *
5
+ * A rule like ` git .*reset +--hard` is a regex. `grep -E` runs it as an
6
+ * automaton, in time linear in the command. JavaScript's and Python's engines
7
+ * backtrack: for every ` git ` they try every end of `.*`, so 200 KB of
8
+ * ` git git git …` took 9.5 s, which is past the point where a harness that
9
+ * treats a hook timeout as "allow" runs the call. A rule marked `sequence`
10
+ * (`s` in a `.rules` line's flags column) is the same regex, read differently:
11
+ *
12
+ * - its top-level `|` alternatives are tried in turn;
13
+ * - each alternative is cut at its top-level `.*` into steps;
14
+ * - each step is searched for once, starting where the previous one ended.
15
+ *
16
+ * Each search is one pass over the text, so a rule costs at most its number of
17
+ * steps times the length of the text. It means the same as the regex provided
18
+ * the first match of every step but the last also ends first, which holds for
19
+ * every step the rule tables use: a step that starts and ends at a space with
20
+ * no space inside, or a fixed word. `.` does not match a newline and neither
21
+ * does a step search cross one in the regex, but the gates normalise every
22
+ * command subject to single spaces first, so there is none. A test fuzzes each
23
+ * sequence rule against its own regex.
24
+ *
25
+ * Self-contained on purpose — no imports, no module state — because the
26
+ * JavaScript gates emit it as source ({@link SEQUENCE_JS_SOURCE}).
27
+ * `packages/gate-js/src/sequence.ts` is a byte-identical copy and
28
+ * `intutic_clawde/gate/sequence.py` a transliteration; all of them run
29
+ * `fixtures/gate-rule-vectors.json`.
30
+ *
31
+ * @module
32
+ */
33
+ /**
34
+ * A sequence rule's source as alternatives of steps: split at every top-level
35
+ * `|`, then each alternative at every top-level `.*`. ` a .*b| c .*d` is
36
+ * `[[' a ', 'b'], [' c ', 'd']]`. Outside a group or a class only, so `(x|y)`
37
+ * stays inside its step. Empty steps are dropped.
38
+ */
39
+ export function sequenceAlternatives(source) {
40
+ const alternatives = [];
41
+ let steps = [];
42
+ let current = '';
43
+ let depth = 0;
44
+ let inClass = false;
45
+ for (let i = 0; i < source.length; i++) {
46
+ const c = source.charAt(i);
47
+ if (c === '\\') {
48
+ current += c + source.charAt(i + 1);
49
+ i++;
50
+ continue;
51
+ }
52
+ if (inClass) {
53
+ current += c;
54
+ if (c === ']')
55
+ inClass = false;
56
+ continue;
57
+ }
58
+ if (c === '[') {
59
+ inClass = true;
60
+ current += c;
61
+ if (source.charAt(i + 1) === '^')
62
+ current += source.charAt(++i);
63
+ if (source.charAt(i + 1) === ']')
64
+ current += source.charAt(++i);
65
+ continue;
66
+ }
67
+ if (c === '(')
68
+ depth++;
69
+ if (c === ')')
70
+ depth--;
71
+ if (depth === 0 && c === '|') {
72
+ steps.push(current);
73
+ alternatives.push(steps.filter((step) => step !== ''));
74
+ steps = [];
75
+ current = '';
76
+ continue;
77
+ }
78
+ if (depth === 0 && c === '.' && source.charAt(i + 1) === '*') {
79
+ steps.push(current);
80
+ current = '';
81
+ i++;
82
+ continue;
83
+ }
84
+ current += c;
85
+ }
86
+ steps.push(current);
87
+ alternatives.push(steps.filter((step) => step !== ''));
88
+ return alternatives;
89
+ }
90
+ /**
91
+ * Compiles a sequence rule's source for {@link sequenceMatch}: each step with
92
+ * the `g` flag, which is what lets a search start at `lastIndex`.
93
+ */
94
+ export function compileSequence(source, ignoreCase) {
95
+ return sequenceAlternatives(source).map((steps) => steps.map((step) => new RegExp(step, ignoreCase ? 'gi' : 'g')));
96
+ }
97
+ /** Whether `text` matches a compiled sequence rule: some alternative's steps occur in order. */
98
+ export function sequenceMatch(alternatives, text) {
99
+ for (const steps of alternatives) {
100
+ let pos = 0;
101
+ let ok = true;
102
+ for (const step of steps) {
103
+ step.lastIndex = pos;
104
+ const m = step.exec(text);
105
+ if (!m) {
106
+ ok = false;
107
+ break;
108
+ }
109
+ pos = m.index + m[0].length;
110
+ }
111
+ if (ok)
112
+ return true;
113
+ }
114
+ return false;
115
+ }
116
+ /**
117
+ * The three functions as JavaScript source, for a gate to emit: the gates run
118
+ * this exact code, not a retyped copy.
119
+ */
120
+ export const SEQUENCE_JS_SOURCE = `${sequenceAlternatives.toString()}\n${compileSequence.toString()}\n${sequenceMatch.toString()}`;
121
+ //# sourceMappingURL=sequence.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sequence.js","sourceRoot":"","sources":["../src/sequence.ts"],"names":[],"mappings":"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"}
@@ -29,41 +29,20 @@
29
29
  * * Snapshot health is reported as an event — "snapshot missing on 400
30
30
  * machines" must not look identical to "snapshot present and healthy".
31
31
  *
32
- * ## Two deliberate divergences from the Python SDK reader
32
+ * ## Padding and case
33
33
  *
34
- * Both were found empirically, by running `src/__tests__/fidelity.test.ts`
35
- * against a hand-port of `intutic_clawde/gate/snapshot.py`'s `_normalise()`
36
- * and watching real patterns from `protectedPaths.ts` fail to fire. Neither
37
- * is a stylistic choice; both are confirmed gaps in `intutic_clawde`'s
38
- * reader relative to the shipped contract it claims to port, carried here
39
- * only as a documented finding, not as behaviour to reproduce.
40
- *
41
- * 1. **No padding.** `_normalise()` lowercases and collapses whitespace but
42
- * does not pad the result with a leading/trailing space. The actual
43
- * shipped gate (`intuticNormalise` in gateBody.ts, emitted from
44
- * `NORMALISE_CONTRACT.jsSource`) pads. Padding is what lets a
45
- * floor/destructive pattern use a plain leading space as a stand-in for
46
- * `^` (`' rm( +-[a-zA-Z-]+)+ +/( |\\*)'` requires a literal space before
47
- * `rm`) — POSIX ERE has no `\b` and no reliable `^`/`$` inside the emitted
48
- * shell gates, so the whole pattern table is authored against the padded
49
- * contract. It is also why `policySnapshot.ts`'s `toGuardPattern` strips
50
- * the `^`/`$` off an SOP `toolPattern` and re-wraps it as `' (name) '`
51
- * before shipping it as a `subject: 'tool'` snapshot rule — that
52
- * transformation only makes sense against a padded reader. Without
53
- * padding, a command that BEGINS with the dangerous verb (`"rm -rf /"`,
54
- * no leading space) never matches `' rm...'` at all, and the block
55
- * silently never fires.
56
- * 2. **Forced lowercasing.** `_normalise()` lowercases unconditionally; the
57
- * real `NORMALISE_CONTRACT.jsSource` does not — case sensitivity is
58
- * governed entirely by each rule's own `ignoreCase`/`i`-flag column.
59
- * `bypass.env_kill_switch` (` [A-Z][A-Z0-9_]*_HOOKS?=`) and
60
- * `destructive.chmod_recursive_root`/`chown_recursive_root`
61
- * (`[a-zA-Z]*R[a-zA-Z]*`, a literal uppercase `R` for the recursive flag)
62
- * both key on case WITHOUT setting that flag; forcing the subject to
63
- * lowercase first makes them never fire, on real production patterns.
64
- *
65
- * This reader pads and preserves case, matching the real shipped contract;
66
- * see the fidelity suite for the evidence.
34
+ * Normalisation pads the subject with a space at each end and collapses
35
+ * whitespace, and does not lowercase, as the shipped gates do
36
+ * (`NORMALISE_CONTRACT` in `protectedPaths.ts`). Padding is what lets a
37
+ * floor/destructive pattern use a plain leading space or non-word character as
38
+ * a stand-in for `^` (POSIX ERE has no `\b` and no reliable `^`/`$` inside the
39
+ * emitted shell gates), so without it a command that BEGINS with the dangerous
40
+ * verb (`"rm -rf /"`, `"DROP TABLE users"`) never matches. Case sensitivity is
41
+ * each rule's own `ignoreCase` flag: `bypass.env_kill_switch` and the
42
+ * recursive chmod/chown rules key on an uppercase letter without one. The
43
+ * Python SDK's reader once lowercased and did not pad, and missed both; it now
44
+ * follows the same contract, and `destructive-sql-vectors.json` in
45
+ * shared-types runs both readers over the same commands.
67
46
  *
68
47
  * The regex-dialect divergence the Python module documents (`.rules` patterns
69
48
  * are authored as JavaScript regexes; compiling them with a different engine
@@ -71,13 +50,26 @@
71
50
  * here — this reader compiles them as native JS `RegExp`, the dialect they
72
51
  * were authored in.
73
52
  */
53
+ import { type McpAllowlistRecord, type McpRegistryRecord } from './mcpRegistryRecord.js';
54
+ import { type SsoGroupRecord } from './ssoGroups.js';
74
55
  export declare const SNAPSHOT_STALE_AFTER_DAYS = 7;
75
56
  /** Severity tiers, in the order the shipped gate handles them. */
76
57
  export declare const SEV_SHADOW: "shadow";
77
58
  export declare const SEV_WARN: "warn";
78
59
  export declare const SEV_BLOCK: "block";
79
- export type Severity = typeof SEV_SHADOW | typeof SEV_WARN | typeof SEV_BLOCK;
80
- export type RuleSubject = 'tool' | 'command' | 'target' | 'any';
60
+ /**
61
+ * A hold rule (a `REQUIRE_APPROVAL:` SOP, or a local `review_before:` token):
62
+ * refuses like a block, but asks a person rather than denying — see hold.ts.
63
+ */
64
+ export declare const SEV_HOLD: "hold";
65
+ export type Severity = typeof SEV_SHADOW | typeof SEV_WARN | typeof SEV_BLOCK | typeof SEV_HOLD;
66
+ /**
67
+ * `phrase`: the source is `|`-separated phrases matched as words (phrases.ts),
68
+ * not a regex. `action`: the source is matched against the action tokens the
69
+ * command classifies to (`" action:deploy "`, actions.ts) — what a local
70
+ * `review_before: action:<name>` compiles to.
71
+ */
72
+ export type RuleSubject = 'tool' | 'command' | 'target' | 'phrase' | 'action' | 'any';
81
73
  export type SnapshotState = 'ok' | 'absent' | 'invalid' | 'empty' | 'stale';
82
74
  export interface Rule {
83
75
  id: string;
@@ -85,6 +77,14 @@ export interface Rule {
85
77
  subject: RuleSubject;
86
78
  reason: string;
87
79
  pattern: RegExp;
80
+ /**
81
+ * A sequence rule's compiled steps (flags `s`, sequence.ts), or null. The
82
+ * rule is matched by searching for its steps in order, in linear time,
83
+ * rather than by {@link pattern}, which a backtracking engine runs in time
84
+ * growing with the square of the text. Absent on a rule built by hand,
85
+ * which is matched by {@link pattern}.
86
+ */
87
+ steps?: RegExp[][] | null;
88
88
  }
89
89
  export declare class Snapshot {
90
90
  rules: Rule[];
@@ -95,11 +95,33 @@ export declare class Snapshot {
95
95
  ageDays: number;
96
96
  /** Regexes that would not compile. */
97
97
  droppedRules: number;
98
+ /**
99
+ * The workspace's SSO-group policy and the member this snapshot was issued
100
+ * to, or null when the workspace has no group policy. On a snapshot that
101
+ * fails its integrity check the member is null — groups unknown — so an
102
+ * edited group list in the file clears nothing.
103
+ */
104
+ ssoGroups: SsoGroupRecord | null;
105
+ /**
106
+ * The workspace's MCP server registry decisions (the `@mcp_registry`
107
+ * record), or null when it made none. Null on a snapshot that fails its
108
+ * integrity check, on which the gate admits no MCP server at all
109
+ * (`mcpSnapshotUnverifiedRefusal`): a deleted record looks like one never
110
+ * set, so neither record can be vouched for.
111
+ */
112
+ mcpRegistry: McpRegistryRecord | null;
113
+ /**
114
+ * The workspace's `mcpAllowedServers` list (the `@mcp_allowlist` record),
115
+ * or null when it set none. Null on a snapshot that fails its integrity
116
+ * check, as {@link mcpRegistry} is.
117
+ */
118
+ mcpAllowlist: McpAllowlistRecord | null;
98
119
  get healthMessage(): string;
99
120
  }
100
121
  export interface Decision {
101
122
  /** `null` means allow. */
102
123
  severity: Severity | null;
124
+ /** The rule's reason and `[id]`; for a hold, the reason alone, which the gate words as a hold. */
103
125
  reason: string;
104
126
  ruleId: string;
105
127
  }
@@ -1 +1 @@
1
- {"version":3,"file":"snapshot.d.ts","sourceRoot":"","sources":["../src/snapshot.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwEG;AAOH,eAAO,MAAM,yBAAyB,IAAI,CAAA;AAE1C,kEAAkE;AAClE,eAAO,MAAM,UAAU,EAAG,QAAiB,CAAA;AAC3C,eAAO,MAAM,QAAQ,EAAG,MAAe,CAAA;AACvC,eAAO,MAAM,SAAS,EAAG,OAAgB,CAAA;AAEzC,MAAM,MAAM,QAAQ,GAAG,OAAO,UAAU,GAAG,OAAO,QAAQ,GAAG,OAAO,SAAS,CAAA;AAC7E,MAAM,MAAM,WAAW,GAAG,MAAM,GAAG,SAAS,GAAG,QAAQ,GAAG,KAAK,CAAA;AAC/D,MAAM,MAAM,aAAa,GAAG,IAAI,GAAG,QAAQ,GAAG,SAAS,GAAG,OAAO,GAAG,OAAO,CAAA;AAE3E,MAAM,WAAW,IAAI;IACnB,EAAE,EAAE,MAAM,CAAA;IACV,QAAQ,EAAE,MAAM,CAAA;IAChB,OAAO,EAAE,WAAW,CAAA;IACpB,MAAM,EAAE,MAAM,CAAA;IACd,OAAO,EAAE,MAAM,CAAA;CAChB;AAED,qBAAa,QAAQ;IACnB,KAAK,EAAE,IAAI,EAAE,CAAK;IAClB,MAAM,SAAS;IACf,KAAK,EAAE,aAAa,CAAW;IAC/B,WAAW,SAAK;IAChB,WAAW,SAAK;IAChB,OAAO,SAAI;IACX,sCAAsC;IACtC,YAAY,SAAI;IAEhB,IAAI,aAAa,IAAI,MAAM,CAa1B;CACF;AAED,MAAM,WAAW,QAAQ;IACvB,0BAA0B;IAC1B,QAAQ,EAAE,QAAQ,GAAG,IAAI,CAAA;IACzB,MAAM,EAAE,MAAM,CAAA;IACd,MAAM,EAAE,MAAM,CAAA;CACf;AAMD,wBAAgB,YAAY,IAAI,MAAM,CAKrC;AAaD,wBAAgB,YAAY,CAAC,WAAW,SAAK,EAAE,IAAI,CAAC,EAAE,MAAM,GAAG,QAAQ,CAgFtE;AAED,qEAAqE;AACrE,wBAAgB,QAAQ,CACtB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,QAAQ,EACd,aAAa,UAAQ,GACpB,QAAQ,CA0CV;AAED,wBAAgB,oBAAoB,IAAI,OAAO,CAE9C"}
1
+ {"version":3,"file":"snapshot.d.ts","sourceRoot":"","sources":["../src/snapshot.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmDG;AAMH,OAAO,EAKL,KAAK,kBAAkB,EACvB,KAAK,iBAAiB,EACvB,MAAM,wBAAwB,CAAA;AAC/B,OAAO,EAA8C,KAAK,cAAc,EAAE,MAAM,gBAAgB,CAAA;AAKhG,eAAO,MAAM,yBAAyB,IAAI,CAAA;AAE1C,kEAAkE;AAClE,eAAO,MAAM,UAAU,EAAG,QAAiB,CAAA;AAC3C,eAAO,MAAM,QAAQ,EAAG,MAAe,CAAA;AACvC,eAAO,MAAM,SAAS,EAAG,OAAgB,CAAA;AACzC;;;GAGG;AACH,eAAO,MAAM,QAAQ,EAAG,MAAe,CAAA;AAEvC,MAAM,MAAM,QAAQ,GAAG,OAAO,UAAU,GAAG,OAAO,QAAQ,GAAG,OAAO,SAAS,GAAG,OAAO,QAAQ,CAAA;AAC/F;;;;;GAKG;AACH,MAAM,MAAM,WAAW,GAAG,MAAM,GAAG,SAAS,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,GAAG,KAAK,CAAA;AACrF,MAAM,MAAM,aAAa,GAAG,IAAI,GAAG,QAAQ,GAAG,SAAS,GAAG,OAAO,GAAG,OAAO,CAAA;AAE3E,MAAM,WAAW,IAAI;IACnB,EAAE,EAAE,MAAM,CAAA;IACV,QAAQ,EAAE,MAAM,CAAA;IAChB,OAAO,EAAE,WAAW,CAAA;IACpB,MAAM,EAAE,MAAM,CAAA;IACd,OAAO,EAAE,MAAM,CAAA;IACf;;;;;;OAMG;IACH,KAAK,CAAC,EAAE,MAAM,EAAE,EAAE,GAAG,IAAI,CAAA;CAC1B;AAED,qBAAa,QAAQ;IACnB,KAAK,EAAE,IAAI,EAAE,CAAK;IAClB,MAAM,SAAS;IACf,KAAK,EAAE,aAAa,CAAW;IAC/B,WAAW,SAAK;IAChB,WAAW,SAAK;IAChB,OAAO,SAAI;IACX,sCAAsC;IACtC,YAAY,SAAI;IAChB;;;;;OAKG;IACH,SAAS,EAAE,cAAc,GAAG,IAAI,CAAO;IACvC;;;;;;OAMG;IACH,WAAW,EAAE,iBAAiB,GAAG,IAAI,CAAO;IAC5C;;;;OAIG;IACH,YAAY,EAAE,kBAAkB,GAAG,IAAI,CAAO;IAE9C,IAAI,aAAa,IAAI,MAAM,CAa1B;CACF;AAED,MAAM,WAAW,QAAQ;IACvB,0BAA0B;IAC1B,QAAQ,EAAE,QAAQ,GAAG,IAAI,CAAA;IACzB,kGAAkG;IAClG,MAAM,EAAE,MAAM,CAAA;IACd,MAAM,EAAE,MAAM,CAAA;CACf;AAMD,wBAAgB,YAAY,IAAI,MAAM,CAKrC;AAYD,wBAAgB,YAAY,CAAC,WAAW,SAAK,EAAE,IAAI,CAAC,EAAE,MAAM,GAAG,QAAQ,CAuGtE;AAED,qEAAqE;AACrE,wBAAgB,QAAQ,CACtB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,QAAQ,EACd,aAAa,UAAQ,GACpB,QAAQ,CAiEV;AAED,wBAAgB,oBAAoB,IAAI,OAAO,CAE9C"}
package/dist/snapshot.js CHANGED
@@ -29,41 +29,20 @@
29
29
  * * Snapshot health is reported as an event — "snapshot missing on 400
30
30
  * machines" must not look identical to "snapshot present and healthy".
31
31
  *
32
- * ## Two deliberate divergences from the Python SDK reader
32
+ * ## Padding and case
33
33
  *
34
- * Both were found empirically, by running `src/__tests__/fidelity.test.ts`
35
- * against a hand-port of `intutic_clawde/gate/snapshot.py`'s `_normalise()`
36
- * and watching real patterns from `protectedPaths.ts` fail to fire. Neither
37
- * is a stylistic choice; both are confirmed gaps in `intutic_clawde`'s
38
- * reader relative to the shipped contract it claims to port, carried here
39
- * only as a documented finding, not as behaviour to reproduce.
40
- *
41
- * 1. **No padding.** `_normalise()` lowercases and collapses whitespace but
42
- * does not pad the result with a leading/trailing space. The actual
43
- * shipped gate (`intuticNormalise` in gateBody.ts, emitted from
44
- * `NORMALISE_CONTRACT.jsSource`) pads. Padding is what lets a
45
- * floor/destructive pattern use a plain leading space as a stand-in for
46
- * `^` (`' rm( +-[a-zA-Z-]+)+ +/( |\\*)'` requires a literal space before
47
- * `rm`) — POSIX ERE has no `\b` and no reliable `^`/`$` inside the emitted
48
- * shell gates, so the whole pattern table is authored against the padded
49
- * contract. It is also why `policySnapshot.ts`'s `toGuardPattern` strips
50
- * the `^`/`$` off an SOP `toolPattern` and re-wraps it as `' (name) '`
51
- * before shipping it as a `subject: 'tool'` snapshot rule — that
52
- * transformation only makes sense against a padded reader. Without
53
- * padding, a command that BEGINS with the dangerous verb (`"rm -rf /"`,
54
- * no leading space) never matches `' rm...'` at all, and the block
55
- * silently never fires.
56
- * 2. **Forced lowercasing.** `_normalise()` lowercases unconditionally; the
57
- * real `NORMALISE_CONTRACT.jsSource` does not — case sensitivity is
58
- * governed entirely by each rule's own `ignoreCase`/`i`-flag column.
59
- * `bypass.env_kill_switch` (` [A-Z][A-Z0-9_]*_HOOKS?=`) and
60
- * `destructive.chmod_recursive_root`/`chown_recursive_root`
61
- * (`[a-zA-Z]*R[a-zA-Z]*`, a literal uppercase `R` for the recursive flag)
62
- * both key on case WITHOUT setting that flag; forcing the subject to
63
- * lowercase first makes them never fire, on real production patterns.
64
- *
65
- * This reader pads and preserves case, matching the real shipped contract;
66
- * see the fidelity suite for the evidence.
34
+ * Normalisation pads the subject with a space at each end and collapses
35
+ * whitespace, and does not lowercase, as the shipped gates do
36
+ * (`NORMALISE_CONTRACT` in `protectedPaths.ts`). Padding is what lets a
37
+ * floor/destructive pattern use a plain leading space or non-word character as
38
+ * a stand-in for `^` (POSIX ERE has no `\b` and no reliable `^`/`$` inside the
39
+ * emitted shell gates), so without it a command that BEGINS with the dangerous
40
+ * verb (`"rm -rf /"`, `"DROP TABLE users"`) never matches. Case sensitivity is
41
+ * each rule's own `ignoreCase` flag: `bypass.env_kill_switch` and the
42
+ * recursive chmod/chown rules key on an uppercase letter without one. The
43
+ * Python SDK's reader once lowercased and did not pad, and missed both; it now
44
+ * follows the same contract, and `destructive-sql-vectors.json` in
45
+ * shared-types runs both readers over the same commands.
67
46
  *
68
47
  * The regex-dialect divergence the Python module documents (`.rules` patterns
69
48
  * are authored as JavaScript regexes; compiling them with a different engine
@@ -75,11 +54,21 @@ import { createHash } from 'node:crypto';
75
54
  import { readFileSync } from 'node:fs';
76
55
  import { homedir } from 'node:os';
77
56
  import { join } from 'node:path';
57
+ import { decodeMcpAllowlistRecord, decodeMcpRegistryRecord, MCP_ALLOWLIST_RECORD_TAG, MCP_REGISTRY_RECORD_TAG, } from './mcpRegistryRecord.js';
58
+ import { decodeSsoGroupRecord, SSO_GROUP_RECORD_TAG } from './ssoGroups.js';
59
+ import { hasPhrase, phraseText } from './phrases.js';
60
+ import { classify } from './actions.js';
61
+ import { compileSequence, sequenceMatch } from './sequence.js';
78
62
  export const SNAPSHOT_STALE_AFTER_DAYS = 7;
79
63
  /** Severity tiers, in the order the shipped gate handles them. */
80
64
  export const SEV_SHADOW = 'shadow';
81
65
  export const SEV_WARN = 'warn';
82
66
  export const SEV_BLOCK = 'block';
67
+ /**
68
+ * A hold rule (a `REQUIRE_APPROVAL:` SOP, or a local `review_before:` token):
69
+ * refuses like a block, but asks a person rather than denying — see hold.ts.
70
+ */
71
+ export const SEV_HOLD = 'hold';
83
72
  export class Snapshot {
84
73
  rules = [];
85
74
  digest = 'none';
@@ -89,12 +78,33 @@ export class Snapshot {
89
78
  ageDays = 0;
90
79
  /** Regexes that would not compile. */
91
80
  droppedRules = 0;
81
+ /**
82
+ * The workspace's SSO-group policy and the member this snapshot was issued
83
+ * to, or null when the workspace has no group policy. On a snapshot that
84
+ * fails its integrity check the member is null — groups unknown — so an
85
+ * edited group list in the file clears nothing.
86
+ */
87
+ ssoGroups = null;
88
+ /**
89
+ * The workspace's MCP server registry decisions (the `@mcp_registry`
90
+ * record), or null when it made none. Null on a snapshot that fails its
91
+ * integrity check, on which the gate admits no MCP server at all
92
+ * (`mcpSnapshotUnverifiedRefusal`): a deleted record looks like one never
93
+ * set, so neither record can be vouched for.
94
+ */
95
+ mcpRegistry = null;
96
+ /**
97
+ * The workspace's `mcpAllowedServers` list (the `@mcp_allowlist` record),
98
+ * or null when it set none. Null on a snapshot that fails its integrity
99
+ * check, as {@link mcpRegistry} is.
100
+ */
101
+ mcpAllowlist = null;
92
102
  get healthMessage() {
93
103
  switch (this.state) {
94
104
  case 'absent':
95
105
  return 'No policy snapshot — built-in protections only';
96
106
  case 'invalid':
97
- return 'Policy snapshot failed its digest or workspace check — dynamic rules dropped';
107
+ return 'Policy snapshot failed its digest or workspace check — dynamic rules dropped except SSO-group refusals, and every MCP call refused';
98
108
  case 'empty':
99
109
  return 'Policy snapshot contains no rules — the compile produced nothing';
100
110
  case 'stale':
@@ -114,8 +124,7 @@ export function snapshotPath() {
114
124
  /**
115
125
  * Collapse and pad whitespace, as the shipped gates do — case is
116
126
  * DELIBERATELY left untouched; a rule that wants case-insensitivity sets its
117
- * own `ignoreCase` flag. See the module doc comment for both ways the Python
118
- * SDK's reader diverges from this.
127
+ * own `ignoreCase` flag. See the module doc comment.
119
128
  */
120
129
  function normalise(value) {
121
130
  const s = value === null || value === undefined ? '' : String(value);
@@ -147,17 +156,32 @@ export function loadSnapshot(workspaceId = '', path) {
147
156
  }
148
157
  if (!line || line.startsWith('#'))
149
158
  continue;
159
+ if (line.startsWith(`${SSO_GROUP_RECORD_TAG}\t`)) {
160
+ snap.ssoGroups = decodeSsoGroupRecord(line);
161
+ continue;
162
+ }
163
+ if (line.startsWith(`${MCP_REGISTRY_RECORD_TAG}\t`)) {
164
+ snap.mcpRegistry = decodeMcpRegistryRecord(line);
165
+ continue;
166
+ }
167
+ if (line.startsWith(`${MCP_ALLOWLIST_RECORD_TAG}\t`)) {
168
+ snap.mcpAllowlist = decodeMcpAllowlistRecord(line);
169
+ continue;
170
+ }
150
171
  const f = line.split('\t');
151
172
  // Column order: id, severity, flags, subject, reason, source(regex), [argPatternB64].
173
+ // Flags: i = case-insensitive, s = a sequence rule.
152
174
  if (f.length < 6 || !f[5])
153
175
  continue;
176
+ const ic = f[2].includes('i');
154
177
  try {
155
178
  snap.rules.push({
156
179
  id: f[0],
157
180
  severity: f[1],
158
181
  subject: f[3] || 'any',
159
182
  reason: f[4],
160
- pattern: new RegExp(f[5], f[2] === 'i' ? 'i' : ''),
183
+ pattern: new RegExp(f[5], ic ? 'i' : ''),
184
+ steps: f[2].includes('s') ? compileSequence(f[5], ic) : null,
161
185
  });
162
186
  }
163
187
  catch {
@@ -172,7 +196,9 @@ export function loadSnapshot(workspaceId = '', path) {
172
196
  .filter((l) => l && !l.startsWith('#'))
173
197
  .join('\n');
174
198
  const actual = createHash('sha256').update(body, 'utf-8').digest('hex').slice(0, 32);
175
- if (snap.digest !== 'none' && actual !== snap.digest) {
199
+ // No digest line is unverified too: the sync daemon always writes one, so
200
+ // its absence means the file was edited.
201
+ if (actual !== snap.digest) {
176
202
  snap.state = 'invalid';
177
203
  }
178
204
  if (snap.state === 'ok' && snap.workspaceId && workspaceId && snap.workspaceId !== workspaceId) {
@@ -185,6 +211,13 @@ export function loadSnapshot(workspaceId = '', path) {
185
211
  }
186
212
  if (snap.state === 'invalid') {
187
213
  snap.rules = []; // additive tier — dropping it returns to yesterday's behaviour
214
+ // Except the group policy, which only ever refuses: it still applies, to a
215
+ // member whose groups this gate can no longer vouch for.
216
+ if (snap.ssoGroups)
217
+ snap.ssoGroups = { ...snap.ssoGroups, member: null };
218
+ // Neither MCP record can be vouched for: the gate admits no MCP server.
219
+ snap.mcpRegistry = null;
220
+ snap.mcpAllowlist = null;
188
221
  }
189
222
  if (snap.state === 'ok' && snap.generatedAt) {
190
223
  const t = Date.parse(snap.generatedAt);
@@ -209,16 +242,36 @@ export function evaluate(toolName, target, command, snap, guardDisabled = false)
209
242
  const nTool = normalise(toolName);
210
243
  const nCommand = normalise(command);
211
244
  const nTarget = normalise(target);
245
+ let words = null;
246
+ // The command's action tokens, space-padded as the hook gates write them, so
247
+ // a hold on `action:deploy` matches whole tokens. Classified with the same
248
+ // needles and phrase matcher as the hook gates and the proxy's actions.rs.
249
+ let actions = null;
212
250
  for (const rule of rules) {
213
- const subjects = rule.subject === 'tool'
214
- ? [nTool]
215
- : rule.subject === 'command'
216
- ? [nCommand]
217
- : rule.subject === 'target'
218
- ? [nTarget]
219
- : [nCommand, nTarget];
251
+ if (rule.subject === 'phrase') {
252
+ // The source is `|`-separated phrases matched as words against the raw
253
+ // command (phrases.ts), not a regex: a backtracking regex for "whatever
254
+ // separates the words" is super-linear on crafted input.
255
+ words ??= phraseText(command);
256
+ const w = words;
257
+ if (!rule.pattern.source.split('|').some((p) => hasPhrase(w, p, true)))
258
+ continue;
259
+ }
260
+ if (rule.subject === 'action')
261
+ actions ??= ' ' + classify(toolName, { command }).join(' ') + ' ';
262
+ const subjects = rule.subject === 'phrase'
263
+ ? [nCommand]
264
+ : rule.subject === 'action'
265
+ ? [actions]
266
+ : rule.subject === 'tool'
267
+ ? [nTool]
268
+ : rule.subject === 'command'
269
+ ? [nCommand]
270
+ : rule.subject === 'target'
271
+ ? [nTarget]
272
+ : [nCommand, nTarget];
220
273
  for (const subject of subjects) {
221
- if (!rule.pattern.test(subject))
274
+ if (rule.subject !== 'phrase' && !(rule.steps ? sequenceMatch(rule.steps, subject) : rule.pattern.test(subject)))
222
275
  continue;
223
276
  if (rule.severity === SEV_SHADOW) {
224
277
  return { severity: SEV_SHADOW, reason: `${rule.reason} [${rule.id}]`, ruleId: rule.id };
@@ -231,7 +284,12 @@ export function evaluate(toolName, target, command, snap, guardDisabled = false)
231
284
  ruleId: rule.id,
232
285
  };
233
286
  }
234
- // The rule's own reason, not a generic one — resolveSeverity reads it.
287
+ if (rule.severity === SEV_HOLD) {
288
+ return { severity: SEV_HOLD, reason: rule.reason, ruleId: rule.id };
289
+ }
290
+ // Any other severity blocks, as an unknown one does in the shipped
291
+ // gates: a severity this reader does not know must not allow. The
292
+ // rule's own reason, not a generic one — resolveSeverity reads it.
235
293
  return { severity: SEV_BLOCK, reason: `${rule.reason} [${rule.id}]`, ruleId: rule.id };
236
294
  }
237
295
  }
@@ -1 +1 @@
1
- {"version":3,"file":"snapshot.js","sourceRoot":"","sources":["../src/snapshot.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"snapshot.js","sourceRoot":"","sources":["../src/snapshot.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmDG;AAEH,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AACxC,OAAO,EAAE,YAAY,EAAE,MAAM,SAAS,CAAA;AACtC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAA;AACjC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAChC,OAAO,EACL,wBAAwB,EACxB,uBAAuB,EACvB,wBAAwB,EACxB,uBAAuB,GAGxB,MAAM,wBAAwB,CAAA;AAC/B,OAAO,EAAE,oBAAoB,EAAE,oBAAoB,EAAuB,MAAM,gBAAgB,CAAA;AAChG,OAAO,EAAE,SAAS,EAAE,UAAU,EAAmB,MAAM,cAAc,CAAA;AACrE,OAAO,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAA;AACvC,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,eAAe,CAAA;AAE9D,MAAM,CAAC,MAAM,yBAAyB,GAAG,CAAC,CAAA;AAE1C,kEAAkE;AAClE,MAAM,CAAC,MAAM,UAAU,GAAG,QAAiB,CAAA;AAC3C,MAAM,CAAC,MAAM,QAAQ,GAAG,MAAe,CAAA;AACvC,MAAM,CAAC,MAAM,SAAS,GAAG,OAAgB,CAAA;AACzC;;;GAGG;AACH,MAAM,CAAC,MAAM,QAAQ,GAAG,MAAe,CAAA;AA4BvC,MAAM,OAAO,QAAQ;IACnB,KAAK,GAAW,EAAE,CAAA;IAClB,MAAM,GAAG,MAAM,CAAA;IACf,KAAK,GAAkB,QAAQ,CAAA;IAC/B,WAAW,GAAG,EAAE,CAAA;IAChB,WAAW,GAAG,EAAE,CAAA;IAChB,OAAO,GAAG,CAAC,CAAA;IACX,sCAAsC;IACtC,YAAY,GAAG,CAAC,CAAA;IAChB;;;;;OAKG;IACH,SAAS,GAA0B,IAAI,CAAA;IACvC;;;;;;OAMG;IACH,WAAW,GAA6B,IAAI,CAAA;IAC5C;;;;OAIG;IACH,YAAY,GAA8B,IAAI,CAAA;IAE9C,IAAI,aAAa;QACf,QAAQ,IAAI,CAAC,KAAK,EAAE,CAAC;YACnB,KAAK,QAAQ;gBACX,OAAO,gDAAgD,CAAA;YACzD,KAAK,SAAS;gBACZ,OAAO,oIAAoI,CAAA;YAC7I,KAAK,OAAO;gBACV,OAAO,kEAAkE,CAAA;YAC3E,KAAK,OAAO;gBACV,OAAO,sBAAsB,IAAI,CAAC,OAAO,8BAA8B,CAAA;YACzE;gBACE,OAAO,EAAE,CAAA;QACb,CAAC;IACH,CAAC;CACF;AAUD,SAAS,KAAK;IACZ,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,CAAA;AACnD,CAAC;AAED,MAAM,UAAU,YAAY;IAC1B,OAAO,CACL,OAAO,CAAC,GAAG,CAAC,sBAAsB;QAClC,IAAI,CAAC,OAAO,EAAE,EAAE,UAAU,EAAE,OAAO,EAAE,uBAAuB,CAAC,CAC9D,CAAA;AACH,CAAC;AAED;;;;GAIG;AACH,SAAS,SAAS,CAAC,KAAc;IAC/B,MAAM,CAAC,GAAG,KAAK,KAAK,IAAI,IAAI,KAAK,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAA;IACpE,OAAO,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,GAAG,GAAG,CAAA;AAClD,CAAC;AAED,MAAM,UAAU,YAAY,CAAC,WAAW,GAAG,EAAE,EAAE,IAAa;IAC1D,MAAM,CAAC,GAAG,IAAI,IAAI,YAAY,EAAE,CAAA;IAChC,MAAM,IAAI,GAAG,IAAI,QAAQ,EAAE,CAAA;IAE3B,IAAI,IAAY,CAAA;IAChB,IAAI,CAAC;QACH,IAAI,GAAG,YAAY,CAAC,CAAC,EAAE,OAAO,CAAC,CAAA;IACjC,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAA,CAAC,uBAAuB;IACrC,CAAC;IAED,IAAI,CAAC,KAAK,GAAG,IAAI,CAAA;IACjB,KAAK,MAAM,IAAI,IAAI,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC;QACpC,IAAI,IAAI,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;YAChC,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAA;YAClC,SAAQ;QACV,CAAC;QACD,IAAI,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,EAAE,CAAC;YACnC,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,IAAI,EAAE,CAAA;YACxC,SAAQ;QACV,CAAC;QACD,IAAI,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,EAAE,CAAC;YACnC,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,IAAI,EAAE,CAAA;YACxC,SAAQ;QACV,CAAC;QACD,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC;YAAE,SAAQ;QAC3C,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,oBAAoB,IAAI,CAAC,EAAE,CAAC;YACjD,IAAI,CAAC,SAAS,GAAG,oBAAoB,CAAC,IAAI,CAAC,CAAA;YAC3C,SAAQ;QACV,CAAC;QACD,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,uBAAuB,IAAI,CAAC,EAAE,CAAC;YACpD,IAAI,CAAC,WAAW,GAAG,uBAAuB,CAAC,IAAI,CAAC,CAAA;YAChD,SAAQ;QACV,CAAC;QACD,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,wBAAwB,IAAI,CAAC,EAAE,CAAC;YACrD,IAAI,CAAC,YAAY,GAAG,wBAAwB,CAAC,IAAI,CAAC,CAAA;YAClD,SAAQ;QACV,CAAC;QAED,MAAM,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA;QAC1B,sFAAsF;QACtF,oDAAoD;QACpD,IAAI,CAAC,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC;YAAE,SAAQ;QACnC,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC,CAAE,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAA;QAC9B,IAAI,CAAC;YACH,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC;gBACd,EAAE,EAAE,CAAC,CAAC,CAAC,CAAE;gBACT,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAE;gBACf,OAAO,EAAG,CAAC,CAAC,CAAC,CAAiB,IAAI,KAAK;gBACvC,MAAM,EAAE,CAAC,CAAC,CAAC,CAAE;gBACb,OAAO,EAAE,IAAI,MAAM,CAAC,CAAC,CAAC,CAAC,CAAE,EAAE,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC;gBACzC,KAAK,EAAE,CAAC,CAAC,CAAC,CAAE,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,eAAe,CAAC,CAAC,CAAC,CAAC,CAAE,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI;aAC/D,CAAC,CAAA;QACJ,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,YAAY,IAAI,CAAC,CAAA;QACxB,CAAC;IACH,CAAC;IAED,4EAA4E;IAC5E,yEAAyE;IACzE,oCAAoC;IACpC,MAAM,IAAI,GAAG,IAAI;SACd,KAAK,CAAC,IAAI,CAAC;SACX,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;SACtC,IAAI,CAAC,IAAI,CAAC,CAAA;IACb,MAAM,MAAM,GAAG,UAAU,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAA;IACpF,0EAA0E;IAC1E,yCAAyC;IACzC,IAAI,MAAM,KAAK,IAAI,CAAC,MAAM,EAAE,CAAC;QAC3B,IAAI,CAAC,KAAK,GAAG,SAAS,CAAA;IACxB,CAAC;IAED,IAAI,IAAI,CAAC,KAAK,KAAK,IAAI,IAAI,IAAI,CAAC,WAAW,IAAI,WAAW,IAAI,IAAI,CAAC,WAAW,KAAK,WAAW,EAAE,CAAC;QAC/F,IAAI,CAAC,KAAK,GAAG,SAAS,CAAA;IACxB,CAAC;IAED,4EAA4E;IAC5E,4CAA4C;IAC5C,IAAI,IAAI,CAAC,KAAK,KAAK,IAAI,IAAI,IAAI,CAAC,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACnD,IAAI,CAAC,KAAK,GAAG,OAAO,CAAA;IACtB,CAAC;IAED,IAAI,IAAI,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;QAC7B,IAAI,CAAC,KAAK,GAAG,EAAE,CAAA,CAAC,+DAA+D;QAC/E,2EAA2E;QAC3E,yDAAyD;QACzD,IAAI,IAAI,CAAC,SAAS;YAAE,IAAI,CAAC,SAAS,GAAG,EAAE,GAAG,IAAI,CAAC,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,CAAA;QACxE,wEAAwE;QACxE,IAAI,CAAC,WAAW,GAAG,IAAI,CAAA;QACvB,IAAI,CAAC,YAAY,GAAG,IAAI,CAAA;IAC1B,CAAC;IAED,IAAI,IAAI,CAAC,KAAK,KAAK,IAAI,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;QAC5C,MAAM,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,WAAW,CAAC,CAAA;QACtC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;YACrB,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC,GAAG,UAAU,CAAC,CAAC,CAAA;YACrE,IAAI,IAAI,CAAC,OAAO,GAAG,yBAAyB,EAAE,CAAC;gBAC7C,IAAI,CAAC,KAAK,GAAG,OAAO,CAAA,CAAC,8CAA8C;YACrE,CAAC;QACH,CAAC;IACH,CAAC;IAED,OAAO,IAAI,CAAA;AACb,CAAC;AAED,qEAAqE;AACrE,MAAM,UAAU,QAAQ,CACtB,QAAgB,EAChB,MAAc,EACd,OAAe,EACf,IAAc,EACd,aAAa,GAAG,KAAK;IAErB,IAAI,KAAK,GAAG,IAAI,CAAC,KAAK,CAAA;IACtB,IAAI,aAAa,EAAE,CAAC;QAClB,sEAAsE;QACtE,uEAAuE;QACvE,uDAAuD;QACvD,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,UAAU,CAAC,cAAc,CAAC,CAAC,CAAA;IAC/D,CAAC;IAED,MAAM,KAAK,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAA;IACjC,MAAM,QAAQ,GAAG,SAAS,CAAC,OAAO,CAAC,CAAA;IACnC,MAAM,OAAO,GAAG,SAAS,CAAC,MAAM,CAAC,CAAA;IACjC,IAAI,KAAK,GAAsB,IAAI,CAAA;IACnC,6EAA6E;IAC7E,2EAA2E;IAC3E,2EAA2E;IAC3E,IAAI,OAAO,GAAkB,IAAI,CAAA;IAEjC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,IAAI,CAAC,OAAO,KAAK,QAAQ,EAAE,CAAC;YAC9B,uEAAuE;YACvE,wEAAwE;YACxE,yDAAyD;YACzD,KAAK,KAAK,UAAU,CAAC,OAAO,CAAC,CAAA;YAC7B,MAAM,CAAC,GAAG,KAAK,CAAA;YACf,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,SAAS,CAAC,CAAC,EAAE,CAAC,EAAE,IAAI,CAAC,CAAC;gBAAE,SAAQ;QAClF,CAAC;QACD,IAAI,IAAI,CAAC,OAAO,KAAK,QAAQ;YAAE,OAAO,KAAK,GAAG,GAAG,QAAQ,CAAC,QAAQ,EAAE,EAAE,OAAO,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,GAAG,CAAA;QAChG,MAAM,QAAQ,GACZ,IAAI,CAAC,OAAO,KAAK,QAAQ;YACvB,CAAC,CAAC,CAAC,QAAQ,CAAC;YACZ,CAAC,CAAC,IAAI,CAAC,OAAO,KAAK,QAAQ;gBACzB,CAAC,CAAC,CAAC,OAAQ,CAAC;gBACZ,CAAC,CAAC,IAAI,CAAC,OAAO,KAAK,MAAM;oBACvB,CAAC,CAAC,CAAC,KAAK,CAAC;oBACT,CAAC,CAAC,IAAI,CAAC,OAAO,KAAK,SAAS;wBAC1B,CAAC,CAAC,CAAC,QAAQ,CAAC;wBACZ,CAAC,CAAC,IAAI,CAAC,OAAO,KAAK,QAAQ;4BACzB,CAAC,CAAC,CAAC,OAAO,CAAC;4BACX,CAAC,CAAC,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAA;QAEjC,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;YAC/B,IAAI,IAAI,CAAC,OAAO,KAAK,QAAQ,IAAI,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,aAAa,CAAC,IAAI,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;gBAAE,SAAQ;YAC1H,IAAI,IAAI,CAAC,QAAQ,KAAK,UAAU,EAAE,CAAC;gBACjC,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,CAAA;YACzF,CAAC;YACD,IAAI,IAAI,CAAC,QAAQ,KAAK,QAAQ,EAAE,CAAC;gBAC/B,MAAM,IAAI,GAAG,QAAQ,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAA;gBAChD,OAAO;oBACL,QAAQ,EAAE,QAAQ;oBAClB,MAAM,EAAE,GAAG,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,UAAU,IAAI,EAAE;oBAClD,MAAM,EAAE,IAAI,CAAC,EAAE;iBAChB,CAAA;YACH,CAAC;YACD,IAAI,IAAI,CAAC,QAAQ,KAAK,QAAQ,EAAE,CAAC;gBAC/B,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,CAAA;YACrE,CAAC;YACD,mEAAmE;YACnE,kEAAkE;YAClE,mEAAmE;YACnE,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,CAAA;QACxF,CAAC;IACH,CAAC;IAED,OAAO,KAAK,EAAE,CAAA;AAChB,CAAC;AAED,MAAM,UAAU,oBAAoB;IAClC,OAAO,OAAO,CAAC,GAAG,CAAC,qBAAqB,KAAK,GAAG,CAAA;AAClD,CAAC"}
@@ -0,0 +1,50 @@
1
+ /**
2
+ * SSO-group tool clearance, read from the policy snapshot.
3
+ *
4
+ * Port of `evaluateSsoGroupClearance` and the `@sso_groups` record in
5
+ * `packages/shared-types/src/ssoGroupClearance.ts` — the evaluator the control
6
+ * plane's hook gate, the MCP proxy and the sync daemon's snapshot compiler
7
+ * share. This package has no workspace dependencies, so it carries a copy, and
8
+ * `src/__tests__/ssoGroups.test.ts` runs the shared vectors
9
+ * (`packages/shared-types/fixtures/sso-group-clearance-vectors.json`) through
10
+ * it so the copy cannot drift. `intutic_clawde/gate/sso_groups.py` is the
11
+ * Python port of the same thing.
12
+ *
13
+ * The snapshot's record carries the workspace's policy and the member the
14
+ * snapshot was issued to, with their groups as the control plane resolved
15
+ * them. It sits inside the snapshot's digest; when the digest fails, the gate
16
+ * still applies the policy but treats the member's groups as unknown, so an
17
+ * edited group list clears nothing.
18
+ */
19
+ export type SsoGroupClearance = 'GRANTED' | 'DENIED' | 'REQUIRES_OBO';
20
+ export interface SsoGroupPolicy {
21
+ highRiskTools: string[];
22
+ requiredGroups: string[];
23
+ requireOboFor: string[];
24
+ }
25
+ export interface SsoGroupRecord {
26
+ policy: SsoGroupPolicy;
27
+ member: {
28
+ memberId: string;
29
+ ssoGroups: string[];
30
+ } | null;
31
+ issuedAt: string;
32
+ }
33
+ export interface SsoGroupDecision {
34
+ clearance: SsoGroupClearance;
35
+ ruleId: string | null;
36
+ reason: string;
37
+ }
38
+ export declare const SSO_GROUP_RECORD_TAG = "@sso_groups";
39
+ export declare function parseSsoGroupPolicy(value: unknown): SsoGroupPolicy | null;
40
+ /**
41
+ * Whether a call named `name` is the tool a policy entry names: exactly, or,
42
+ * for an entry that is an MCP tool's own name (not starting with `mcp__`), as
43
+ * the name a harness gives it on any server, `mcp__<server>__<entry>`.
44
+ */
45
+ export declare function ssoGroupToolMatches(entry: string, name: string): boolean;
46
+ /** `memberGroups` null means the groups are unknown — a high-risk tool is then refused. */
47
+ export declare function evaluateSsoGroupClearance(policy: SsoGroupPolicy | null, toolName: string, memberGroups: readonly string[] | null): SsoGroupDecision;
48
+ /** Reads the snapshot's record line; null for any other line or a damaged one. */
49
+ export declare function decodeSsoGroupRecord(line: string): SsoGroupRecord | null;
50
+ //# sourceMappingURL=ssoGroups.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ssoGroups.d.ts","sourceRoot":"","sources":["../src/ssoGroups.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,MAAM,MAAM,iBAAiB,GAAG,SAAS,GAAG,QAAQ,GAAG,cAAc,CAAA;AAErE,MAAM,WAAW,cAAc;IAC7B,aAAa,EAAE,MAAM,EAAE,CAAA;IACvB,cAAc,EAAE,MAAM,EAAE,CAAA;IACxB,aAAa,EAAE,MAAM,EAAE,CAAA;CACxB;AAED,MAAM,WAAW,cAAc;IAC7B,MAAM,EAAE,cAAc,CAAA;IACtB,MAAM,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,EAAE,CAAA;KAAE,GAAG,IAAI,CAAA;IACxD,QAAQ,EAAE,MAAM,CAAA;CACjB;AAED,MAAM,WAAW,gBAAgB;IAC/B,SAAS,EAAE,iBAAiB,CAAA;IAC5B,MAAM,EAAE,MAAM,GAAG,IAAI,CAAA;IACrB,MAAM,EAAE,MAAM,CAAA;CACf;AAED,eAAO,MAAM,oBAAoB,gBAAgB,CAAA;AAMjD,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,OAAO,GAAG,cAAc,GAAG,IAAI,CAQzE;AAMD;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAKxE;AAOD,2FAA2F;AAC3F,wBAAgB,yBAAyB,CACvC,MAAM,EAAE,cAAc,GAAG,IAAI,EAC7B,QAAQ,EAAE,MAAM,EAChB,YAAY,EAAE,SAAS,MAAM,EAAE,GAAG,IAAI,GACrC,gBAAgB,CAuBlB;AAED,kFAAkF;AAClF,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,cAAc,GAAG,IAAI,CAgBxE"}