nowaikit 3.0.0 → 4.0.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.
- package/LICENSE +10 -10
- package/README.md +8 -6
- package/desktop/renderer/dist/assets/index-D46KUWoj.js +49 -0
- package/desktop/renderer/dist/index.html +5 -5
- package/desktop/serve.cjs +134 -10
- package/dist/a2a/agent-card.d.ts +8 -0
- package/dist/a2a/agent-card.d.ts.map +1 -0
- package/dist/a2a/agent-card.js +82 -0
- package/dist/a2a/agent-card.js.map +1 -0
- package/dist/a2a/index.d.ts +13 -0
- package/dist/a2a/index.d.ts.map +1 -0
- package/dist/a2a/index.js +74 -0
- package/dist/a2a/index.js.map +1 -0
- package/dist/a2a/task-manager.d.ts +20 -0
- package/dist/a2a/task-manager.d.ts.map +1 -0
- package/dist/a2a/task-manager.js +148 -0
- package/dist/a2a/task-manager.js.map +1 -0
- package/dist/a2a/types.d.ts +73 -0
- package/dist/a2a/types.d.ts.map +1 -0
- package/dist/a2a/types.js +6 -0
- package/dist/a2a/types.js.map +1 -0
- package/dist/api/index.d.ts +16 -0
- package/dist/api/index.d.ts.map +1 -0
- package/dist/api/index.js +106 -0
- package/dist/api/index.js.map +1 -0
- package/dist/cli/config-store.d.ts +31 -0
- package/dist/cli/config-store.d.ts.map +1 -1
- package/dist/cli/config-store.js +44 -1
- package/dist/cli/config-store.js.map +1 -1
- package/dist/cli/index.js +115 -9
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/setup.d.ts.map +1 -1
- package/dist/cli/setup.js +669 -49
- package/dist/cli/setup.js.map +1 -1
- package/dist/cli/shortcuts.d.ts +2 -0
- package/dist/cli/shortcuts.d.ts.map +1 -0
- package/dist/cli/shortcuts.js +122 -0
- package/dist/cli/shortcuts.js.map +1 -0
- package/dist/dashboard/index.d.ts +7 -0
- package/dist/dashboard/index.d.ts.map +1 -0
- package/dist/dashboard/index.js +111 -0
- package/dist/dashboard/index.js.map +1 -0
- package/dist/direct/llm-client.d.ts +1 -1
- package/dist/direct/llm-client.d.ts.map +1 -1
- package/dist/direct/llm-client.js +9 -4
- package/dist/direct/llm-client.js.map +1 -1
- package/dist/prompts/capabilities/build-app.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-app.js +2 -0
- package/dist/prompts/capabilities/build-app.js.map +1 -1
- package/dist/prompts/capabilities/build-atf-suite.d.ts +4 -0
- package/dist/prompts/capabilities/build-atf-suite.d.ts.map +1 -0
- package/dist/prompts/capabilities/build-atf-suite.js +143 -0
- package/dist/prompts/capabilities/build-atf-suite.js.map +1 -0
- package/dist/prompts/capabilities/build-business-rule.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-business-rule.js +2 -0
- package/dist/prompts/capabilities/build-business-rule.js.map +1 -1
- package/dist/prompts/capabilities/build-catalog.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-catalog.js +2 -0
- package/dist/prompts/capabilities/build-catalog.js.map +1 -1
- package/dist/prompts/capabilities/build-client-script.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-client-script.js +2 -0
- package/dist/prompts/capabilities/build-client-script.js.map +1 -1
- package/dist/prompts/capabilities/build-flow.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-flow.js +2 -0
- package/dist/prompts/capabilities/build-flow.js.map +1 -1
- package/dist/prompts/capabilities/build-portal.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-portal.js +2 -0
- package/dist/prompts/capabilities/build-portal.js.map +1 -1
- package/dist/prompts/capabilities/build-rest-api.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-rest-api.js +2 -0
- package/dist/prompts/capabilities/build-rest-api.js.map +1 -1
- package/dist/prompts/capabilities/build-test-plan.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-test-plan.js +2 -0
- package/dist/prompts/capabilities/build-test-plan.js.map +1 -1
- package/dist/prompts/capabilities/build-uib.d.ts.map +1 -1
- package/dist/prompts/capabilities/build-uib.js +2 -0
- package/dist/prompts/capabilities/build-uib.js.map +1 -1
- package/dist/prompts/capabilities/docs-app.d.ts.map +1 -1
- package/dist/prompts/capabilities/docs-app.js +2 -0
- package/dist/prompts/capabilities/docs-app.js.map +1 -1
- package/dist/prompts/capabilities/docs-release.d.ts.map +1 -1
- package/dist/prompts/capabilities/docs-release.js +2 -0
- package/dist/prompts/capabilities/docs-release.js.map +1 -1
- package/dist/prompts/capabilities/docs-runbook.d.ts.map +1 -1
- package/dist/prompts/capabilities/docs-runbook.js +2 -0
- package/dist/prompts/capabilities/docs-runbook.js.map +1 -1
- package/dist/prompts/capabilities/docs-script.d.ts.map +1 -1
- package/dist/prompts/capabilities/docs-script.js +2 -0
- package/dist/prompts/capabilities/docs-script.js.map +1 -1
- package/dist/prompts/capabilities/ops-deploy.d.ts.map +1 -1
- package/dist/prompts/capabilities/ops-deploy.js +2 -0
- package/dist/prompts/capabilities/ops-deploy.js.map +1 -1
- package/dist/prompts/capabilities/ops-risk.d.ts.map +1 -1
- package/dist/prompts/capabilities/ops-risk.js +2 -0
- package/dist/prompts/capabilities/ops-risk.js.map +1 -1
- package/dist/prompts/capabilities/ops-triage.d.ts.map +1 -1
- package/dist/prompts/capabilities/ops-triage.js +2 -0
- package/dist/prompts/capabilities/ops-triage.js.map +1 -1
- package/dist/prompts/capabilities/review-acls.d.ts.map +1 -1
- package/dist/prompts/capabilities/review-acls.js +2 -0
- package/dist/prompts/capabilities/review-acls.js.map +1 -1
- package/dist/prompts/capabilities/review-code.d.ts.map +1 -1
- package/dist/prompts/capabilities/review-code.js +2 -0
- package/dist/prompts/capabilities/review-code.js.map +1 -1
- package/dist/prompts/capabilities/review-flows.d.ts.map +1 -1
- package/dist/prompts/capabilities/review-flows.js +2 -0
- package/dist/prompts/capabilities/review-flows.js.map +1 -1
- package/dist/prompts/capabilities/review-scripts.d.ts.map +1 -1
- package/dist/prompts/capabilities/review-scripts.js +2 -0
- package/dist/prompts/capabilities/review-scripts.js.map +1 -1
- package/dist/prompts/capabilities/scan-automation.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-automation.js +2 -0
- package/dist/prompts/capabilities/scan-automation.js.map +1 -1
- package/dist/prompts/capabilities/scan-cmdb.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-cmdb.js +2 -0
- package/dist/prompts/capabilities/scan-cmdb.js.map +1 -1
- package/dist/prompts/capabilities/scan-debt.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-debt.js +2 -0
- package/dist/prompts/capabilities/scan-debt.js.map +1 -1
- package/dist/prompts/capabilities/scan-health.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-health.js +2 -0
- package/dist/prompts/capabilities/scan-health.js.map +1 -1
- package/dist/prompts/capabilities/scan-security.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-security.js +2 -0
- package/dist/prompts/capabilities/scan-security.js.map +1 -1
- package/dist/prompts/capabilities/scan-upgrade.d.ts.map +1 -1
- package/dist/prompts/capabilities/scan-upgrade.js +2 -0
- package/dist/prompts/capabilities/scan-upgrade.js.map +1 -1
- package/dist/prompts/index.d.ts.map +1 -1
- package/dist/prompts/index.js +47 -8
- package/dist/prompts/index.js.map +1 -1
- package/dist/reports/brand.d.ts +79 -0
- package/dist/reports/brand.d.ts.map +1 -0
- package/dist/reports/brand.js +204 -0
- package/dist/reports/brand.js.map +1 -0
- package/dist/reports/charts.d.ts +11 -0
- package/dist/reports/charts.d.ts.map +1 -0
- package/dist/reports/charts.js +91 -0
- package/dist/reports/charts.js.map +1 -0
- package/dist/reports/index.d.ts +13 -0
- package/dist/reports/index.d.ts.map +1 -0
- package/dist/reports/index.js +65 -0
- package/dist/reports/index.js.map +1 -0
- package/dist/reports/parser.d.ts +13 -0
- package/dist/reports/parser.d.ts.map +1 -0
- package/dist/reports/parser.js +202 -0
- package/dist/reports/parser.js.map +1 -0
- package/dist/reports/pdf-generator.d.ts +8 -0
- package/dist/reports/pdf-generator.d.ts.map +1 -0
- package/dist/reports/pdf-generator.js +244 -0
- package/dist/reports/pdf-generator.js.map +1 -0
- package/dist/reports/pptx-generator.d.ts +8 -0
- package/dist/reports/pptx-generator.d.ts.map +1 -0
- package/dist/reports/pptx-generator.js +273 -0
- package/dist/reports/pptx-generator.js.map +1 -0
- package/dist/reports/types.d.ts +60 -0
- package/dist/reports/types.d.ts.map +1 -0
- package/dist/reports/types.js +7 -0
- package/dist/reports/types.js.map +1 -0
- package/dist/resources/index.d.ts.map +1 -1
- package/dist/resources/index.js +10 -0
- package/dist/resources/index.js.map +1 -1
- package/dist/resources/query-syntax.d.ts +6 -0
- package/dist/resources/query-syntax.d.ts.map +1 -0
- package/dist/resources/query-syntax.js +113 -0
- package/dist/resources/query-syntax.js.map +1 -0
- package/dist/sdk/index.d.ts +51 -0
- package/dist/sdk/index.d.ts.map +1 -0
- package/dist/sdk/index.js +55 -0
- package/dist/sdk/index.js.map +1 -0
- package/dist/server.d.ts +2 -1
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +103 -92
- package/dist/server.js.map +1 -1
- package/dist/servicenow/client.js +1 -1
- package/dist/servicenow/client.js.map +1 -1
- package/dist/tools/ai-agents.d.ts +145 -0
- package/dist/tools/ai-agents.d.ts.map +1 -0
- package/dist/tools/ai-agents.js +185 -0
- package/dist/tools/ai-agents.js.map +1 -0
- package/dist/tools/cmdb-reconciliation.d.ts +112 -0
- package/dist/tools/cmdb-reconciliation.d.ts.map +1 -0
- package/dist/tools/cmdb-reconciliation.js +267 -0
- package/dist/tools/cmdb-reconciliation.js.map +1 -0
- package/dist/tools/discovery.d.ts +34 -0
- package/dist/tools/discovery.d.ts.map +1 -0
- package/dist/tools/discovery.js +168 -0
- package/dist/tools/discovery.js.map +1 -0
- package/dist/tools/fluent.d.ts +105 -11
- package/dist/tools/fluent.d.ts.map +1 -1
- package/dist/tools/fluent.js +118 -1
- package/dist/tools/fluent.js.map +1 -1
- package/dist/tools/index.d.ts +840 -0
- package/dist/tools/index.d.ts.map +1 -1
- package/dist/tools/index.js +44 -6
- package/dist/tools/index.js.map +1 -1
- package/dist/tools/ml.d.ts +104 -0
- package/dist/tools/ml.d.ts.map +1 -1
- package/dist/tools/ml.js +139 -0
- package/dist/tools/ml.js.map +1 -1
- package/dist/tools/now-assist-skills.d.ts +129 -0
- package/dist/tools/now-assist-skills.d.ts.map +1 -0
- package/dist/tools/now-assist-skills.js +128 -0
- package/dist/tools/now-assist-skills.js.map +1 -0
- package/dist/tools/orchestration.d.ts +132 -0
- package/dist/tools/orchestration.d.ts.map +1 -0
- package/dist/tools/orchestration.js +320 -0
- package/dist/tools/orchestration.js.map +1 -0
- package/dist/tools/reporting.d.ts +127 -1
- package/dist/tools/reporting.d.ts.map +1 -1
- package/dist/tools/reporting.js +64 -0
- package/dist/tools/reporting.js.map +1 -1
- package/dist/tools/schema-cache.d.ts +44 -0
- package/dist/tools/schema-cache.d.ts.map +1 -0
- package/dist/tools/schema-cache.js +127 -0
- package/dist/tools/schema-cache.js.map +1 -0
- package/dist/tools-manifest.json +1250 -25
- package/dist/transport/auth-middleware.d.ts +16 -0
- package/dist/transport/auth-middleware.d.ts.map +1 -0
- package/dist/transport/auth-middleware.js +31 -0
- package/dist/transport/auth-middleware.js.map +1 -0
- package/dist/transport/http-server.d.ts +44 -0
- package/dist/transport/http-server.d.ts.map +1 -0
- package/dist/transport/http-server.js +172 -0
- package/dist/transport/http-server.js.map +1 -0
- package/dist/transport/index.d.ts +19 -0
- package/dist/transport/index.d.ts.map +1 -0
- package/dist/transport/index.js +105 -0
- package/dist/transport/index.js.map +1 -0
- package/dist/utils/permissions.d.ts +2 -0
- package/dist/utils/permissions.d.ts.map +1 -1
- package/dist/utils/permissions.js +8 -0
- package/dist/utils/permissions.js.map +1 -1
- package/package.json +27 -4
- package/desktop/renderer/dist/assets/index-B-6BYnh8.js +0 -49
|
@@ -4,13 +4,13 @@
|
|
|
4
4
|
<meta charset="UTF-8" />
|
|
5
5
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
6
6
|
<title>NowAIKit</title>
|
|
7
|
-
<link rel="icon" type="image/svg+xml" href="
|
|
8
|
-
<link rel="icon" type="image/png" sizes="32x32" href="
|
|
9
|
-
<link rel="apple-touch-icon" sizes="180x180" href="
|
|
7
|
+
<link rel="icon" type="image/svg+xml" href="/favicon.svg" />
|
|
8
|
+
<link rel="icon" type="image/png" sizes="32x32" href="/favicon-32.png" />
|
|
9
|
+
<link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png" />
|
|
10
10
|
<!-- CSP: script-src unsafe-inline needed for Vite HMR in dev; style-src unsafe-inline needed for React inline styles -->
|
|
11
11
|
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; connect-src 'self' https://*.service-now.com https://*.servicenowservices.com https://generativelanguage.googleapis.com ws://localhost:* http://localhost:*; img-src 'self' data:; frame-ancestors 'none'; form-action 'self';" />
|
|
12
|
-
<script type="module" crossorigin src="
|
|
13
|
-
<link rel="stylesheet" crossorigin href="
|
|
12
|
+
<script type="module" crossorigin src="/assets/index-D46KUWoj.js"></script>
|
|
13
|
+
<link rel="stylesheet" crossorigin href="/assets/index-Bb0ncZQl.css">
|
|
14
14
|
</head>
|
|
15
15
|
<body>
|
|
16
16
|
<div id="root"></div>
|
package/desktop/serve.cjs
CHANGED
|
@@ -56,11 +56,13 @@ const MIME = {
|
|
|
56
56
|
// ─── AI provider proxy config ────────────────────────────────────────────────
|
|
57
57
|
|
|
58
58
|
const AI_PROXIES = {
|
|
59
|
-
'/api/ai/anthropic':
|
|
60
|
-
'/api/ai/openai':
|
|
61
|
-
'/api/ai/google':
|
|
62
|
-
'/api/ai/groq':
|
|
63
|
-
'/api/ai/openrouter': { target: 'https://openrouter.ai',
|
|
59
|
+
'/api/ai/anthropic': { target: 'https://api.anthropic.com', strip: '/api/ai/anthropic' },
|
|
60
|
+
'/api/ai/openai': { target: 'https://api.openai.com', strip: '/api/ai/openai' },
|
|
61
|
+
'/api/ai/google': { target: 'https://generativelanguage.googleapis.com', strip: '/api/ai/google' },
|
|
62
|
+
'/api/ai/groq': { target: 'https://api.groq.com', strip: '/api/ai/groq' },
|
|
63
|
+
'/api/ai/openrouter': { target: 'https://openrouter.ai', strip: '/api/ai/openrouter' },
|
|
64
|
+
'/api/ai/ollama': { target: 'http://localhost:11434', strip: '/api/ai/ollama' },
|
|
65
|
+
'/api/ai/lmstudio': { target: 'http://localhost:1234', strip: '/api/ai/lmstudio' },
|
|
64
66
|
};
|
|
65
67
|
|
|
66
68
|
// Headers that are safe to forward to upstream AI providers
|
|
@@ -159,9 +161,11 @@ function proxyRequest(req, res, proxyConfig) {
|
|
|
159
161
|
}
|
|
160
162
|
}
|
|
161
163
|
|
|
164
|
+
const isTargetHttps = target.protocol === 'https:';
|
|
165
|
+
const mod = isTargetHttps ? https : http;
|
|
162
166
|
const options = {
|
|
163
167
|
hostname: target.hostname,
|
|
164
|
-
port: 443,
|
|
168
|
+
port: isTargetHttps ? 443 : (parseInt(target.port, 10) || 80),
|
|
165
169
|
path: target.pathname + target.search,
|
|
166
170
|
method: req.method,
|
|
167
171
|
headers,
|
|
@@ -170,7 +174,7 @@ function proxyRequest(req, res, proxyConfig) {
|
|
|
170
174
|
const origin = req.headers.origin;
|
|
171
175
|
const allowedOrigin = isAllowedOrigin(origin) ? (origin || '*') : '';
|
|
172
176
|
|
|
173
|
-
const proxyReq =
|
|
177
|
+
const proxyReq = mod.request(options, (proxyRes) => {
|
|
174
178
|
// Set CORS headers for the allowed origin
|
|
175
179
|
if (allowedOrigin) {
|
|
176
180
|
res.setHeader('Access-Control-Allow-Origin', allowedOrigin);
|
|
@@ -370,6 +374,87 @@ function serveStatic(req, res) {
|
|
|
370
374
|
});
|
|
371
375
|
}
|
|
372
376
|
|
|
377
|
+
// ─── Report generation handler ───────────────────────────────────────────────
|
|
378
|
+
|
|
379
|
+
/**
|
|
380
|
+
* POST /api/report/generate
|
|
381
|
+
* Body: { markdown, format, title, instanceUrl, instanceName, capability }
|
|
382
|
+
* Returns: binary file with appropriate Content-Type
|
|
383
|
+
*/
|
|
384
|
+
function handleReportGenerate(req, res) {
|
|
385
|
+
const chunks = [];
|
|
386
|
+
let totalSize = 0;
|
|
387
|
+
const MAX_BODY = 10 * 1024 * 1024;
|
|
388
|
+
|
|
389
|
+
req.on('data', chunk => {
|
|
390
|
+
totalSize += chunk.length;
|
|
391
|
+
if (totalSize > MAX_BODY) {
|
|
392
|
+
res.writeHead(413, { 'Content-Type': 'application/json' });
|
|
393
|
+
res.end(JSON.stringify({ error: 'Request body too large' }));
|
|
394
|
+
req.destroy();
|
|
395
|
+
return;
|
|
396
|
+
}
|
|
397
|
+
chunks.push(chunk);
|
|
398
|
+
});
|
|
399
|
+
|
|
400
|
+
req.on('end', async () => {
|
|
401
|
+
if (totalSize > MAX_BODY) return;
|
|
402
|
+
|
|
403
|
+
try {
|
|
404
|
+
const body = JSON.parse(Buffer.concat(chunks).toString());
|
|
405
|
+
const { markdown, format, title, instanceUrl, instanceName, capability } = body;
|
|
406
|
+
|
|
407
|
+
if (!markdown || !format || !title) {
|
|
408
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
409
|
+
res.end(JSON.stringify({ error: 'markdown, format, and title are required' }));
|
|
410
|
+
return;
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
if (format !== 'pdf' && format !== 'pptx') {
|
|
414
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
415
|
+
res.end(JSON.stringify({ error: 'format must be "pdf" or "pptx"' }));
|
|
416
|
+
return;
|
|
417
|
+
}
|
|
418
|
+
|
|
419
|
+
// Dynamic import of the report module (ESM from CJS)
|
|
420
|
+
const reportModule = await import(path.resolve(__dirname, '..', 'dist', 'reports', 'index.js'));
|
|
421
|
+
const result = await reportModule.generateReport(markdown, format, {
|
|
422
|
+
title,
|
|
423
|
+
instanceUrl: instanceUrl || '',
|
|
424
|
+
instanceName: instanceName || 'instance',
|
|
425
|
+
capability: capability || '',
|
|
426
|
+
});
|
|
427
|
+
|
|
428
|
+
// Read generated file and send it
|
|
429
|
+
const fileBuffer = fs.readFileSync(result.filePath);
|
|
430
|
+
const contentType = format === 'pdf' ? 'application/pdf' : 'application/vnd.openxmlformats-officedocument.presentationml.presentation';
|
|
431
|
+
const fileName = path.basename(result.filePath);
|
|
432
|
+
|
|
433
|
+
const origin = req.headers.origin;
|
|
434
|
+
const allowedOrigin = isAllowedOrigin(origin) ? (origin || '*') : '';
|
|
435
|
+
|
|
436
|
+
const headers = {
|
|
437
|
+
'Content-Type': contentType,
|
|
438
|
+
'Content-Disposition': `attachment; filename="${fileName}"`,
|
|
439
|
+
'Content-Length': fileBuffer.length,
|
|
440
|
+
};
|
|
441
|
+
if (allowedOrigin) {
|
|
442
|
+
headers['Access-Control-Allow-Origin'] = allowedOrigin;
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
res.writeHead(200, headers);
|
|
446
|
+
res.end(fileBuffer);
|
|
447
|
+
|
|
448
|
+
// Cleanup temp file
|
|
449
|
+
try { fs.unlinkSync(result.filePath); } catch { /* ignore */ }
|
|
450
|
+
} catch (err) {
|
|
451
|
+
console.error('Report generation error:', err.message || err);
|
|
452
|
+
res.writeHead(500, { 'Content-Type': 'application/json' });
|
|
453
|
+
res.end(JSON.stringify({ error: 'Report generation failed: ' + (err.message || 'unknown error') }));
|
|
454
|
+
}
|
|
455
|
+
});
|
|
456
|
+
}
|
|
457
|
+
|
|
373
458
|
// ─── HTTP server ─────────────────────────────────────────────────────────────
|
|
374
459
|
|
|
375
460
|
const server = http.createServer((req, res) => {
|
|
@@ -430,16 +515,36 @@ const server = http.createServer((req, res) => {
|
|
|
430
515
|
return;
|
|
431
516
|
}
|
|
432
517
|
|
|
518
|
+
// Report generation endpoint
|
|
519
|
+
if (req.url === '/api/report/generate' && req.method === 'POST') {
|
|
520
|
+
if (!proxySecurityCheck()) return;
|
|
521
|
+
handleReportGenerate(req, res);
|
|
522
|
+
return;
|
|
523
|
+
}
|
|
524
|
+
|
|
433
525
|
// Serve static files
|
|
434
526
|
serveStatic(req, res);
|
|
435
527
|
});
|
|
436
528
|
|
|
437
|
-
|
|
529
|
+
// Try preferred port, fall back to alternatives if busy
|
|
530
|
+
const FALLBACK_PORTS = [PORT, PORT + 1, PORT + 2, PORT + 3, PORT + 10, 0];
|
|
531
|
+
let portIndex = 0;
|
|
532
|
+
|
|
533
|
+
function tryListen() {
|
|
534
|
+
const tryPort = FALLBACK_PORTS[portIndex];
|
|
535
|
+
server.listen(tryPort, HOST);
|
|
536
|
+
}
|
|
537
|
+
|
|
538
|
+
server.on('listening', () => {
|
|
539
|
+
const actualPort = server.address().port;
|
|
540
|
+
if (actualPort !== PORT) {
|
|
541
|
+
console.log(`\n ⚠ Port ${PORT} was in use, using port ${actualPort} instead.`);
|
|
542
|
+
}
|
|
438
543
|
console.log(`\n NowAIKit Web Server`);
|
|
439
544
|
console.log(` ───────────────────────────────`);
|
|
440
|
-
console.log(` Local: http://localhost:${
|
|
545
|
+
console.log(` Local: http://localhost:${actualPort}`);
|
|
441
546
|
if (HOST !== '127.0.0.1' && HOST !== 'localhost') {
|
|
442
|
-
console.log(` Network: http://${HOST}:${
|
|
547
|
+
console.log(` Network: http://${HOST}:${actualPort}`);
|
|
443
548
|
}
|
|
444
549
|
console.log(`\n AI proxy: /api/ai/* -> provider APIs (CORS proxied)`);
|
|
445
550
|
console.log(` Snow proxy: /api/snow/* -> ServiceNow instances (CORS proxied)`);
|
|
@@ -447,3 +552,22 @@ server.listen(PORT, HOST, () => {
|
|
|
447
552
|
console.log(`\n All AI providers + ServiceNow instances supported.`);
|
|
448
553
|
console.log(` Press Ctrl+C to stop.\n`);
|
|
449
554
|
});
|
|
555
|
+
|
|
556
|
+
server.on('error', (err) => {
|
|
557
|
+
if (err.code === 'EADDRINUSE') {
|
|
558
|
+
portIndex++;
|
|
559
|
+
if (portIndex < FALLBACK_PORTS.length) {
|
|
560
|
+
const next = FALLBACK_PORTS[portIndex] || 'random';
|
|
561
|
+
console.log(` Port ${FALLBACK_PORTS[portIndex - 1]} is in use, trying ${next}…`);
|
|
562
|
+
tryListen();
|
|
563
|
+
} else {
|
|
564
|
+
console.error(` ✕ All ports are in use. Set PORT=<number> to specify a port.`);
|
|
565
|
+
process.exit(1);
|
|
566
|
+
}
|
|
567
|
+
} else {
|
|
568
|
+
console.error(` ✕ Server error: ${err.message}`);
|
|
569
|
+
process.exit(1);
|
|
570
|
+
}
|
|
571
|
+
});
|
|
572
|
+
|
|
573
|
+
tryListen();
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A2A Agent Card generator — exposes NowAIKit capabilities as an A2A agent.
|
|
3
|
+
* Maps MCP tool domains to A2A skills.
|
|
4
|
+
*/
|
|
5
|
+
import type { AgentCard } from './types.js';
|
|
6
|
+
/** Build agent card from current tool definitions. */
|
|
7
|
+
export declare function buildAgentCard(): AgentCard;
|
|
8
|
+
//# sourceMappingURL=agent-card.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"agent-card.d.ts","sourceRoot":"","sources":["../../src/a2a/agent-card.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,EAAE,SAAS,EAAc,MAAM,YAAY,CAAC;AA4BxD,sDAAsD;AACtD,wBAAgB,cAAc,IAAI,SAAS,CAyC1C"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import { getTools } from '../tools/index.js';
|
|
2
|
+
import { isAuthRequired } from '../transport/auth-middleware.js';
|
|
3
|
+
/** Categorize tools into skills by domain prefix. */
|
|
4
|
+
const DOMAIN_MAP = {
|
|
5
|
+
incident: { name: 'Incident Management', description: 'Create, update, resolve, and close incidents. Triage P1/P2 issues.', tags: ['itsm', 'incident'] },
|
|
6
|
+
problem: { name: 'Problem Management', description: 'Create and manage problem records, find root causes.', tags: ['itsm', 'problem'] },
|
|
7
|
+
change: { name: 'Change Management', description: 'Create, approve, and manage change requests. Risk assessment and CAB.', tags: ['itsm', 'change'] },
|
|
8
|
+
knowledge: { name: 'Knowledge Management', description: 'Search, create, and publish knowledge articles.', tags: ['knowledge', 'kb'] },
|
|
9
|
+
catalog: { name: 'Service Catalog', description: 'Browse, manage, and order catalog items.', tags: ['catalog', 'request'] },
|
|
10
|
+
cmdb: { name: 'CMDB Management', description: 'Search CIs, view relationships, health dashboards, reconciliation.', tags: ['cmdb', 'itom'] },
|
|
11
|
+
security: { name: 'Security Operations', description: 'Manage security incidents, vulnerabilities, compliance, GRC risks.', tags: ['secops', 'security', 'grc'] },
|
|
12
|
+
hrsd: { name: 'HR Service Delivery', description: 'HR cases, onboarding, offboarding, employee lifecycle.', tags: ['hrsd', 'hr'] },
|
|
13
|
+
csm: { name: 'Customer Service Management', description: 'CSM cases, accounts, contacts, SLAs.', tags: ['csm', 'customer'] },
|
|
14
|
+
flow: { name: 'Flow Designer', description: 'Create and manage flows, subflows, and process automations.', tags: ['flow', 'automation'] },
|
|
15
|
+
script: { name: 'Platform Scripting', description: 'Business rules, script includes, client scripts, ACLs.', tags: ['scripting', 'development'] },
|
|
16
|
+
ml: { name: 'Machine Learning', description: 'Anomaly detection, change risk prediction, incident forecasting.', tags: ['ml', 'ai'] },
|
|
17
|
+
atf: { name: 'Automated Testing', description: 'ATF test suites, test execution, failure analysis.', tags: ['testing', 'atf'] },
|
|
18
|
+
devops: { name: 'DevOps', description: 'Pipelines, deployments, DevOps insights.', tags: ['devops', 'cicd'] },
|
|
19
|
+
report: { name: 'Reporting & Analytics', description: 'Generate reports, dashboards, KPIs, trend analysis.', tags: ['reporting', 'analytics'] },
|
|
20
|
+
fluent: { name: 'Fluent Query & SDK', description: 'GlideQuery-style queries, batch operations, now-sdk integration.', tags: ['fluent', 'query', 'sdk'] },
|
|
21
|
+
now_assist: { name: 'Now Assist Skills', description: 'Create, manage, and test Now Assist AI skills.', tags: ['now-assist', 'ai', 'skills'] },
|
|
22
|
+
ai_agent: { name: 'AI Agents', description: 'Create and manage AI agents with automatic ACL generation.', tags: ['ai-agent', 'aiaf'] },
|
|
23
|
+
orchestration: { name: 'Multi-Agent Orchestration', description: 'Create and execute multi-step playbooks chaining tools.', tags: ['orchestration', 'playbook'] },
|
|
24
|
+
discover: { name: 'Schema Discovery', description: 'Discover table schemas and generate dynamic CRUD tools.', tags: ['discovery', 'schema'] },
|
|
25
|
+
};
|
|
26
|
+
/** Build agent card from current tool definitions. */
|
|
27
|
+
export function buildAgentCard() {
|
|
28
|
+
const tools = getTools();
|
|
29
|
+
const baseUrl = `http://${process.env.HOST || 'localhost'}:${process.env.PORT || '3000'}`;
|
|
30
|
+
// Group tools by domain
|
|
31
|
+
const skillMap = new Map();
|
|
32
|
+
for (const tool of tools) {
|
|
33
|
+
const prefix = getDomainPrefix(tool.name);
|
|
34
|
+
if (!skillMap.has(prefix))
|
|
35
|
+
skillMap.set(prefix, []);
|
|
36
|
+
skillMap.get(prefix).push(tool.name);
|
|
37
|
+
}
|
|
38
|
+
// Convert to A2A skills
|
|
39
|
+
const skills = [];
|
|
40
|
+
for (const [prefix, toolNames] of skillMap) {
|
|
41
|
+
const domain = DOMAIN_MAP[prefix] || { name: capitalize(prefix), description: `${capitalize(prefix)} tools`, tags: [prefix] };
|
|
42
|
+
skills.push({
|
|
43
|
+
id: `nowaikit-${prefix}`,
|
|
44
|
+
name: domain.name,
|
|
45
|
+
description: `${domain.description} (${toolNames.length} tools)`,
|
|
46
|
+
tags: domain.tags,
|
|
47
|
+
});
|
|
48
|
+
}
|
|
49
|
+
return {
|
|
50
|
+
name: 'NowAIKit',
|
|
51
|
+
description: 'The most comprehensive ServiceNow AI toolkit — 400+ tools covering ITSM, CMDB, HRSD, CSM, SecOps, GRC, DevOps, and more.',
|
|
52
|
+
url: baseUrl,
|
|
53
|
+
version: '4.0.0',
|
|
54
|
+
capabilities: {
|
|
55
|
+
streaming: true,
|
|
56
|
+
pushNotifications: false,
|
|
57
|
+
stateTransitionHistory: true,
|
|
58
|
+
},
|
|
59
|
+
authentication: {
|
|
60
|
+
schemes: isAuthRequired() ? ['bearer'] : [],
|
|
61
|
+
},
|
|
62
|
+
defaultInputModes: ['text'],
|
|
63
|
+
defaultOutputModes: ['text', 'data'],
|
|
64
|
+
skills,
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
function getDomainPrefix(toolName) {
|
|
68
|
+
// Match known prefixes
|
|
69
|
+
for (const prefix of Object.keys(DOMAIN_MAP)) {
|
|
70
|
+
if (toolName.startsWith(prefix + '_') || toolName.startsWith(prefix))
|
|
71
|
+
return prefix;
|
|
72
|
+
}
|
|
73
|
+
// Generic tools
|
|
74
|
+
if (['query_records', 'get_record', 'create_record', 'update_record', 'delete_record', 'get_table_schema', 'get_user', 'get_group'].includes(toolName))
|
|
75
|
+
return 'core';
|
|
76
|
+
// Fallback: use first word
|
|
77
|
+
return toolName.split('_')[0];
|
|
78
|
+
}
|
|
79
|
+
function capitalize(s) {
|
|
80
|
+
return s.charAt(0).toUpperCase() + s.slice(1);
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=agent-card.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"agent-card.js","sourceRoot":"","sources":["../../src/a2a/agent-card.ts"],"names":[],"mappings":"AAKA,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEjE,qDAAqD;AACrD,MAAM,UAAU,GAA0E;IACxF,QAAQ,EAAE,EAAE,IAAI,EAAE,qBAAqB,EAAE,WAAW,EAAE,oEAAoE,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,UAAU,CAAC,EAAE;IACxJ,OAAO,EAAE,EAAE,IAAI,EAAE,oBAAoB,EAAE,WAAW,EAAE,sDAAsD,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,SAAS,CAAC,EAAE;IACvI,MAAM,EAAE,EAAE,IAAI,EAAE,mBAAmB,EAAE,WAAW,EAAE,uEAAuE,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,QAAQ,CAAC,EAAE;IACrJ,SAAS,EAAE,EAAE,IAAI,EAAE,sBAAsB,EAAE,WAAW,EAAE,iDAAiD,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,IAAI,CAAC,EAAE;IACtI,OAAO,EAAE,EAAE,IAAI,EAAE,iBAAiB,EAAE,WAAW,EAAE,0CAA0C,EAAE,IAAI,EAAE,CAAC,SAAS,EAAE,SAAS,CAAC,EAAE;IAC3H,IAAI,EAAE,EAAE,IAAI,EAAE,iBAAiB,EAAE,WAAW,EAAE,oEAAoE,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,EAAE;IAC5I,QAAQ,EAAE,EAAE,IAAI,EAAE,qBAAqB,EAAE,WAAW,EAAE,oEAAoE,EAAE,IAAI,EAAE,CAAC,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,EAAE;IACjK,IAAI,EAAE,EAAE,IAAI,EAAE,qBAAqB,EAAE,WAAW,EAAE,wDAAwD,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,IAAI,CAAC,EAAE;IAClI,GAAG,EAAE,EAAE,IAAI,EAAE,6BAA6B,EAAE,WAAW,EAAE,sCAAsC,EAAE,IAAI,EAAE,CAAC,KAAK,EAAE,UAAU,CAAC,EAAE;IAC5H,IAAI,EAAE,EAAE,IAAI,EAAE,eAAe,EAAE,WAAW,EAAE,6DAA6D,EAAE,IAAI,EAAE,CAAC,MAAM,EAAE,YAAY,CAAC,EAAE;IACzI,MAAM,EAAE,EAAE,IAAI,EAAE,oBAAoB,EAAE,WAAW,EAAE,wDAAwD,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,aAAa,CAAC,EAAE;IACjJ,EAAE,EAAE,EAAE,IAAI,EAAE,kBAAkB,EAAE,WAAW,EAAE,kEAAkE,EAAE,IAAI,EAAE,CAAC,IAAI,EAAE,IAAI,CAAC,EAAE;IACrI,GAAG,EAAE,EAAE,IAAI,EAAE,mBAAmB,EAAE,WAAW,EAAE,oDAAoD,EAAE,IAAI,EAAE,CAAC,SAAS,EAAE,KAAK,CAAC,EAAE;IAC/H,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,0CAA0C,EAAE,IAAI,EAAE,CAAC,QAAQ,EAAE,MAAM,CAAC,EAAE;IAC7G,MAAM,EAAE,EAAE,IAAI,EAAE,uBAAuB,EAAE,WAAW,EAAE,qDAAqD,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,WAAW,CAAC,EAAE;IAC/I,MAAM,EAAE,EAAE,IAAI,EAAE,oBAAoB,EAAE,WAAW,EAAE,kEAAkE,EAAE,IAAI,EAAE,CAAC,QAAQ,EAAE,OAAO,EAAE,KAAK,CAAC,EAAE;IACzJ,UAAU,EAAE,EAAE,IAAI,EAAE,mBAAmB,EAAE,WAAW,EAAE,gDAAgD,EAAE,IAAI,EAAE,CAAC,YAAY,EAAE,IAAI,EAAE,QAAQ,CAAC,EAAE;IAC9I,QAAQ,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE,WAAW,EAAE,4DAA4D,EAAE,IAAI,EAAE,CAAC,UAAU,EAAE,MAAM,CAAC,EAAE;IACtI,aAAa,EAAE,EAAE,IAAI,EAAE,2BAA2B,EAAE,WAAW,EAAE,yDAAyD,EAAE,IAAI,EAAE,CAAC,eAAe,EAAE,UAAU,CAAC,EAAE;IACjK,QAAQ,EAAE,EAAE,IAAI,EAAE,kBAAkB,EAAE,WAAW,EAAE,yDAAyD,EAAE,IAAI,EAAE,CAAC,WAAW,EAAE,QAAQ,CAAC,EAAE;CAC9I,CAAC;AAEF,sDAAsD;AACtD,MAAM,UAAU,cAAc;IAC5B,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;IACzB,MAAM,OAAO,GAAG,UAAU,OAAO,CAAC,GAAG,CAAC,IAAI,IAAI,WAAW,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,IAAI,MAAM,EAAE,CAAC;IAE1F,wBAAwB;IACxB,MAAM,QAAQ,GAAG,IAAI,GAAG,EAAoB,CAAC;IAC7C,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC1C,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,MAAM,CAAC;YAAE,QAAQ,CAAC,GAAG,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC;QACpD,QAAQ,CAAC,GAAG,CAAC,MAAM,CAAE,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACxC,CAAC;IAED,wBAAwB;IACxB,MAAM,MAAM,GAAiB,EAAE,CAAC;IAChC,KAAK,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,IAAI,QAAQ,EAAE,CAAC;QAC3C,MAAM,MAAM,GAAG,UAAU,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,EAAE,UAAU,CAAC,MAAM,CAAC,EAAE,WAAW,EAAE,GAAG,UAAU,CAAC,MAAM,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,MAAM,CAAC,EAAE,CAAC;QAC9H,MAAM,CAAC,IAAI,CAAC;YACV,EAAE,EAAE,YAAY,MAAM,EAAE;YACxB,IAAI,EAAE,MAAM,CAAC,IAAI;YACjB,WAAW,EAAE,GAAG,MAAM,CAAC,WAAW,KAAK,SAAS,CAAC,MAAM,SAAS;YAChE,IAAI,EAAE,MAAM,CAAC,IAAI;SAClB,CAAC,CAAC;IACL,CAAC;IAED,OAAO;QACL,IAAI,EAAE,UAAU;QAChB,WAAW,EAAE,0HAA0H;QACvI,GAAG,EAAE,OAAO;QACZ,OAAO,EAAE,OAAO;QAChB,YAAY,EAAE;YACZ,SAAS,EAAE,IAAI;YACf,iBAAiB,EAAE,KAAK;YACxB,sBAAsB,EAAE,IAAI;SAC7B;QACD,cAAc,EAAE;YACd,OAAO,EAAE,cAAc,EAAE,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,EAAE;SAC5C;QACD,iBAAiB,EAAE,CAAC,MAAM,CAAC;QAC3B,kBAAkB,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC;QACpC,MAAM;KACP,CAAC;AACJ,CAAC;AAED,SAAS,eAAe,CAAC,QAAgB;IACvC,uBAAuB;IACvB,KAAK,MAAM,MAAM,IAAI,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,EAAE,CAAC;QAC7C,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,GAAG,GAAG,CAAC,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,CAAC;YAAE,OAAO,MAAM,CAAC;IACtF,CAAC;IACD,gBAAgB;IAChB,IAAI,CAAC,eAAe,EAAE,YAAY,EAAE,eAAe,EAAE,eAAe,EAAE,eAAe,EAAE,kBAAkB,EAAE,UAAU,EAAE,WAAW,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC;QAAE,OAAO,MAAM,CAAC;IACtK,2BAA2B;IAC3B,OAAO,QAAQ,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAE,CAAC;AACjC,CAAC;AAED,SAAS,UAAU,CAAC,CAAS;IAC3B,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,WAAW,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;AAChD,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A2A Protocol routes — mount on the HTTP server.
|
|
3
|
+
*
|
|
4
|
+
* Endpoints:
|
|
5
|
+
* GET /.well-known/agent.json — Agent card (no auth)
|
|
6
|
+
* POST /a2a/tasks/send — Send a task (synchronous)
|
|
7
|
+
* POST /a2a/tasks/sendSubscribe — Send a task (SSE streaming)
|
|
8
|
+
* GET /a2a/tasks/:taskId — Get task status
|
|
9
|
+
* POST /a2a/tasks/:taskId/cancel — Cancel a task
|
|
10
|
+
*/
|
|
11
|
+
import type { NowAIKitHttpServer } from '../transport/http-server.js';
|
|
12
|
+
export declare function mountA2ARoutes(httpServer: NowAIKitHttpServer): void;
|
|
13
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/a2a/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AACH,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,6BAA6B,CAAC;AAKtE,wBAAgB,cAAc,CAAC,UAAU,EAAE,kBAAkB,GAAG,IAAI,CAoFnE"}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { buildAgentCard } from './agent-card.js';
|
|
2
|
+
import { taskManager } from './task-manager.js';
|
|
3
|
+
export function mountA2ARoutes(httpServer) {
|
|
4
|
+
// Agent card — no auth required for discovery
|
|
5
|
+
httpServer.get('/.well-known/agent.json', async (_req, res) => {
|
|
6
|
+
const card = buildAgentCard();
|
|
7
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
8
|
+
res.end(JSON.stringify(card, null, 2));
|
|
9
|
+
}, false);
|
|
10
|
+
// Send task (synchronous)
|
|
11
|
+
httpServer.post('/a2a/tasks/send', async (req, res) => {
|
|
12
|
+
const body = req.body;
|
|
13
|
+
if (!body?.message?.parts?.length) {
|
|
14
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
15
|
+
res.end(JSON.stringify({ error: 'Missing message with parts' }));
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
const result = await taskManager.sendTask(body);
|
|
19
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
20
|
+
res.end(JSON.stringify(result));
|
|
21
|
+
});
|
|
22
|
+
// Send task with SSE streaming
|
|
23
|
+
httpServer.post('/a2a/tasks/sendSubscribe', async (req, res) => {
|
|
24
|
+
const body = req.body;
|
|
25
|
+
if (!body?.message?.parts?.length) {
|
|
26
|
+
res.writeHead(400, { 'Content-Type': 'application/json' });
|
|
27
|
+
res.end(JSON.stringify({ error: 'Missing message with parts' }));
|
|
28
|
+
return;
|
|
29
|
+
}
|
|
30
|
+
// Set up SSE
|
|
31
|
+
res.writeHead(200, {
|
|
32
|
+
'Content-Type': 'text/event-stream',
|
|
33
|
+
'Cache-Control': 'no-cache',
|
|
34
|
+
'Connection': 'keep-alive',
|
|
35
|
+
});
|
|
36
|
+
// Send working status
|
|
37
|
+
const { randomUUID } = await import('crypto');
|
|
38
|
+
const taskId = body.id || randomUUID();
|
|
39
|
+
res.write(`event: task-status-update\ndata: ${JSON.stringify({ id: taskId, status: { state: 'working', timestamp: new Date().toISOString() } })}\n\n`);
|
|
40
|
+
// Execute
|
|
41
|
+
const result = await taskManager.sendTask({ ...body, id: taskId });
|
|
42
|
+
// Send result
|
|
43
|
+
if (result.artifacts?.length) {
|
|
44
|
+
res.write(`event: task-artifact-update\ndata: ${JSON.stringify({ id: taskId, artifact: result.artifacts[0] })}\n\n`);
|
|
45
|
+
}
|
|
46
|
+
res.write(`event: task-status-update\ndata: ${JSON.stringify({ id: taskId, status: result.status })}\n\n`);
|
|
47
|
+
res.end();
|
|
48
|
+
});
|
|
49
|
+
// Get task status
|
|
50
|
+
httpServer.get('/a2a/tasks/:taskId', async (req, res) => {
|
|
51
|
+
const taskId = req.params.taskId;
|
|
52
|
+
const task = taskManager.getTask(taskId);
|
|
53
|
+
if (!task) {
|
|
54
|
+
res.writeHead(404, { 'Content-Type': 'application/json' });
|
|
55
|
+
res.end(JSON.stringify({ error: 'Task not found' }));
|
|
56
|
+
return;
|
|
57
|
+
}
|
|
58
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
59
|
+
res.end(JSON.stringify(task));
|
|
60
|
+
});
|
|
61
|
+
// Cancel task
|
|
62
|
+
httpServer.post('/a2a/tasks/:taskId/cancel', async (req, res) => {
|
|
63
|
+
const taskId = req.params.taskId;
|
|
64
|
+
const success = taskManager.cancelTask(taskId);
|
|
65
|
+
if (!success) {
|
|
66
|
+
res.writeHead(404, { 'Content-Type': 'application/json' });
|
|
67
|
+
res.end(JSON.stringify({ error: 'Task not found or already completed' }));
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
71
|
+
res.end(JSON.stringify({ id: taskId, status: { state: 'canceled' } }));
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/a2a/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { Task, SendTaskRequest, SendTaskResponse } from './types.js';
|
|
2
|
+
declare class TaskManager {
|
|
3
|
+
private tasks;
|
|
4
|
+
/** Send a task synchronously — execute and return the result. */
|
|
5
|
+
sendTask(request: SendTaskRequest): Promise<SendTaskResponse>;
|
|
6
|
+
/** Get a task by ID. */
|
|
7
|
+
getTask(taskId: string): Task | undefined;
|
|
8
|
+
/** Cancel a task. */
|
|
9
|
+
cancelTask(taskId: string): boolean;
|
|
10
|
+
/**
|
|
11
|
+
* Parse an A2A message to determine which tool to call.
|
|
12
|
+
* Strategy: look for tool name in the text, or match keywords to tools.
|
|
13
|
+
*/
|
|
14
|
+
private parseMessage;
|
|
15
|
+
private extractArgsFromText;
|
|
16
|
+
private getHelpText;
|
|
17
|
+
}
|
|
18
|
+
export declare const taskManager: TaskManager;
|
|
19
|
+
export {};
|
|
20
|
+
//# sourceMappingURL=task-manager.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"task-manager.d.ts","sourceRoot":"","sources":["../../src/a2a/task-manager.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,IAAI,EAAE,eAAe,EAAE,gBAAgB,EAAyC,MAAM,YAAY,CAAC;AAKjH,cAAM,WAAW;IACf,OAAO,CAAC,KAAK,CAA2B;IAExC,iEAAiE;IAC3D,QAAQ,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAqEnE,wBAAwB;IACxB,OAAO,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS;IAIzC,qBAAqB;IACrB,UAAU,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO;IAUnC;;;OAGG;IACH,OAAO,CAAC,YAAY;IAiCpB,OAAO,CAAC,mBAAmB;IAa3B,OAAO,CAAC,WAAW;CASpB;AAED,eAAO,MAAM,WAAW,aAAoB,CAAC"}
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A2A Task Manager — handles the lifecycle of A2A tasks.
|
|
3
|
+
* Maps incoming A2A messages to NowAIKit tool invocations.
|
|
4
|
+
*/
|
|
5
|
+
import { randomUUID } from 'crypto';
|
|
6
|
+
import { getTools, executeTool } from '../tools/index.js';
|
|
7
|
+
import { instanceManager } from '../servicenow/instances.js';
|
|
8
|
+
import { logger } from '../utils/logging.js';
|
|
9
|
+
class TaskManager {
|
|
10
|
+
tasks = new Map();
|
|
11
|
+
/** Send a task synchronously — execute and return the result. */
|
|
12
|
+
async sendTask(request) {
|
|
13
|
+
const taskId = request.id || randomUUID();
|
|
14
|
+
const sessionId = request.sessionId || randomUUID();
|
|
15
|
+
const task = {
|
|
16
|
+
id: taskId,
|
|
17
|
+
sessionId,
|
|
18
|
+
status: { state: 'submitted', timestamp: new Date().toISOString() },
|
|
19
|
+
history: [request.message],
|
|
20
|
+
artifacts: [],
|
|
21
|
+
};
|
|
22
|
+
this.tasks.set(taskId, task);
|
|
23
|
+
// Update to working
|
|
24
|
+
task.status = { state: 'working', timestamp: new Date().toISOString() };
|
|
25
|
+
try {
|
|
26
|
+
// Parse the message to determine tool and arguments
|
|
27
|
+
const { toolName, toolArgs } = this.parseMessage(request.message);
|
|
28
|
+
if (!toolName) {
|
|
29
|
+
// No specific tool found — return a helpful response
|
|
30
|
+
task.status = {
|
|
31
|
+
state: 'completed',
|
|
32
|
+
message: { role: 'agent', parts: [{ type: 'text', text: this.getHelpText() }] },
|
|
33
|
+
timestamp: new Date().toISOString(),
|
|
34
|
+
};
|
|
35
|
+
this.tasks.set(taskId, task);
|
|
36
|
+
return { id: taskId, sessionId, status: task.status };
|
|
37
|
+
}
|
|
38
|
+
// Execute the tool
|
|
39
|
+
const client = instanceManager.getClient();
|
|
40
|
+
const result = await executeTool(client, toolName, toolArgs);
|
|
41
|
+
const artifact = {
|
|
42
|
+
name: toolName,
|
|
43
|
+
description: `Result from ${toolName}`,
|
|
44
|
+
parts: [{ type: 'data', data: result, mimeType: 'application/json' }],
|
|
45
|
+
index: 0,
|
|
46
|
+
};
|
|
47
|
+
task.artifacts = [artifact];
|
|
48
|
+
task.status = {
|
|
49
|
+
state: 'completed',
|
|
50
|
+
message: {
|
|
51
|
+
role: 'agent',
|
|
52
|
+
parts: [
|
|
53
|
+
{ type: 'text', text: typeof result === 'string' ? result : JSON.stringify(result, null, 2) },
|
|
54
|
+
],
|
|
55
|
+
},
|
|
56
|
+
timestamp: new Date().toISOString(),
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
catch (error) {
|
|
60
|
+
logger.error(`A2A task failed: ${taskId}`, error);
|
|
61
|
+
task.status = {
|
|
62
|
+
state: 'failed',
|
|
63
|
+
message: {
|
|
64
|
+
role: 'agent',
|
|
65
|
+
parts: [{ type: 'text', text: `Error: ${error instanceof Error ? error.message : 'Unknown error'}` }],
|
|
66
|
+
},
|
|
67
|
+
timestamp: new Date().toISOString(),
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
this.tasks.set(taskId, task);
|
|
71
|
+
return { id: taskId, sessionId, status: task.status, artifacts: task.artifacts };
|
|
72
|
+
}
|
|
73
|
+
/** Get a task by ID. */
|
|
74
|
+
getTask(taskId) {
|
|
75
|
+
return this.tasks.get(taskId);
|
|
76
|
+
}
|
|
77
|
+
/** Cancel a task. */
|
|
78
|
+
cancelTask(taskId) {
|
|
79
|
+
const task = this.tasks.get(taskId);
|
|
80
|
+
if (!task)
|
|
81
|
+
return false;
|
|
82
|
+
if (task.status.state === 'completed' || task.status.state === 'failed')
|
|
83
|
+
return false;
|
|
84
|
+
task.status = { state: 'canceled', timestamp: new Date().toISOString() };
|
|
85
|
+
this.tasks.set(taskId, task);
|
|
86
|
+
return true;
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Parse an A2A message to determine which tool to call.
|
|
90
|
+
* Strategy: look for tool name in the text, or match keywords to tools.
|
|
91
|
+
*/
|
|
92
|
+
parseMessage(message) {
|
|
93
|
+
const tools = getTools();
|
|
94
|
+
const textParts = message.parts.filter(p => p.type === 'text');
|
|
95
|
+
const dataParts = message.parts.filter(p => p.type === 'data');
|
|
96
|
+
const text = textParts.map(p => p.text).join(' ').toLowerCase();
|
|
97
|
+
// Check if data part contains explicit tool name and args
|
|
98
|
+
for (const part of dataParts) {
|
|
99
|
+
if (part.data && typeof part.data === 'object') {
|
|
100
|
+
const data = part.data;
|
|
101
|
+
if (data.tool_name && tools.find(t => t.name === data.tool_name)) {
|
|
102
|
+
return { toolName: data.tool_name, toolArgs: data.arguments || {} };
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
// Try exact tool name match in text
|
|
107
|
+
for (const tool of tools) {
|
|
108
|
+
if (text.includes(tool.name)) {
|
|
109
|
+
return { toolName: tool.name, toolArgs: this.extractArgsFromText(text, tool.name) };
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
// Keyword matching for common operations
|
|
113
|
+
if (text.includes('incident') && (text.includes('create') || text.includes('new')))
|
|
114
|
+
return { toolName: 'create_incident', toolArgs: {} };
|
|
115
|
+
if (text.includes('incident') && text.includes('list'))
|
|
116
|
+
return { toolName: 'query_records', toolArgs: { table: 'incident', query: 'active=true', limit: 20 } };
|
|
117
|
+
if (text.includes('change') && text.includes('list'))
|
|
118
|
+
return { toolName: 'list_change_requests', toolArgs: {} };
|
|
119
|
+
if (text.includes('knowledge') && text.includes('search'))
|
|
120
|
+
return { toolName: 'search_knowledge', toolArgs: { query: text } };
|
|
121
|
+
if (text.includes('cmdb') && text.includes('health'))
|
|
122
|
+
return { toolName: 'cmdb_health_dashboard', toolArgs: {} };
|
|
123
|
+
return { toolName: null, toolArgs: {} };
|
|
124
|
+
}
|
|
125
|
+
extractArgsFromText(text, _toolName) {
|
|
126
|
+
// Simple extraction — look for key=value patterns
|
|
127
|
+
const args = {};
|
|
128
|
+
const kvPattern = /(\w+)\s*[=:]\s*["']?([^"',\s]+)["']?/g;
|
|
129
|
+
let match;
|
|
130
|
+
while ((match = kvPattern.exec(text)) !== null) {
|
|
131
|
+
if (match[1] !== _toolName.split('_')[0]) {
|
|
132
|
+
args[match[1]] = match[2];
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
return args;
|
|
136
|
+
}
|
|
137
|
+
getHelpText() {
|
|
138
|
+
const tools = getTools();
|
|
139
|
+
return `I'm NowAIKit, a ServiceNow AI agent with ${tools.length}+ tools. ` +
|
|
140
|
+
`You can send me tasks like:\n` +
|
|
141
|
+
`- "List active incidents"\n` +
|
|
142
|
+
`- "Search knowledge for VPN setup"\n` +
|
|
143
|
+
`- "CMDB health dashboard"\n` +
|
|
144
|
+
`- Or specify a tool directly: { "tool_name": "query_records", "arguments": { "table": "incident" } }`;
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
export const taskManager = new TaskManager();
|
|
148
|
+
//# sourceMappingURL=task-manager.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"task-manager.js","sourceRoot":"","sources":["../../src/a2a/task-manager.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,QAAQ,CAAC;AAEpC,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAC1D,OAAO,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAC;AAC7D,OAAO,EAAE,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAE7C,MAAM,WAAW;IACP,KAAK,GAAG,IAAI,GAAG,EAAgB,CAAC;IAExC,iEAAiE;IACjE,KAAK,CAAC,QAAQ,CAAC,OAAwB;QACrC,MAAM,MAAM,GAAG,OAAO,CAAC,EAAE,IAAI,UAAU,EAAE,CAAC;QAC1C,MAAM,SAAS,GAAG,OAAO,CAAC,SAAS,IAAI,UAAU,EAAE,CAAC;QAEpD,MAAM,IAAI,GAAS;YACjB,EAAE,EAAE,MAAM;YACV,SAAS;YACT,MAAM,EAAE,EAAE,KAAK,EAAE,WAAW,EAAE,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EAAE;YACnE,OAAO,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC;YAC1B,SAAS,EAAE,EAAE;SACd,CAAC;QACF,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QAE7B,oBAAoB;QACpB,IAAI,CAAC,MAAM,GAAG,EAAE,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EAAE,CAAC;QAExE,IAAI,CAAC;YACH,oDAAoD;YACpD,MAAM,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;YAElE,IAAI,CAAC,QAAQ,EAAE,CAAC;gBACd,qDAAqD;gBACrD,IAAI,CAAC,MAAM,GAAG;oBACZ,KAAK,EAAE,WAAW;oBAClB,OAAO,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,WAAW,EAAE,EAAE,CAAC,EAAE;oBAC/E,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;iBACpC,CAAC;gBACF,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;gBAC7B,OAAO,EAAE,EAAE,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,CAAC;YACxD,CAAC;YAED,mBAAmB;YACnB,MAAM,MAAM,GAAG,eAAe,CAAC,SAAS,EAAE,CAAC;YAC3C,MAAM,MAAM,GAAG,MAAM,WAAW,CAAC,MAAM,EAAE,QAAQ,EAAE,QAAQ,CAAC,CAAC;YAE7D,MAAM,QAAQ,GAAa;gBACzB,IAAI,EAAE,QAAQ;gBACd,WAAW,EAAE,eAAe,QAAQ,EAAE;gBACtC,KAAK,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,kBAAkB,EAAc,CAAC;gBACjF,KAAK,EAAE,CAAC;aACT,CAAC;YACF,IAAI,CAAC,SAAS,GAAG,CAAC,QAAQ,CAAC,CAAC;YAE5B,IAAI,CAAC,MAAM,GAAG;gBACZ,KAAK,EAAE,WAAW;gBAClB,OAAO,EAAE;oBACP,IAAI,EAAE,OAAO;oBACb,KAAK,EAAE;wBACL,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,MAAM,KAAK,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,EAAc;qBAC1G;iBACF;gBACD,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;aACpC,CAAC;QACJ,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,CAAC,KAAK,CAAC,oBAAoB,MAAM,EAAE,EAAE,KAAK,CAAC,CAAC;YAClD,IAAI,CAAC,MAAM,GAAG;gBACZ,KAAK,EAAE,QAAQ;gBACf,OAAO,EAAE;oBACP,IAAI,EAAE,OAAO;oBACb,KAAK,EAAE,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,UAAU,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,eAAe,EAAE,EAAc,CAAC;iBAClH;gBACD,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;aACpC,CAAC;QACJ,CAAC;QAED,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QAC7B,OAAO,EAAE,EAAE,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,CAAC;IACnF,CAAC;IAED,wBAAwB;IACxB,OAAO,CAAC,MAAc;QACpB,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IAChC,CAAC;IAED,qBAAqB;IACrB,UAAU,CAAC,MAAc;QACvB,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;QACpC,IAAI,CAAC,IAAI;YAAE,OAAO,KAAK,CAAC;QACxB,IAAI,IAAI,CAAC,MAAM,CAAC,KAAK,KAAK,WAAW,IAAI,IAAI,CAAC,MAAM,CAAC,KAAK,KAAK,QAAQ;YAAE,OAAO,KAAK,CAAC;QAEtF,IAAI,CAAC,MAAM,GAAG,EAAE,KAAK,EAAE,UAAU,EAAE,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EAAE,CAAC;QACzE,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QAC7B,OAAO,IAAI,CAAC;IACd,CAAC;IAED;;;OAGG;IACK,YAAY,CAAC,OAAgB;QACnC,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;QACzB,MAAM,SAAS,GAAG,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,MAAM,CAAe,CAAC;QAC7E,MAAM,SAAS,GAAG,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,MAAM,CAAe,CAAC;QAC7E,MAAM,IAAI,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;QAEhE,0DAA0D;QAC1D,KAAK,MAAM,IAAI,IAAI,SAAS,EAAE,CAAC;YAC7B,IAAI,IAAI,CAAC,IAAI,IAAI,OAAO,IAAI,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;gBAC/C,MAAM,IAAI,GAAG,IAAI,CAAC,IAA2B,CAAC;gBAC9C,IAAI,IAAI,CAAC,SAAS,IAAI,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,SAAS,CAAC,EAAE,CAAC;oBACjE,OAAO,EAAE,QAAQ,EAAE,IAAI,CAAC,SAAS,EAAE,QAAQ,EAAE,IAAI,CAAC,SAAS,IAAI,EAAE,EAAE,CAAC;gBACtE,CAAC;YACH,CAAC;QACH,CAAC;QAED,oCAAoC;QACpC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;YACzB,IAAI,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;gBAC7B,OAAO,EAAE,QAAQ,EAAE,IAAI,CAAC,IAAI,EAAE,QAAQ,EAAE,IAAI,CAAC,mBAAmB,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;YACtF,CAAC;QACH,CAAC;QAED,yCAAyC;QACzC,IAAI,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;YAAE,OAAO,EAAE,QAAQ,EAAE,iBAAiB,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;QACzI,IAAI,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC;YAAE,OAAO,EAAE,QAAQ,EAAE,eAAe,EAAE,QAAQ,EAAE,EAAE,KAAK,EAAE,UAAU,EAAE,KAAK,EAAE,aAAa,EAAE,KAAK,EAAE,EAAE,EAAE,EAAE,CAAC;QAC/J,IAAI,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC;YAAE,OAAO,EAAE,QAAQ,EAAE,sBAAsB,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;QAChH,IAAI,IAAI,CAAC,QAAQ,CAAC,WAAW,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC;YAAE,OAAO,EAAE,QAAQ,EAAE,kBAAkB,EAAE,QAAQ,EAAE,EAAE,KAAK,EAAE,IAAI,EAAE,EAAE,CAAC;QAC9H,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,IAAI,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC;YAAE,OAAO,EAAE,QAAQ,EAAE,uBAAuB,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;QAEjH,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,QAAQ,EAAE,EAAE,EAAE,CAAC;IAC1C,CAAC;IAEO,mBAAmB,CAAC,IAAY,EAAE,SAAiB;QACzD,kDAAkD;QAClD,MAAM,IAAI,GAAwB,EAAE,CAAC;QACrC,MAAM,SAAS,GAAG,uCAAuC,CAAC;QAC1D,IAAI,KAAK,CAAC;QACV,OAAO,CAAC,KAAK,GAAG,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,KAAK,IAAI,EAAE,CAAC;YAC/C,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,SAAS,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;gBACzC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAE,CAAC,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;YAC7B,CAAC;QACH,CAAC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAEO,WAAW;QACjB,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;QACzB,OAAO,4CAA4C,KAAK,CAAC,MAAM,WAAW;YACxE,+BAA+B;YAC/B,6BAA6B;YAC7B,sCAAsC;YACtC,6BAA6B;YAC7B,sGAAsG,CAAC;IAC3G,CAAC;CACF;AAED,MAAM,CAAC,MAAM,WAAW,GAAG,IAAI,WAAW,EAAE,CAAC"}
|