@intutic/sync-daemon 1.10.1 → 2.1.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 (107) hide show
  1. package/dist/agentReporter.d.ts +4 -12
  2. package/dist/agentReporter.d.ts.map +1 -1
  3. package/dist/agentReporter.js +25 -4
  4. package/dist/agentReporter.js.map +1 -1
  5. package/dist/configWriter.d.ts.map +1 -1
  6. package/dist/configWriter.js +20 -6
  7. package/dist/configWriter.js.map +1 -1
  8. package/dist/harness/aiderConfigMerger.d.ts +41 -5
  9. package/dist/harness/aiderConfigMerger.d.ts.map +1 -1
  10. package/dist/harness/aiderConfigMerger.js +110 -86
  11. package/dist/harness/aiderConfigMerger.js.map +1 -1
  12. package/dist/harness/antigravityHooks.d.ts +13 -8
  13. package/dist/harness/antigravityHooks.d.ts.map +1 -1
  14. package/dist/harness/antigravityHooks.js +51 -39
  15. package/dist/harness/antigravityHooks.js.map +1 -1
  16. package/dist/harness/claudeCodeHooks.d.ts.map +1 -1
  17. package/dist/harness/claudeCodeHooks.js +42 -28
  18. package/dist/harness/claudeCodeHooks.js.map +1 -1
  19. package/dist/harness/clineHooks.d.ts +39 -9
  20. package/dist/harness/clineHooks.d.ts.map +1 -1
  21. package/dist/harness/clineHooks.js +139 -60
  22. package/dist/harness/clineHooks.js.map +1 -1
  23. package/dist/harness/codexConfigMerger.d.ts +38 -0
  24. package/dist/harness/codexConfigMerger.d.ts.map +1 -0
  25. package/dist/harness/codexConfigMerger.js +101 -0
  26. package/dist/harness/codexConfigMerger.js.map +1 -0
  27. package/dist/harness/codexHooks.d.ts +4 -2
  28. package/dist/harness/codexHooks.d.ts.map +1 -1
  29. package/dist/harness/codexHooks.js +11 -11
  30. package/dist/harness/codexHooks.js.map +1 -1
  31. package/dist/harness/continueConfigMerger.d.ts +46 -0
  32. package/dist/harness/continueConfigMerger.d.ts.map +1 -0
  33. package/dist/harness/continueConfigMerger.js +90 -0
  34. package/dist/harness/continueConfigMerger.js.map +1 -0
  35. package/dist/harness/continueHooks.d.ts +15 -25
  36. package/dist/harness/continueHooks.d.ts.map +1 -1
  37. package/dist/harness/continueHooks.js +22 -119
  38. package/dist/harness/continueHooks.js.map +1 -1
  39. package/dist/harness/cursorHooks.d.ts +33 -16
  40. package/dist/harness/cursorHooks.d.ts.map +1 -1
  41. package/dist/harness/cursorHooks.js +66 -25
  42. package/dist/harness/cursorHooks.js.map +1 -1
  43. package/dist/harness/dshHooks.d.ts +59 -52
  44. package/dist/harness/dshHooks.d.ts.map +1 -1
  45. package/dist/harness/dshHooks.js +145 -147
  46. package/dist/harness/dshHooks.js.map +1 -1
  47. package/dist/harness/gateKind.d.ts.map +1 -1
  48. package/dist/harness/gateKind.js +1 -0
  49. package/dist/harness/gateKind.js.map +1 -1
  50. package/dist/harness/githubCopilotHooks.js +1 -1
  51. package/dist/harness/grokHooks.d.ts.map +1 -1
  52. package/dist/harness/grokHooks.js +7 -2
  53. package/dist/harness/grokHooks.js.map +1 -1
  54. package/dist/harness/hermesHooks.d.ts +9 -0
  55. package/dist/harness/hermesHooks.d.ts.map +1 -1
  56. package/dist/harness/hermesHooks.js +32 -31
  57. package/dist/harness/hermesHooks.js.map +1 -1
  58. package/dist/harness/jsonMergeTarget.d.ts +23 -0
  59. package/dist/harness/jsonMergeTarget.d.ts.map +1 -0
  60. package/dist/harness/jsonMergeTarget.js +50 -0
  61. package/dist/harness/jsonMergeTarget.js.map +1 -0
  62. package/dist/harness/mcpAutoWrite.d.ts +28 -6
  63. package/dist/harness/mcpAutoWrite.d.ts.map +1 -1
  64. package/dist/harness/mcpAutoWrite.js +258 -32
  65. package/dist/harness/mcpAutoWrite.js.map +1 -1
  66. package/dist/harness/n8nHooks.d.ts.map +1 -1
  67. package/dist/harness/n8nHooks.js +6 -7
  68. package/dist/harness/n8nHooks.js.map +1 -1
  69. package/dist/harness/openCodeHooks.d.ts +37 -6
  70. package/dist/harness/openCodeHooks.d.ts.map +1 -1
  71. package/dist/harness/openCodeHooks.js +101 -8
  72. package/dist/harness/openCodeHooks.js.map +1 -1
  73. package/dist/harness/openWebuiHooks.d.ts.map +1 -1
  74. package/dist/harness/openWebuiHooks.js +5 -4
  75. package/dist/harness/openWebuiHooks.js.map +1 -1
  76. package/dist/harness/openhandsHooks.d.ts +13 -0
  77. package/dist/harness/openhandsHooks.d.ts.map +1 -1
  78. package/dist/harness/openhandsHooks.js +70 -0
  79. package/dist/harness/openhandsHooks.js.map +1 -1
  80. package/dist/harness/piHooks.d.ts +17 -0
  81. package/dist/harness/piHooks.d.ts.map +1 -1
  82. package/dist/harness/piHooks.js +28 -29
  83. package/dist/harness/piHooks.js.map +1 -1
  84. package/dist/harness/protectedPaths.d.ts +64 -6
  85. package/dist/harness/protectedPaths.d.ts.map +1 -1
  86. package/dist/harness/protectedPaths.js +161 -11
  87. package/dist/harness/protectedPaths.js.map +1 -1
  88. package/dist/harness/windsurfHooks.d.ts +3 -1
  89. package/dist/harness/windsurfHooks.d.ts.map +1 -1
  90. package/dist/harness/windsurfHooks.js +64 -42
  91. package/dist/harness/windsurfHooks.js.map +1 -1
  92. package/dist/harness/windsurfJetBrainsProxy.d.ts +9 -6
  93. package/dist/harness/windsurfJetBrainsProxy.d.ts.map +1 -1
  94. package/dist/harness/windsurfJetBrainsProxy.js +17 -6
  95. package/dist/harness/windsurfJetBrainsProxy.js.map +1 -1
  96. package/dist/index.d.ts +3 -0
  97. package/dist/index.d.ts.map +1 -1
  98. package/dist/index.js +3 -0
  99. package/dist/index.js.map +1 -1
  100. package/dist/lib/policySnapshot.d.ts +19 -0
  101. package/dist/lib/policySnapshot.d.ts.map +1 -1
  102. package/dist/lib/policySnapshot.js +29 -2
  103. package/dist/lib/policySnapshot.js.map +1 -1
  104. package/dist/watcher/settingsGuard.d.ts.map +1 -1
  105. package/dist/watcher/settingsGuard.js +14 -15
  106. package/dist/watcher/settingsGuard.js.map +1 -1
  107. package/package.json +6 -6
@@ -20,6 +20,7 @@ import * as fs from 'node:fs/promises';
20
20
  import * as path from 'node:path';
21
21
  import * as os from 'node:os';
22
22
  import { createLogger } from '@intutic/logger';
23
+ import { parseDocument, isMap } from 'yaml';
23
24
  import { newIso } from '@intutic/id';
24
25
  import { emitShellGate, SHELL_EXTRACT, SHELL_FAIL_CLOSED } from './gateBody.js';
25
26
  const log = createLogger('sync-hermes-hooks');
@@ -97,43 +98,43 @@ exit 0
97
98
  }
98
99
  // ─── YAML merge helpers ───────────────────────────────────────────────────────
99
100
  /**
100
- * YAML-safe merge of the Hermes config.
101
- *
102
- * Strategy (no YAML library — pure string manipulation):
103
- * - If file doesn't exist: write fresh with just the hooks block.
104
- * - If file exists and already contains `preToolUse:`: replace the command line.
105
- * - If file exists but has no `preToolUse:`: append the hooks block.
106
- * - If file has `hooks:` but no `preToolUse:`: insert inside existing hooks section.
101
+ * Merge the hook registration into the Hermes config: `hooks.preToolUse.command`
102
+ * is set to the gate, and everything else in the file — other hooks, MCP
103
+ * servers, comments — is kept. Edited through the `yaml` document model; an
104
+ * earlier line-based version replaced the first `command:` line anywhere in
105
+ * the file, whichever key it belonged to. A file that does not parse, or is
106
+ * not a mapping, is left untouched and reported.
107
107
  */
108
- async function mergeHermesConfig(hookScriptPath) {
109
- const hooksBlock = [
110
- 'hooks:',
111
- ' preToolUse:',
112
- ` command: ${hookScriptPath}`,
113
- ].join('\n');
114
- let existing = null;
108
+ export function mergeHermesYaml(existing, hookScriptPath) {
109
+ const doc = parseDocument(existing);
110
+ if (doc.errors.length > 0)
111
+ return null;
112
+ if (doc.contents === null)
113
+ doc.contents = doc.createNode({});
114
+ if (!isMap(doc.contents))
115
+ return null;
115
116
  try {
116
- existing = await fs.readFile(HERMES_CONFIG, 'utf-8');
117
+ doc.setIn(['hooks', 'preToolUse', 'command'], hookScriptPath);
117
118
  }
118
119
  catch {
119
- // File doesn't exist — write fresh
120
- }
121
- let merged;
122
- if (existing === null) {
123
- // Fresh write
124
- merged = hooksBlock + '\n';
120
+ // `hooks` or `hooks.preToolUse` is a scalar or list — not a shape to edit.
121
+ return null;
125
122
  }
126
- else if (/^\s*preToolUse:/m.test(existing)) {
127
- // Replace the existing command line under preToolUse:
128
- merged = existing.replace(/^(\s*command:\s*).*$/m, `$1${hookScriptPath}`);
123
+ return doc.toString();
124
+ }
125
+ async function mergeHermesConfig(hookScriptPath) {
126
+ let existing = '';
127
+ try {
128
+ existing = await fs.readFile(HERMES_CONFIG, 'utf-8');
129
129
  }
130
- else if (/^hooks:/m.test(existing)) {
131
- // hooks: block exists but no preToolUse: — insert inside hooks section
132
- merged = existing.replace(/^(hooks:\s*)$/m, `$1\n preToolUse:\n command: ${hookScriptPath}`);
130
+ catch (err) {
131
+ if (err.code !== 'ENOENT')
132
+ throw err;
133
133
  }
134
- else {
135
- // No hooks: block at all — append
136
- merged = existing.trimEnd() + '\n\n' + hooksBlock + '\n';
134
+ const merged = mergeHermesYaml(existing, hookScriptPath);
135
+ if (merged === null) {
136
+ log.warn({ action: 'hermes_config_merge_skipped', path: HERMES_CONFIG }, `${HERMES_CONFIG} could not be merged — left untouched`);
137
+ return;
137
138
  }
138
139
  const tmpPath = HERMES_CONFIG + '.intutic-tmp';
139
140
  await fs.writeFile(tmpPath, merged, 'utf-8');
@@ -156,7 +157,7 @@ Before every tool call, you MUST verify compliance with workspace SOPs.
156
157
  A pre-tool-use hook (\`~/.intutic/hooks/hermes-check.sh\`) enforces these rules automatically.
157
158
 
158
159
  If a tool call is blocked, do NOT attempt to circumvent the governance gate.
159
- To update policy, use the Intutic control plane at \`${proxyUrl}\`.
160
+ Policy is managed in Intutic; this agent's LLM traffic goes through the Intutic proxy at \`${proxyUrl}\`.
160
161
  `;
161
162
  }
162
163
  // ─── Main export ──────────────────────────────────────────────────────────────
@@ -1 +1 @@
1
- {"version":3,"file":"hermesHooks.js","sourceRoot":"","sources":["../../src/harness/hermesHooks.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"hermesHooks.js","sourceRoot":"","sources":["../../src/harness/hermesHooks.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,23 @@
1
+ /**
2
+ * jsonMergeTarget.ts — read a user-owned JSON config before merging into it.
3
+ *
4
+ * Every writer that adds Intutic keys to a file the user also edits (a
5
+ * harness's settings.json or hooks.json) used to treat a parse failure like a
6
+ * missing file and "start fresh" — so a single comment, trailing comma or
7
+ * half-saved edit made the next sync replace the user's whole file with the
8
+ * few keys Intutic owns. This helper separates the two cases: a missing file
9
+ * is an empty object, and a file that is present but not a plain JSON object
10
+ * is reported and left alone.
11
+ *
12
+ * @module
13
+ */
14
+ /**
15
+ * Read `filePath` as a JSON object to merge into.
16
+ *
17
+ * @returns the parsed object, `{}` when the file does not exist, or `null`
18
+ * when the file exists but is not a JSON object. On `null` the
19
+ * caller must skip its write; a warning naming the file has already
20
+ * been logged.
21
+ */
22
+ export declare function readJsonObjectForMerge(filePath: string): Promise<Record<string, unknown> | null>;
23
+ //# sourceMappingURL=jsonMergeTarget.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"jsonMergeTarget.d.ts","sourceRoot":"","sources":["../../src/harness/jsonMergeTarget.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAOH;;;;;;;GAOG;AACH,wBAAsB,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAAC,CAuBtG"}
@@ -0,0 +1,50 @@
1
+ /**
2
+ * jsonMergeTarget.ts — read a user-owned JSON config before merging into it.
3
+ *
4
+ * Every writer that adds Intutic keys to a file the user also edits (a
5
+ * harness's settings.json or hooks.json) used to treat a parse failure like a
6
+ * missing file and "start fresh" — so a single comment, trailing comma or
7
+ * half-saved edit made the next sync replace the user's whole file with the
8
+ * few keys Intutic owns. This helper separates the two cases: a missing file
9
+ * is an empty object, and a file that is present but not a plain JSON object
10
+ * is reported and left alone.
11
+ *
12
+ * @module
13
+ */
14
+ import * as fs from 'node:fs/promises';
15
+ import { createLogger } from '@intutic/logger';
16
+ const log = createLogger('sync-json-merge');
17
+ /**
18
+ * Read `filePath` as a JSON object to merge into.
19
+ *
20
+ * @returns the parsed object, `{}` when the file does not exist, or `null`
21
+ * when the file exists but is not a JSON object. On `null` the
22
+ * caller must skip its write; a warning naming the file has already
23
+ * been logged.
24
+ */
25
+ export async function readJsonObjectForMerge(filePath) {
26
+ let raw;
27
+ try {
28
+ raw = await fs.readFile(filePath, 'utf-8');
29
+ }
30
+ catch (err) {
31
+ if (err.code === 'ENOENT')
32
+ return {};
33
+ log.warn({ action: 'config_merge_skipped', path: filePath, error: String(err) }, `Could not read ${filePath} — left untouched`);
34
+ return null;
35
+ }
36
+ if (raw.trim() === '')
37
+ return {};
38
+ try {
39
+ const parsed = JSON.parse(raw);
40
+ if (typeof parsed === 'object' && parsed !== null && !Array.isArray(parsed)) {
41
+ return parsed;
42
+ }
43
+ }
44
+ catch {
45
+ // Reported below with the not-an-object case.
46
+ }
47
+ log.warn({ action: 'config_merge_skipped', path: filePath }, `${filePath} is not a plain JSON object (comments, a trailing comma or a syntax error?) — left untouched; fix it and the next sync will add the Intutic entries`);
48
+ return null;
49
+ }
50
+ //# sourceMappingURL=jsonMergeTarget.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"jsonMergeTarget.js","sourceRoot":"","sources":["../../src/harness/jsonMergeTarget.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,MAAM,kBAAkB,CAAA;AACtC,OAAO,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAE9C,MAAM,GAAG,GAAG,YAAY,CAAC,iBAAiB,CAAC,CAAA;AAE3C;;;;;;;GAOG;AACH,MAAM,CAAC,KAAK,UAAU,sBAAsB,CAAC,QAAgB;IAC3D,IAAI,GAAW,CAAA;IACf,IAAI,CAAC;QACH,GAAG,GAAG,MAAM,EAAE,CAAC,QAAQ,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAA;IAC5C,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,IAAK,GAA6B,CAAC,IAAI,KAAK,QAAQ;YAAE,OAAO,EAAE,CAAA;QAC/D,GAAG,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,sBAAsB,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,CAAC,GAAG,CAAC,EAAE,EAAE,kBAAkB,QAAQ,mBAAmB,CAAC,CAAA;QAC/H,OAAO,IAAI,CAAA;IACb,CAAC;IACD,IAAI,GAAG,CAAC,IAAI,EAAE,KAAK,EAAE;QAAE,OAAO,EAAE,CAAA;IAChC,IAAI,CAAC;QACH,MAAM,MAAM,GAAY,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;QACvC,IAAI,OAAO,MAAM,KAAK,QAAQ,IAAI,MAAM,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE,CAAC;YAC5E,OAAO,MAAiC,CAAA;QAC1C,CAAC;IACH,CAAC;IAAC,MAAM,CAAC;QACP,8CAA8C;IAChD,CAAC;IACD,GAAG,CAAC,IAAI,CACN,EAAE,MAAM,EAAE,sBAAsB,EAAE,IAAI,EAAE,QAAQ,EAAE,EAClD,GAAG,QAAQ,qJAAqJ,CACjK,CAAA;IACD,OAAO,IAAI,CAAA;AACb,CAAC"}
@@ -3,7 +3,8 @@
3
3
  * MCP servers with the @intutic/mcp-governance-proxy.
4
4
  *
5
5
  * Injects and proxy-wraps MCP server entries in:
6
- * - Claude Code: ~/.claude/mcp.json
6
+ * - Claude Code: ~/.claude.json (user-scope `mcpServers`, and the
7
+ * local-scope `projects[<workspaceRoot>].mcpServers`)
7
8
  * - Claude Desktop: ~/Library/Application Support/Claude/claude_desktop_config.json
8
9
  * - Cursor (global): ~/Library/Application Support/Cursor/User/globalSettings.json
9
10
  * - Cursor (project): <workspaceRoot>/.cursor/mcp.json
@@ -15,11 +16,14 @@
15
16
  * - Muse Code: ~/.config/muse/settings.json (`mcp_servers` section)
16
17
  * - Grok Build: ~/.grok/config.toml + <workspaceRoot>/.grok/config.toml
17
18
  * ([mcp_servers.*] tables)
19
+ * - OpenCode: ~/.config/opencode/opencode.json + <workspaceRoot>/opencode.json
20
+ * (`mcp` block — TD-487; see `injectOpenCode`)
18
21
  *
19
- * That is 12 config paths across 10 `HarnessType` values (Cursor and Grok
20
- * Build each own two paths — global/project for Cursor, user/project for
21
- * Grok Build). `discoverMcpServers` below reads all twelve read-only, for
22
- * reporting; the injectors above are the only thing that writes.
22
+ * That is 14 config paths across 11 `HarnessType` values (Cursor, Grok
23
+ * Build and OpenCode each own two paths — global/project for Cursor and
24
+ * OpenCode, user/project for Grok Build). `discoverMcpServers` below reads
25
+ * all fourteen read-only, for reporting; the injectors above are the only
26
+ * thing that writes.
23
27
  *
24
28
  * # Grok Build's compat-path overlap — dedup, not a bug
25
29
  *
@@ -92,9 +96,27 @@ export interface DiscoveredMcpServer {
92
96
  transport: 'stdio' | 'http' | 'sse' | 'unknown';
93
97
  wrapped: boolean;
94
98
  }
99
+ /**
100
+ * Resolve the path to the @intutic/mcp-governance-proxy entry point.
101
+ *
102
+ * Resolution order:
103
+ * 1. The copy installed next to this daemon — a dependency of
104
+ * `@intutic/sync-daemon`, so a global `npm install -g @intutic/cli` has it
105
+ * in the CLI's own node_modules. This is the normal case: the user's
106
+ * project has no reason to depend on the proxy.
107
+ * 2. `<workspaceRoot>/node_modules/@intutic/mcp-governance-proxy/dist/index.js`
108
+ * and `<workspaceRoot>/packages/mcp-proxy/dist/index.js` — for a run from
109
+ * a bundled binary, whose bundled modules are not on disk for `node` to
110
+ * load (their paths start with `/snapshot/`), and for a source checkout
111
+ * that has not built the proxy yet.
112
+ *
113
+ * Synchronous on purpose — this runs while building config entries, not in a
114
+ * hot path.
115
+ */
116
+ export declare function resolveProxyBin(workspaceRoot: string): string;
95
117
  /**
96
118
  * Discover every MCP server declared in any harness config this daemon knows
97
- * how to parse — the same 12 config paths / 10 harnesses `injectMcpServer`
119
+ * how to parse — the same 14 config paths / 11 harnesses `injectMcpServer`
98
120
  * wraps — without writing anything. Used for reporting (agentReporter's
99
121
  * `mcp_tools` facet) so visibility does not silently lag behind whatever
100
122
  * `injectMcpServer` was last run against.
@@ -1 +1 @@
1
- {"version":3,"file":"mcpAutoWrite.d.ts","sourceRoot":"","sources":["../../src/harness/mcpAutoWrite.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqFG;AAoDH;gEACgE;AAChE,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,MAAM,CAAA;IACd,OAAO,EAAE,MAAM,CAAA;IACf,SAAS,EAAE,OAAO,GAAG,MAAM,GAAG,KAAK,GAAG,SAAS,CAAA;IAC/C,OAAO,EAAE,OAAO,CAAA;CACjB;AAw7BD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAsB,kBAAkB,CAAC,aAAa,EAAE,MAAM,GAAG,OAAO,CAAC,mBAAmB,EAAE,CAAC,CAe9F;AAID;;;;;;;;;;;;;;;GAeG;AACH,wBAAsB,eAAe,CAAC,aAAa,EAAE,MAAM,EAAE,WAAW,SAAY,GAAG,OAAO,CAAC,IAAI,CAAC,CA2BnG"}
1
+ {"version":3,"file":"mcpAutoWrite.d.ts","sourceRoot":"","sources":["../../src/harness/mcpAutoWrite.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAyFG;AAsDH;gEACgE;AAChE,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,MAAM,CAAA;IACd,OAAO,EAAE,MAAM,CAAA;IACf,SAAS,EAAE,OAAO,GAAG,MAAM,GAAG,KAAK,GAAG,SAAS,CAAA;IAC/C,OAAO,EAAE,OAAO,CAAA;CACjB;AAQD;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,eAAe,CAAC,aAAa,EAAE,MAAM,GAAG,MAAM,CAc7D;AAopCD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAsB,kBAAkB,CAAC,aAAa,EAAE,MAAM,GAAG,OAAO,CAAC,mBAAmB,EAAE,CAAC,CAgB9F;AAID;;;;;;;;;;;;;;;GAeG;AACH,wBAAsB,eAAe,CAAC,aAAa,EAAE,MAAM,EAAE,WAAW,SAAY,GAAG,OAAO,CAAC,IAAI,CAAC,CA6BnG"}