@poolzin/pool-bot 2026.3.7 → 2026.3.10

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 (150) hide show
  1. package/CHANGELOG.md +40 -0
  2. package/README.md +147 -69
  3. package/dist/.buildstamp +1 -1
  4. package/dist/agents/error-classifier.js +251 -0
  5. package/dist/agents/skills/security.js +211 -0
  6. package/dist/build-info.json +3 -3
  7. package/dist/cli/cron-cli/register.cron-dashboard.js +339 -0
  8. package/dist/cli/cron-cli/register.js +2 -0
  9. package/dist/cli/errors.js +187 -0
  10. package/dist/cli/lazy-commands.example.js +113 -0
  11. package/dist/cli/lazy-commands.js +329 -0
  12. package/dist/cli/program/command-registry.js +26 -0
  13. package/dist/cli/program/register.maintenance.js +21 -0
  14. package/dist/cli/program/register.skills.js +4 -0
  15. package/dist/cli/program/register.subclis.js +9 -0
  16. package/dist/cli/swarm-cli/register.js +8 -0
  17. package/dist/cli/swarm-cli/register.swarm-status.js +488 -0
  18. package/dist/cli/telemetry-cli/register.js +10 -0
  19. package/dist/cli/telemetry-cli/register.telemetry-alerts.js +176 -0
  20. package/dist/cli/telemetry-cli/register.telemetry-metrics.js +323 -0
  21. package/dist/cli/telemetry-cli/register.telemetry-status.js +179 -0
  22. package/dist/commands/doctor-checks.js +498 -0
  23. package/dist/config/config.js +1 -0
  24. package/dist/config/secrets-integration.js +88 -0
  25. package/dist/context-engine/index.js +33 -0
  26. package/dist/context-engine/legacy.js +179 -0
  27. package/dist/context-engine/registry.js +86 -0
  28. package/dist/context-engine/summarizing.js +290 -0
  29. package/dist/context-engine/types.js +7 -0
  30. package/dist/cron/service/timer.js +18 -0
  31. package/dist/gateway/protocol/index.js +5 -2
  32. package/dist/gateway/protocol/schema/error-codes.js +1 -0
  33. package/dist/gateway/protocol/schema/swarm.js +80 -0
  34. package/dist/gateway/protocol/schema.js +1 -0
  35. package/dist/gateway/server-close.js +4 -0
  36. package/dist/gateway/server-constants.js +1 -0
  37. package/dist/gateway/server-cron.js +29 -0
  38. package/dist/gateway/server-maintenance.js +35 -2
  39. package/dist/gateway/server-methods/swarm.js +58 -0
  40. package/dist/gateway/server-methods/telemetry.js +71 -0
  41. package/dist/gateway/server-methods-list.js +8 -0
  42. package/dist/gateway/server-methods.js +9 -2
  43. package/dist/gateway/server.impl.js +33 -16
  44. package/dist/infra/abort-pattern.js +106 -0
  45. package/dist/infra/retry.js +96 -0
  46. package/dist/secrets/index.js +28 -0
  47. package/dist/secrets/resolver.js +185 -0
  48. package/dist/secrets/runtime.js +142 -0
  49. package/dist/secrets/types.js +11 -0
  50. package/dist/security/dangerous-tools.js +80 -0
  51. package/dist/security/types.js +12 -0
  52. package/dist/skills/commands.js +333 -0
  53. package/dist/skills/index.js +164 -0
  54. package/dist/skills/loader.js +282 -0
  55. package/dist/skills/parser.js +446 -0
  56. package/dist/skills/registry.js +394 -0
  57. package/dist/skills/security.js +312 -0
  58. package/dist/skills/types.js +21 -0
  59. package/dist/swarm/service.js +247 -0
  60. package/dist/telemetry/alert-engine.js +258 -0
  61. package/dist/telemetry/cron-instrumentation.js +49 -0
  62. package/dist/telemetry/gateway-instrumentation.js +80 -0
  63. package/dist/telemetry/instrumentation.js +66 -0
  64. package/dist/telemetry/service.js +345 -0
  65. package/dist/test-utils/index.js +219 -0
  66. package/dist/tui/components/assistant-message.js +6 -2
  67. package/dist/tui/components/hyperlink-markdown.js +32 -0
  68. package/dist/tui/components/searchable-select-list.js +12 -1
  69. package/dist/tui/components/user-message.js +6 -2
  70. package/dist/tui/index.js +611 -0
  71. package/dist/tui/theme/theme-detection.js +226 -0
  72. package/dist/tui/tui-command-handlers.js +20 -0
  73. package/dist/tui/tui-formatters.js +4 -3
  74. package/dist/tui/utils/ctrl-c-handler.js +67 -0
  75. package/dist/tui/utils/osc8-hyperlinks.js +208 -0
  76. package/dist/tui/utils/safe-stop.js +180 -0
  77. package/dist/tui/utils/session-key-utils.js +81 -0
  78. package/dist/tui/utils/text-sanitization.js +284 -0
  79. package/dist/utils/lru-cache.js +116 -0
  80. package/dist/utils/performance.js +199 -0
  81. package/dist/utils/retry.js +240 -0
  82. package/docs/INTEGRATION_PLAN.md +475 -0
  83. package/docs/INTEGRATION_SUMMARY.md +215 -0
  84. package/docs/MELHORIAS_IMPLEMENTADAS.md +228 -0
  85. package/docs/MELHORIAS_PROFISSIONAIS.md +282 -0
  86. package/docs/PLANO_ACAO_TUI.md +357 -0
  87. package/docs/PROGRESSO_TUI.md +66 -0
  88. package/docs/RELATORIO_FINAL.md +217 -0
  89. package/docs/diagnostico-shell-completion.md +265 -0
  90. package/docs/features/advanced-memory.md +585 -0
  91. package/docs/features/discord-components-v2.md +277 -0
  92. package/docs/features/swarm.md +100 -0
  93. package/docs/features/telemetry.md +284 -0
  94. package/docs/integrations/HEXSTRIKE_PLAN.md +796 -0
  95. package/docs/integrations/INTEGRATION_PLAN.md +744 -0
  96. package/docs/integrations/PAGE_AGENT_PLAN.md +370 -0
  97. package/docs/integrations/XYOPS_PLAN.md +978 -0
  98. package/docs/models/provider-infrastructure.md +400 -0
  99. package/docs/security/exec-approvals.md +294 -0
  100. package/docs/skills/IMPLEMENTATION_SUMMARY.md +145 -0
  101. package/docs/skills/SKILL.md +524 -0
  102. package/docs/skills.md +405 -0
  103. package/extensions/bluebubbles/package.json +1 -1
  104. package/extensions/copilot-proxy/package.json +1 -1
  105. package/extensions/diagnostics-otel/package.json +1 -1
  106. package/extensions/discord/package.json +1 -1
  107. package/extensions/feishu/package.json +1 -1
  108. package/extensions/google-antigravity-auth/package.json +1 -1
  109. package/extensions/google-gemini-cli-auth/package.json +1 -1
  110. package/extensions/googlechat/package.json +1 -1
  111. package/extensions/hexstrike-bridge/README.md +119 -0
  112. package/extensions/hexstrike-bridge/index.test.ts +247 -0
  113. package/extensions/hexstrike-bridge/index.ts +487 -0
  114. package/extensions/hexstrike-bridge/package.json +17 -0
  115. package/extensions/imessage/package.json +1 -1
  116. package/extensions/irc/package.json +1 -1
  117. package/extensions/line/package.json +1 -1
  118. package/extensions/llm-task/package.json +1 -1
  119. package/extensions/lobster/package.json +1 -1
  120. package/extensions/matrix/CHANGELOG.md +5 -0
  121. package/extensions/matrix/package.json +1 -1
  122. package/extensions/mattermost/package.json +1 -1
  123. package/extensions/mcp-server/index.ts +14 -0
  124. package/extensions/mcp-server/package.json +11 -0
  125. package/extensions/mcp-server/src/service.ts +540 -0
  126. package/extensions/memory-core/package.json +1 -1
  127. package/extensions/memory-lancedb/package.json +1 -1
  128. package/extensions/minimax-portal-auth/package.json +1 -1
  129. package/extensions/msteams/CHANGELOG.md +5 -0
  130. package/extensions/msteams/package.json +1 -1
  131. package/extensions/nextcloud-talk/package.json +1 -1
  132. package/extensions/nostr/CHANGELOG.md +5 -0
  133. package/extensions/nostr/package.json +1 -1
  134. package/extensions/open-prose/package.json +1 -1
  135. package/extensions/openai-codex-auth/package.json +1 -1
  136. package/extensions/signal/package.json +1 -1
  137. package/extensions/slack/package.json +1 -1
  138. package/extensions/telegram/package.json +1 -1
  139. package/extensions/tlon/package.json +1 -1
  140. package/extensions/twitch/CHANGELOG.md +5 -0
  141. package/extensions/twitch/package.json +1 -1
  142. package/extensions/voice-call/CHANGELOG.md +5 -0
  143. package/extensions/voice-call/package.json +1 -1
  144. package/extensions/whatsapp/package.json +1 -1
  145. package/extensions/zalo/CHANGELOG.md +5 -0
  146. package/extensions/zalo/package.json +1 -1
  147. package/extensions/zalouser/CHANGELOG.md +5 -0
  148. package/extensions/zalouser/package.json +1 -1
  149. package/package.json +8 -1
  150. package/skills/example-skill/SKILL.md +195 -0
@@ -0,0 +1,487 @@
1
+ import type { PoolBotPluginApi, PoolBotPluginDefinition, PoolBotPluginConfigSchema } from "../../src/plugins/types.js";
2
+ import type { GatewayRequestHandlerOptions } from "../../src/gateway/server-methods/types.js";
3
+ import { ErrorCodes } from "../../src/gateway/protocol/schema/error-codes.js";
4
+ import { getGlobalTelemetryService } from "../../src/telemetry/service.js";
5
+ import { z } from "zod";
6
+
7
+ const HexStrikeConfigSchema = z.object({
8
+ baseUrl: z.string().default("http://localhost:8888"),
9
+ timeoutMs: z.number().default(300000),
10
+ maxConcurrentScans: z.number().default(3),
11
+ });
12
+
13
+ type HexStrikeConfig = z.infer<typeof HexStrikeConfigSchema>;
14
+
15
+ interface ScanJob {
16
+ id: string;
17
+ tool: string;
18
+ target: string;
19
+ status: "pending" | "running" | "completed" | "failed";
20
+ progress: number;
21
+ result?: unknown;
22
+ error?: string;
23
+ startedAt?: Date;
24
+ completedAt?: Date;
25
+ durationMs?: number;
26
+ }
27
+
28
+ interface HexStrikeTool {
29
+ name: string;
30
+ description: string;
31
+ category: string;
32
+ params: Array<{
33
+ name: string;
34
+ type: string;
35
+ required: boolean;
36
+ description: string;
37
+ }>;
38
+ }
39
+
40
+ class HexStrikeClient {
41
+ private config: HexStrikeConfig;
42
+ private activeScans = new Map<string, ScanJob>();
43
+ private metrics = {
44
+ totalScans: 0,
45
+ completedScans: 0,
46
+ failedScans: 0,
47
+ totalDurationMs: 0,
48
+ };
49
+
50
+ constructor(config: HexStrikeConfig) {
51
+ this.config = config;
52
+ }
53
+
54
+ private recordMetrics(job: ScanJob): void {
55
+ const telemetry = getGlobalTelemetryService();
56
+ if (!telemetry) return;
57
+
58
+ const duration = job.durationMs ?? 0;
59
+
60
+ telemetry.recordCounter("poolbot.security.scans_total", 1, {
61
+ tool: job.tool,
62
+ status: job.status,
63
+ });
64
+
65
+ if (duration > 0) {
66
+ telemetry.recordHistogram("poolbot.security.scan_duration_ms", duration, {
67
+ tool: job.tool,
68
+ });
69
+ }
70
+
71
+ if (job.status === "completed") {
72
+ this.metrics.completedScans++;
73
+ } else if (job.status === "failed") {
74
+ this.metrics.failedScans++;
75
+ telemetry.recordCounter("poolbot.security.scan_failures", 1, {
76
+ tool: job.tool,
77
+ error: job.error ? job.error.substring(0, 50) : "unknown",
78
+ });
79
+ }
80
+
81
+ this.metrics.totalScans++;
82
+ this.metrics.totalDurationMs += duration;
83
+ }
84
+
85
+ async listTools(): Promise<HexStrikeTool[]> {
86
+ const startTime = Date.now();
87
+ const telemetry = getGlobalTelemetryService();
88
+
89
+ try {
90
+ const response = await fetch(`${this.config.baseUrl}/api/tools`, {
91
+ method: "GET",
92
+ headers: { "Content-Type": "application/json" },
93
+ });
94
+
95
+ if (!response.ok) {
96
+ throw new Error(`HexStrike API error: ${response.status}`);
97
+ }
98
+
99
+ const data = await response.json();
100
+ const tools = data.tools || [];
101
+
102
+ telemetry?.recordCounter("poolbot.security.api_calls", 1, {
103
+ endpoint: "list_tools",
104
+ status: "success",
105
+ });
106
+
107
+ return tools;
108
+ } catch (error) {
109
+ telemetry?.recordCounter("poolbot.security.api_calls", 1, {
110
+ endpoint: "list_tools",
111
+ status: "error",
112
+ });
113
+ throw new Error(`Failed to list tools: ${String(error)}`);
114
+ } finally {
115
+ telemetry?.recordHistogram("poolbot.security.api_latency_ms", Date.now() - startTime, {
116
+ endpoint: "list_tools",
117
+ });
118
+ }
119
+ }
120
+
121
+ async executeTool(tool: string, params: Record<string, unknown>): Promise<ScanJob> {
122
+ const jobId = `scan-${Date.now()}-${Math.random().toString(36).slice(2, 7)}`;
123
+
124
+ const job: ScanJob = {
125
+ id: jobId,
126
+ tool,
127
+ target: typeof params.target === "string" ? params.target : typeof params.host === "string" ? params.host : typeof params.url === "string" ? params.url : "unknown",
128
+ status: "pending",
129
+ progress: 0,
130
+ };
131
+
132
+ this.activeScans.set(jobId, job);
133
+
134
+ const telemetry = getGlobalTelemetryService();
135
+ telemetry?.recordGauge("poolbot.security.active_scans", this.getActiveScanCount());
136
+
137
+ const startTime = Date.now();
138
+
139
+ try {
140
+ job.status = "running";
141
+ job.startedAt = new Date();
142
+
143
+ const response = await fetch(`${this.config.baseUrl}/api/scan`, {
144
+ method: "POST",
145
+ headers: { "Content-Type": "application/json" },
146
+ body: JSON.stringify({ tool, params }),
147
+ });
148
+
149
+ if (!response.ok) {
150
+ throw new Error(`Scan failed: ${response.status}`);
151
+ }
152
+
153
+ const result = await response.json();
154
+
155
+ job.status = "completed";
156
+ job.progress = 100;
157
+ job.result = result;
158
+ job.completedAt = new Date();
159
+ job.durationMs = Date.now() - startTime;
160
+
161
+ this.recordMetrics(job);
162
+
163
+ return job;
164
+ } catch (error) {
165
+ job.status = "failed";
166
+ job.error = String(error);
167
+ job.completedAt = new Date();
168
+ job.durationMs = Date.now() - startTime;
169
+
170
+ this.recordMetrics(job);
171
+
172
+ throw error;
173
+ } finally {
174
+ telemetry?.recordGauge("poolbot.security.active_scans", this.getActiveScanCount());
175
+ }
176
+ }
177
+
178
+ getJob(jobId: string): ScanJob | undefined {
179
+ return this.activeScans.get(jobId);
180
+ }
181
+
182
+ listJobs(): ScanJob[] {
183
+ return Array.from(this.activeScans.values());
184
+ }
185
+
186
+ getActiveScanCount(): number {
187
+ return Array.from(this.activeScans.values()).filter((j: ScanJob) => j.status === "running").length;
188
+ }
189
+
190
+ getMetrics() {
191
+ return { ...this.metrics };
192
+ }
193
+
194
+ async getHealth(): Promise<{ status: string; version?: string; latencyMs?: number }> {
195
+ const startTime = Date.now();
196
+
197
+ try {
198
+ const response = await fetch(`${this.config.baseUrl}/health`, {
199
+ method: "GET",
200
+ } as RequestInit);
201
+
202
+ const latencyMs = Date.now() - startTime;
203
+
204
+ if (!response.ok) {
205
+ return { status: "unhealthy", latencyMs };
206
+ }
207
+
208
+ const data = await response.json();
209
+ return { status: "healthy", version: data.version, latencyMs };
210
+ } catch {
211
+ return { status: "offline" };
212
+ }
213
+ }
214
+ }
215
+
216
+ // Wrap Zod schema to match PoolBotPluginConfigSchema
217
+ const configSchema: PoolBotPluginConfigSchema = {
218
+ parse(value: unknown) {
219
+ return HexStrikeConfigSchema.parse(value);
220
+ },
221
+ safeParse(value: unknown) {
222
+ const result = HexStrikeConfigSchema.safeParse(value);
223
+ if (result.success) {
224
+ return { success: true, data: result.data };
225
+ }
226
+ return {
227
+ success: false,
228
+ error: {
229
+ issues: result.error?.issues?.map((issue) => ({
230
+ path: issue.path.map(String),
231
+ message: issue.message,
232
+ })),
233
+ },
234
+ };
235
+ },
236
+ };
237
+
238
+ const definition: PoolBotPluginDefinition = {
239
+ id: "hexstrike-bridge",
240
+ name: "HexStrike Security Bridge",
241
+ description: "Integrates HexStrike AI security tools (150+ scanners)",
242
+ version: "2026.3.9",
243
+
244
+ configSchema,
245
+
246
+ async register(api: PoolBotPluginApi) {
247
+ const config = HexStrikeConfigSchema.parse(api.pluginConfig || {});
248
+ const client = new HexStrikeClient(config);
249
+
250
+ api.logger.info(`HexStrike bridge registering (baseUrl: ${config.baseUrl})`);
251
+
252
+ // Record plugin load metric
253
+ const telemetry = getGlobalTelemetryService();
254
+ telemetry?.recordCounter("poolbot.security.plugin_loads", 1);
255
+
256
+ // Register gateway methods
257
+ api.registerGatewayMethod("security.status", async (opts: GatewayRequestHandlerOptions) => {
258
+ const health = await client.getHealth();
259
+ const metrics = client.getMetrics();
260
+
261
+ opts.respond(true, {
262
+ connected: health.status === "healthy",
263
+ version: health.version,
264
+ latencyMs: health.latencyMs,
265
+ maxConcurrent: config.maxConcurrentScans,
266
+ activeScans: client.getActiveScanCount(),
267
+ totalScans: metrics.totalScans,
268
+ completedScans: metrics.completedScans,
269
+ failedScans: metrics.failedScans,
270
+ });
271
+ });
272
+
273
+ api.registerGatewayMethod("security.tools.list", async (opts: GatewayRequestHandlerOptions) => {
274
+ const tools = await client.listTools();
275
+ opts.respond(true, { tools });
276
+ });
277
+
278
+ api.registerGatewayMethod("security.scan.start", async (opts: GatewayRequestHandlerOptions) => {
279
+ const params = opts.params as { tool: string; target: string; options?: Record<string, unknown> };
280
+
281
+ // Check concurrent scan limit
282
+ if (client.getActiveScanCount() >= config.maxConcurrentScans) {
283
+ opts.respond(false, undefined, {
284
+ code: ErrorCodes.UNAVAILABLE,
285
+ message: `Maximum concurrent scans (${config.maxConcurrentScans}) reached`,
286
+ });
287
+ return;
288
+ }
289
+
290
+ const job = await client.executeTool(params.tool, {
291
+ target: params.target,
292
+ ...params.options,
293
+ });
294
+ opts.respond(true, { jobId: job.id, status: job.status });
295
+ });
296
+
297
+ api.registerGatewayMethod("security.scan.status", async (opts: GatewayRequestHandlerOptions) => {
298
+ const params = opts.params as { jobId: string };
299
+ const job = client.getJob(params.jobId);
300
+ if (!job) {
301
+ opts.respond(false, undefined, { code: ErrorCodes.INVALID_REQUEST, message: `Job not found: ${params.jobId}` });
302
+ return;
303
+ }
304
+ opts.respond(true, {
305
+ jobId: job.id,
306
+ status: job.status,
307
+ progress: job.progress,
308
+ result: job.result,
309
+ error: job.error,
310
+ durationMs: job.durationMs,
311
+ startedAt: job.startedAt,
312
+ completedAt: job.completedAt,
313
+ });
314
+ });
315
+
316
+ api.registerGatewayMethod("security.scan.list", async (opts: GatewayRequestHandlerOptions) => {
317
+ const jobs = client.listJobs();
318
+ opts.respond(true, {
319
+ jobs: jobs.map(j => ({
320
+ jobId: j.id,
321
+ tool: j.tool,
322
+ target: j.target,
323
+ status: j.status,
324
+ progress: j.progress,
325
+ durationMs: j.durationMs,
326
+ startedAt: j.startedAt,
327
+ completedAt: j.completedAt,
328
+ })),
329
+ });
330
+ });
331
+
332
+ api.registerGatewayMethod("security.metrics", async (opts: GatewayRequestHandlerOptions) => {
333
+ const metrics = client.getMetrics();
334
+ const health = await client.getHealth();
335
+
336
+ opts.respond(true, {
337
+ ...metrics,
338
+ activeScans: client.getActiveScanCount(),
339
+ connected: health.status === "healthy",
340
+ averageDurationMs: metrics.totalScans > 0 ? Math.round(metrics.totalDurationMs / metrics.totalScans) : 0,
341
+ });
342
+ });
343
+
344
+ // Register CLI commands
345
+ api.registerCli((ctx) => {
346
+ const securityCmd = ctx.program
347
+ .command("security")
348
+ .description("Security scanning via HexStrike AI");
349
+
350
+ securityCmd
351
+ .command("status")
352
+ .description("Check HexStrike connection status")
353
+ .action(async () => {
354
+ const health = await client.getHealth();
355
+ console.log(`HexStrike Status: ${health.status}`);
356
+ if (health.version) {
357
+ console.log(`Version: ${health.version}`);
358
+ }
359
+ if (health.latencyMs) {
360
+ console.log(`Latency: ${health.latencyMs}ms`);
361
+ }
362
+ });
363
+
364
+ securityCmd
365
+ .command("tools")
366
+ .description("List available security tools")
367
+ .action(async () => {
368
+ const tools = await client.listTools();
369
+ console.log(`\nAvailable Security Tools (${tools.length}):\n`);
370
+
371
+ const byCategory = new Map<string, HexStrikeTool[]>();
372
+ for (const tool of tools) {
373
+ const list = byCategory.get(tool.category) || [];
374
+ list.push(tool);
375
+ byCategory.set(tool.category, list);
376
+ }
377
+
378
+ for (const [category, categoryTools] of byCategory) {
379
+ console.log(`\n${category}:`);
380
+ for (const tool of categoryTools) {
381
+ console.log(` • ${tool.name} - ${tool.description}`);
382
+ }
383
+ }
384
+ });
385
+
386
+ securityCmd
387
+ .command("scan <tool> <target>")
388
+ .description("Run a security scan")
389
+ .option("-w, --wait", "Wait for scan completion", false)
390
+ .option("-t, --timeout <seconds>", "Timeout in seconds", "300")
391
+ .action(async (tool: string, target: string, options: { wait?: boolean; timeout?: string }) => {
392
+ console.log(`Starting ${tool} scan against ${target}...`);
393
+
394
+ const job = await client.executeTool(tool, {
395
+ target,
396
+ });
397
+
398
+ console.log(`Scan started: ${job.id}`);
399
+
400
+ if (options.wait) {
401
+ console.log("Waiting for completion...");
402
+
403
+ const startTime = Date.now();
404
+ const timeoutMs = parseInt(options.timeout || "300", 10) * 1000;
405
+
406
+ while (job.status === "running" || job.status === "pending") {
407
+ if (Date.now() - startTime > timeoutMs) {
408
+ console.log("Timeout reached");
409
+ break;
410
+ }
411
+
412
+ await new Promise(r => setTimeout(r, 2000));
413
+ const current = client.getJob(job.id);
414
+ if (current) {
415
+ Object.assign(job, current);
416
+ if (job.progress > 0) {
417
+ process.stdout.write(`\rProgress: ${job.progress}%`);
418
+ }
419
+ }
420
+ }
421
+
422
+ console.log("\n");
423
+
424
+ if (job.status === "completed" && job.result) {
425
+ console.log("Scan completed successfully!");
426
+ console.log(JSON.stringify(job.result, null, 2));
427
+ } else if (job.error) {
428
+ console.error(`Scan failed: ${job.error}`);
429
+ process.exit(1);
430
+ }
431
+ } else {
432
+ console.log(`Use 'poolbot security scan-status ${job.id}' to check progress`);
433
+ }
434
+ });
435
+
436
+ securityCmd
437
+ .command("scan-status <jobId>")
438
+ .description("Check scan status")
439
+ .action(async (jobId: string) => {
440
+ const job = client.getJob(jobId);
441
+ if (!job) {
442
+ console.error(`Job not found: ${jobId}`);
443
+ process.exit(1);
444
+ }
445
+
446
+ console.log(`Job: ${job.id}`);
447
+ console.log(`Tool: ${job.tool}`);
448
+ console.log(`Target: ${job.target}`);
449
+ console.log(`Status: ${job.status}`);
450
+ console.log(`Progress: ${job.progress}%`);
451
+ if (job.durationMs) {
452
+ console.log(`Duration: ${job.durationMs}ms`);
453
+ }
454
+
455
+ if (job.result) {
456
+ console.log("\nResult:");
457
+ console.log(JSON.stringify(job.result, null, 2));
458
+ }
459
+
460
+ if (job.error) {
461
+ console.error(`\nError: ${job.error}`);
462
+ }
463
+ });
464
+
465
+ securityCmd
466
+ .command("metrics")
467
+ .description("Show security scan metrics")
468
+ .action(async () => {
469
+ const metrics = client.getMetrics();
470
+ const health = await client.getHealth();
471
+
472
+ console.log("\nSecurity Scan Metrics:\n");
473
+ console.log(`Connection: ${health.status}`);
474
+ console.log(`Active Scans: ${client.getActiveScanCount()}`);
475
+ console.log(`Total Scans: ${metrics.totalScans}`);
476
+ console.log(`Completed: ${metrics.completedScans}`);
477
+ console.log(`Failed: ${metrics.failedScans}`);
478
+ console.log(`Success Rate: ${metrics.totalScans > 0 ? Math.round((metrics.completedScans / metrics.totalScans) * 100) : 0}%`);
479
+ if (metrics.totalScans > 0) {
480
+ console.log(`Avg Duration: ${Math.round(metrics.totalDurationMs / metrics.totalScans)}ms`);
481
+ }
482
+ });
483
+ });
484
+ },
485
+ };
486
+
487
+ export default definition;
@@ -0,0 +1,17 @@
1
+ {
2
+ "name": "@poolbot/hexstrike-bridge",
3
+ "version": "2026.3.10",
4
+ "type": "module",
5
+ "description": "HexStrike AI security tools bridge for PoolBot - integrates 150+ security scanners",
6
+ "poolbot": {
7
+ "extensions": [
8
+ "./src/index.ts"
9
+ ]
10
+ },
11
+ "dependencies": {
12
+ "zod": "^3.22.4"
13
+ },
14
+ "devDependencies": {
15
+ "poolbot": "workspace:*"
16
+ }
17
+ }
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/imessage",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Poolbot iMessage channel plugin",
6
6
  "poolbot": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolzin/irc",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "description": "Pool Bot IRC channel plugin",
5
5
  "type": "module",
6
6
  "devDependencies": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/line",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Poolbot LINE channel plugin",
6
6
  "poolbot": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/llm-task",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Poolbot JSON-only LLM task plugin",
6
6
  "poolbot": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/lobster",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Lobster workflow tool plugin (typed pipelines + resumable approvals)",
6
6
  "poolbot": {
@@ -1,5 +1,10 @@
1
1
  # Changelog
2
2
 
3
+ ## 2026.3.10
4
+
5
+ ### Changes
6
+ - Version alignment with core Poolbot release numbers.
7
+
3
8
  ## 2026.3.4
4
9
 
5
10
  ### Changes
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/matrix",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Poolbot Matrix channel plugin",
6
6
  "poolbot": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poolbot/mattermost",
3
- "version": "2026.3.4",
3
+ "version": "2026.3.10",
4
4
  "type": "module",
5
5
  "description": "Poolbot Mattermost channel plugin",
6
6
  "poolbot": {
@@ -0,0 +1,14 @@
1
+ import type { PoolBotPluginApi } from "../../src/plugins/types.js";
2
+
3
+ import { createMcpServerService } from "./src/service.js";
4
+
5
+ const plugin = {
6
+ id: "mcp-server",
7
+ name: "MCP Server",
8
+ description: "MCP (Model Context Protocol) server - exposes PoolBot tools via MCP protocol",
9
+ register(api: PoolBotPluginApi) {
10
+ api.registerService(createMcpServerService());
11
+ },
12
+ };
13
+
14
+ export default plugin;
@@ -0,0 +1,11 @@
1
+ {
2
+ "name": "@poolbot/mcp-server",
3
+ "version": "2026.3.10",
4
+ "type": "module",
5
+ "description": "MCP (Model Context Protocol) server plugin for PoolBot - exposes tools via MCP protocol",
6
+ "poolbot": {
7
+ "extensions": [
8
+ "./index.ts"
9
+ ]
10
+ }
11
+ }