@bli-cockpit/mcp 0.1.111 → 0.1.112

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/README.md CHANGED
@@ -109,7 +109,7 @@ about what an agent can reach.
109
109
 
110
110
  <!-- BEGIN GENERATED verb census — `npm run mcp:readme` -->
111
111
 
112
- **147 of 152 Tower verbs have an MCP twin.**
112
+ **149 of 154 Tower verbs have an MCP twin.**
113
113
  Each tool goes through the SAME door its CLI verb calls, with the same
114
114
  collector device token — never a second route and never a service-role
115
115
  reader. `src/verb-census.test.ts` fails when a verb is in none of the
@@ -251,7 +251,9 @@ three tables below.
251
251
  | `cockpit settings switches set` | `settings_set` | `POST /api/settings/{jarvis-model,switches,model-routing,env-blobs} + PUT /api/settings/cli-floor` |
252
252
  | `cockpit settings` | `settings_show` | `GET /api/settings/* + /api/team/members` |
253
253
  | `cockpit setup` | `setup_read` | `GET /api/setup` |
254
+ | `cockpit slack connect` | `slack_connect` | `GET /api/slack/connections` |
254
255
  | `cockpit slack coverage` | `slack_coverage` | `GET /api/ops/slack/coverage` |
256
+ | `cockpit slack disconnect` | `slack_disconnect` | `DELETE /api/slack/connections` |
255
257
  | `cockpit slack read` | `slack_read` | `POST /api/ops/slack/read` |
256
258
  | `cockpit speed` | `speed_read` | `GET /api/* (every rail page's data door, see speed-tools.ts)` |
257
259
  | `cockpit speed --seen` | `speed_seen` | `GET /api/speed/seen` |
package/dist/ops-tools.js CHANGED
@@ -194,6 +194,17 @@ export function registerOpsTools(server, deps) {
194
194
  ...(toolRouter?.ok ? { toolRouter: toolRouter.body.board ?? null } : {}),
195
195
  });
196
196
  }));
197
+ register("slack_connect", { title: "Connect your Slack coverage", description: "Return your connection state and browser consent paths; consent must happen on Tower.", inputSchema: {} }, async () => withSession(deps, async (session) => {
198
+ const response = await callAgentDoor(session, deps.fetchImpl, "GET", "/api/slack/connections");
199
+ if (!response.ok)
200
+ return errorResult(doorFailureText("slack_connect", response));
201
+ const connections = response.body["connections"];
202
+ return textResult(connections.map(row => `${row["workspace"]}: ${row["connected"] ? "connected" : "Connect Slack"} ${new URL(String(row["connectPath"]), session.dashboardUrl).toString()}`).join("\n"), response.body);
203
+ }));
204
+ register("slack_disconnect", { title: "Disconnect your Slack grant", description: "Remove your saved credential for one workspace; retain collected data and bot membership.", inputSchema: { workspace: z.enum(["bli", "blue_pearl"]).describe("Which Slack workspace to disconnect: bli or blue_pearl.") } }, async (args) => withSession(deps, async (session) => {
205
+ const response = await callAgentDoor(session, deps.fetchImpl, "DELETE", `/api/slack/connections?workspace=${args.workspace}`);
206
+ return response.ok ? textResult(`Disconnected Slack for ${args.workspace}.`, response.body) : errorResult(doorFailureText("slack_disconnect", response));
207
+ }));
197
208
  register("slack_coverage", {
198
209
  title: "Read Tower's Slack collection coverage",
199
210
  description: "Which Slack channels the bot can actually read, per workspace, and which are stale beyond the server's own "
@@ -236,6 +247,8 @@ export function registerOpsTools(server, deps) {
236
247
  })
237
248
  .join("\n\n");
238
249
  return textResult(`${workspaces.length} workspace(s), ${staleTotal} stale channel(s).${lines ? `\n\n${lines}` : ""}`
250
+ + (coverage["privateCoverage"] ?? []).map(row => `\n${row["workspace"]}: ${row["botMemberCount"]}/${row["privateChannelsKnown"]} known private channels with the bot; ${row["peopleConnected"]} connected; not connected: ${(row["peopleNotConnected"] ?? []).join(", ") || "none"}; as of ${row["asOf"] ?? "no scan yet"}`).join("")
251
+ + (coverage["privateCoverageError"] ? `\nPrivate coverage unavailable: ${coverage["privateCoverageError"]}` : "")
239
252
  + (typeof coverage["note"] === "string" ? `\n\n${coverage["note"]}` : ""), { coverage });
240
253
  }));
241
254
  register("slack_read", {
@@ -10,7 +10,7 @@
10
10
  * from `src/` under Node's type stripping, so it may import nothing.
11
11
  */
12
12
  /** Tools that change nothing. The smoke calls every one. */
13
- export declare const READ_TOOLS: readonly ["get_ticket_timeline", "get_active_tickets", "docs_list", "docs_tree", "docs_read", "docs_sync_status", "msg_channels", "msg_read", "msg_thread", "work_list_issues", "work_get_issue", "work_issue_history", "work_list_projects", "careers_list", "careers_show", "careers_resume_url", "careers_takehome_show", "careers_settings_show", "rename_pending", "github_pr", "setup_read", "speed_read", "speed_seen", "usage_people", "usage_sessions", "mail_accounts", "mail_inbox", "mail_read", "mail_search", "mail_attachment", "mail_sync_status", "cal_today", "cal_week", "cal_next", "cal_find", "cal_calendars", "cal_sync_status", "jarvis_ask", "jarvis_trace", "jarvis_check", "models_list", "models_card", "models_compare", "brief_read", "brief_history", "brief_status", "brief_missed", "notes_folders", "notes_list", "glossary_list", "notes_show", "notes_shelf", "notes_shelves", "notes_place", "notes_accounts", "notes_recordings", "notes_recording", "notes_sync_status", "notes_granola_status", "notes_bot_upcoming", "ops_status", "slack_coverage", "slack_read", "memory_rules", "memory_profile", "memory_consolidation", "settings_show", "settings_list", "model_show", "team_members", "team_device_list", "scout_board", "workbook_read", "tower_search", "sources_check", "logs_digest", "brain_status"];
13
+ export declare const READ_TOOLS: readonly ["get_ticket_timeline", "get_active_tickets", "docs_list", "docs_tree", "docs_read", "docs_sync_status", "msg_channels", "msg_read", "msg_thread", "work_list_issues", "work_get_issue", "work_issue_history", "work_list_projects", "careers_list", "careers_show", "careers_resume_url", "careers_takehome_show", "careers_settings_show", "rename_pending", "github_pr", "setup_read", "speed_read", "speed_seen", "usage_people", "usage_sessions", "mail_accounts", "mail_inbox", "mail_read", "mail_search", "mail_attachment", "mail_sync_status", "cal_today", "cal_week", "cal_next", "cal_find", "cal_calendars", "cal_sync_status", "jarvis_ask", "jarvis_trace", "jarvis_check", "models_list", "models_card", "models_compare", "brief_read", "brief_history", "brief_status", "brief_missed", "notes_folders", "notes_list", "glossary_list", "notes_show", "notes_shelf", "notes_shelves", "notes_place", "notes_accounts", "notes_recordings", "notes_recording", "notes_sync_status", "notes_granola_status", "notes_bot_upcoming", "ops_status", "slack_coverage", "slack_connect", "slack_disconnect", "slack_read", "memory_rules", "memory_profile", "memory_consolidation", "settings_show", "settings_list", "model_show", "team_members", "team_device_list", "scout_board", "workbook_read", "tower_search", "sources_check", "logs_digest", "brain_status"];
14
14
  /**
15
15
  * Tools that write, but answer a dry run that writes nothing. The smoke calls
16
16
  * each one ONLY with its dry-run flag set (`scripts/smoke.ts` says which).
@@ -74,6 +74,8 @@ export const READ_TOOLS = [
74
74
  "notes_bot_upcoming",
75
75
  "ops_status",
76
76
  "slack_coverage",
77
+ "slack_connect",
78
+ "slack_disconnect",
77
79
  "slack_read",
78
80
  "memory_rules",
79
81
  "memory_profile",
@@ -354,6 +354,8 @@ export const MCP_TWINS = {
354
354
  "memory requeue": { tool: "memory_requeue", door: "POST /api/memory/requeue" },
355
355
  "ops status": { tool: "ops_status", door: "GET /api/ops/status" },
356
356
  "ops recompile": { tool: "ops_recompile", door: "POST /api/ops/recompile" },
357
+ "slack connect": { tool: "slack_connect", door: "GET /api/slack/connections" },
358
+ "slack disconnect": { tool: "slack_disconnect", door: "DELETE /api/slack/connections" },
357
359
  "slack coverage": { tool: "slack_coverage", door: "GET /api/ops/slack/coverage" },
358
360
  "slack read": { tool: "slack_read", door: "POST /api/ops/slack/read" },
359
361
  "settings show": { tool: "settings_show", door: "GET /api/settings/* + /api/team/members" },
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@bli-cockpit/mcp",
3
- "version": "0.1.111",
3
+ "version": "0.1.112",
4
4
  "private": false,
5
5
  "description": "bli-tower: an MCP server over BLI Cockpit's agent doors: JARVIS (jarvis_*), documents (docs_*), channels (msg_*), issues (work_*), the daily page (brief_*), meeting notes (notes_*), the ops board (ops_status/slack_*), settings/team/model, Scout and the workbook, plus the legacy event-stream tools (emit_event, get_ticket_timeline, get_active_tickets).",
6
6
  "type": "module",