@buildautomaton/cli 0.1.48 → 0.1.49

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/dist/cli.js CHANGED
@@ -25174,7 +25174,7 @@ var {
25174
25174
  } = import_index.default;
25175
25175
 
25176
25176
  // src/cli-version.ts
25177
- var CLI_VERSION = "0.1.48".length > 0 ? "0.1.48" : "0.0.0-dev";
25177
+ var CLI_VERSION = "0.1.49".length > 0 ? "0.1.49" : "0.0.0-dev";
25178
25178
 
25179
25179
  // src/cli/defaults.ts
25180
25180
  var DEFAULT_API_URL = process.env.BUILDAUTOMATON_API_URL ?? "https://api.buildautomaton.com";
@@ -27678,6 +27678,238 @@ var WebSocketMessageSchema = external_exports.object({
27678
27678
  error: external_exports.string().optional()
27679
27679
  });
27680
27680
 
27681
+ // ../types/src/integrations/link-detection/linear.ts
27682
+ function detectLinearLink(url2) {
27683
+ const linearMatch = url2.match(
27684
+ /https?:\/\/(?:app\.)?linear\.app\/([^/]+)\/issue\/([A-Z]+-\d+)/i
27685
+ );
27686
+ if (linearMatch) {
27687
+ return {
27688
+ url: url2,
27689
+ integrationType: "linear",
27690
+ resourceType: "work-item",
27691
+ resourceId: linearMatch[2],
27692
+ workspaceId: linearMatch[1]
27693
+ };
27694
+ }
27695
+ return null;
27696
+ }
27697
+
27698
+ // ../types/src/integrations/link-detection/github.ts
27699
+ function detectGitHubLink(url2) {
27700
+ const githubIssueMatch = url2.match(
27701
+ /https?:\/\/github\.com\/([^/]+)\/([^/]+)\/issues\/(\d+)/i
27702
+ );
27703
+ if (githubIssueMatch) {
27704
+ return {
27705
+ url: url2,
27706
+ integrationType: "github",
27707
+ resourceType: "issue",
27708
+ resourceId: githubIssueMatch[3],
27709
+ owner: githubIssueMatch[1],
27710
+ repo: githubIssueMatch[2]
27711
+ };
27712
+ }
27713
+ const githubPRMatch = url2.match(
27714
+ /https?:\/\/github\.com\/([^/]+)\/([^/]+)\/pull\/(\d+)/i
27715
+ );
27716
+ if (githubPRMatch) {
27717
+ return {
27718
+ url: url2,
27719
+ integrationType: "github",
27720
+ resourceType: "pull-request",
27721
+ resourceId: githubPRMatch[3],
27722
+ owner: githubPRMatch[1],
27723
+ repo: githubPRMatch[2]
27724
+ };
27725
+ }
27726
+ return null;
27727
+ }
27728
+
27729
+ // ../types/src/integrations/link-detection/jira.ts
27730
+ function detectJIRALink(url2) {
27731
+ const jiraMatch = url2.match(
27732
+ /https?:\/\/([^/]+)\.atlassian\.net\/(?:browse|jira\/software\/projects\/[^/]+\/issues)\/([A-Z]+-\d+)/i
27733
+ );
27734
+ if (jiraMatch) {
27735
+ return {
27736
+ url: url2,
27737
+ integrationType: "jira",
27738
+ resourceType: "issue",
27739
+ resourceId: jiraMatch[2],
27740
+ projectKey: jiraMatch[2].split("-")[0]
27741
+ };
27742
+ }
27743
+ return null;
27744
+ }
27745
+
27746
+ // ../types/src/integrations/link-detection/notion.ts
27747
+ function formatNotionPageId(hex) {
27748
+ if (hex.length !== 32) return hex;
27749
+ return `${hex.slice(0, 8)}-${hex.slice(8, 12)}-${hex.slice(12, 16)}-${hex.slice(16, 20)}-${hex.slice(20, 32)}`;
27750
+ }
27751
+ function detectNotionLink(url2) {
27752
+ const standardMatch = url2.match(
27753
+ /https?:\/\/(?:www\.)?notion\.(?:so|site)\/(?:[^/#?]+\/)?(?:[^/#?-]+-)?([a-f0-9]{32})/i
27754
+ );
27755
+ if (standardMatch) {
27756
+ return {
27757
+ url: url2,
27758
+ integrationType: "notion",
27759
+ resourceType: "page",
27760
+ resourceId: formatNotionPageId(standardMatch[1])
27761
+ };
27762
+ }
27763
+ const siteMatch = url2.match(
27764
+ /https?:\/\/([^.]+)\.notion\.(?:so|site)\/(?:[^/#?-]+-)?([a-f0-9]{32})/i
27765
+ );
27766
+ if (siteMatch) {
27767
+ return {
27768
+ url: url2,
27769
+ integrationType: "notion",
27770
+ resourceType: "page",
27771
+ resourceId: formatNotionPageId(siteMatch[2]),
27772
+ notionWorkspaceId: siteMatch[1]
27773
+ };
27774
+ }
27775
+ return null;
27776
+ }
27777
+
27778
+ // ../types/src/integrations/link-detection/slack.ts
27779
+ function detectSlackLink(url2) {
27780
+ const archiveThreadMatch = url2.match(
27781
+ /https?:\/\/(?:([^./]+)\.)?slack\.com\/archives\/([A-Z0-9]+)\/p(\d+)(?:\?.*)?$/i
27782
+ );
27783
+ if (archiveThreadMatch) {
27784
+ return {
27785
+ url: url2,
27786
+ integrationType: "slack",
27787
+ resourceType: "thread",
27788
+ resourceId: `${archiveThreadMatch[2]}-${archiveThreadMatch[3]}`,
27789
+ isChannel: false
27790
+ };
27791
+ }
27792
+ const appThreadMatch = url2.match(
27793
+ /https?:\/\/app\.slack\.com\/client\/([^/]+)\/([A-Z0-9]+)\/thread\/[A-Z0-9]+-(\d+)/i
27794
+ );
27795
+ if (appThreadMatch) {
27796
+ return {
27797
+ url: url2,
27798
+ integrationType: "slack",
27799
+ resourceType: "thread",
27800
+ resourceId: `${appThreadMatch[2]}-${appThreadMatch[3]}`,
27801
+ isChannel: false
27802
+ };
27803
+ }
27804
+ const channelOnlyMatch = url2.match(
27805
+ /https?:\/\/(?:app\.)?(?:([^./]+)\.)?slack\.com\/archives\/([A-Z0-9]+)\/?(\?.*)?$/i
27806
+ );
27807
+ if (channelOnlyMatch && !url2.includes("/p")) {
27808
+ return {
27809
+ url: url2,
27810
+ integrationType: "slack",
27811
+ resourceType: "channel",
27812
+ resourceId: channelOnlyMatch[2],
27813
+ isChannel: true
27814
+ };
27815
+ }
27816
+ return null;
27817
+ }
27818
+
27819
+ // ../types/src/integrations/link-detection/zoom.ts
27820
+ function detectZoomLink(url2) {
27821
+ try {
27822
+ const u = new URL(url2);
27823
+ const host = u.hostname.toLowerCase();
27824
+ if (!host.endsWith("zoom.us") && !host.endsWith("zoom.com")) return null;
27825
+ const pathParts = u.pathname.split("/").filter(Boolean);
27826
+ if (pathParts.length >= 2 && (pathParts[0] === "j" || pathParts[0] === "s" || pathParts[0] === "my")) {
27827
+ const meetingId = pathParts[1].replace(/\s/g, "");
27828
+ if (meetingId.length >= 9) {
27829
+ return {
27830
+ url: url2,
27831
+ integrationType: "zoom",
27832
+ resourceType: "meeting",
27833
+ resourceId: meetingId,
27834
+ zoomMeetingId: meetingId
27835
+ };
27836
+ }
27837
+ }
27838
+ } catch {
27839
+ }
27840
+ return null;
27841
+ }
27842
+
27843
+ // ../types/src/integrations/link-detection/asana.ts
27844
+ var ASANA_TASK_GID = /\d{10,}/;
27845
+ function parseAsanaTaskGid(segment) {
27846
+ const trimmed2 = segment.trim();
27847
+ if (!ASANA_TASK_GID.test(trimmed2)) return null;
27848
+ return trimmed2;
27849
+ }
27850
+ function detectAsanaLink(url2) {
27851
+ const v1ProjectMatch = url2.match(
27852
+ /https?:\/\/app\.asana\.com\/1\/[^/]+\/project\/([^/?#]+)\/task\/([^/?#]+)/i
27853
+ );
27854
+ if (v1ProjectMatch) {
27855
+ const taskGid = parseAsanaTaskGid(v1ProjectMatch[2]);
27856
+ if (!taskGid) return null;
27857
+ return {
27858
+ url: url2,
27859
+ integrationType: "asana",
27860
+ resourceType: "task",
27861
+ resourceId: taskGid,
27862
+ asanaProjectGid: v1ProjectMatch[1]
27863
+ };
27864
+ }
27865
+ const v1TaskMatch = url2.match(/https?:\/\/app\.asana\.com\/1\/[^/]+(?:\/[^/]+)*\/task\/([^/?#]+)/i);
27866
+ if (v1TaskMatch) {
27867
+ const taskGid = parseAsanaTaskGid(v1TaskMatch[1]);
27868
+ if (!taskGid) return null;
27869
+ return {
27870
+ url: url2,
27871
+ integrationType: "asana",
27872
+ resourceType: "task",
27873
+ resourceId: taskGid
27874
+ };
27875
+ }
27876
+ const legacyMatch = url2.match(/https?:\/\/app\.asana\.com\/0\/([^/?#]+)\/([^/?#]+)/i);
27877
+ if (legacyMatch) {
27878
+ const projectGid = legacyMatch[1];
27879
+ const taskGid = parseAsanaTaskGid(legacyMatch[2]);
27880
+ if (!taskGid) return null;
27881
+ if (projectGid === "inbox" || projectGid === "my_tasks") {
27882
+ return null;
27883
+ }
27884
+ return {
27885
+ url: url2,
27886
+ integrationType: "asana",
27887
+ resourceType: "task",
27888
+ resourceId: taskGid,
27889
+ asanaProjectGid: projectGid === "0" ? void 0 : projectGid
27890
+ };
27891
+ }
27892
+ return null;
27893
+ }
27894
+
27895
+ // ../types/src/integrations/link-detection/index.ts
27896
+ function detectIntegrationLink(url2) {
27897
+ return detectLinearLink(url2) || detectGitHubLink(url2) || detectJIRALink(url2) || detectNotionLink(url2) || detectSlackLink(url2) || detectZoomLink(url2) || detectAsanaLink(url2);
27898
+ }
27899
+ function extractIntegrationLinks(text) {
27900
+ const urlRegex = /https?:\/\/[^\s<>"{}|\\^`[\]]+/gi;
27901
+ const urls = text.match(urlRegex) || [];
27902
+ const links = [];
27903
+ for (const url2 of urls) {
27904
+ const detected = detectIntegrationLink(url2);
27905
+ if (detected) links.push(detected);
27906
+ }
27907
+ return links;
27908
+ }
27909
+ function extractFetchableIntegrationLinks(text) {
27910
+ return extractIntegrationLinks(text).filter((link) => !(link.integrationType === "slack" && link.isChannel));
27911
+ }
27912
+
27681
27913
  // ../types/src/checkpoints.ts
27682
27914
  init_zod();
27683
27915
  var CheckpointKindSchema = external_exports.enum(["daily", "weekly", "overall"]);
@@ -28105,6 +28337,16 @@ var GitRepoMetaSchema = external_exports.object({
28105
28337
  updatedAt: external_exports.string()
28106
28338
  });
28107
28339
 
28340
+ // ../types/src/bridge-mcp-tool-display.ts
28341
+ var GET_INTEGRATION_CONTENT_TOOL = "get_integration_content";
28342
+ var LIST_PARENT_SESSION_PROMPTS_TOOL = "list_parent_session_prompts";
28343
+ var GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL = "get_parent_session_turn_transcript";
28344
+ var BRIDGE_MCP_TOOL_LABELS = {
28345
+ [GET_INTEGRATION_CONTENT_TOOL]: "Fetch external ticket content",
28346
+ [LIST_PARENT_SESSION_PROMPTS_TOOL]: "List parent session prompts",
28347
+ [GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL]: "Read parent session transcript"
28348
+ };
28349
+
28108
28350
  // ../types/src/claude-code-permission-mode.ts
28109
28351
  var CLAUDE_CODE_PERMISSION_MODES = [
28110
28352
  "default",
@@ -36155,7 +36397,15 @@ async function fetchInternalApiJson(params) {
36155
36397
  const token = params.getCloudAccessToken();
36156
36398
  if (!token) return { ok: false, error: "Missing cloud access token." };
36157
36399
  const url2 = `${internalApiBase(params.cloudApiBaseUrl)}${params.path}`;
36158
- const res = await fetch(url2, { headers: { Authorization: `Bearer ${token}` } });
36400
+ const method = params.method ?? "GET";
36401
+ const res = await fetch(url2, {
36402
+ method,
36403
+ headers: {
36404
+ Authorization: `Bearer ${token}`,
36405
+ ...params.body != null ? { "Content-Type": "application/json" } : {}
36406
+ },
36407
+ ...params.body != null ? { body: JSON.stringify(params.body) } : {}
36408
+ });
36159
36409
  if (!res.ok) {
36160
36410
  const t = await res.text().catch(() => "");
36161
36411
  return { ok: false, error: `${params.errorLabel} (${res.status}): ${t.slice(0, 200)}` };
@@ -36272,6 +36522,39 @@ async function enrichForkedSessionPromptForAgent(params) {
36272
36522
  return buildForkedSessionAgentPrompt(params.promptText, params.sessionId, parentSessionId);
36273
36523
  }
36274
36524
 
36525
+ // src/agents/acp/build-integration-content-agent-prompt-note.ts
36526
+ function buildIntegrationContentAgentPromptNote(sessionId) {
36527
+ const sessionRef = sessionId.trim();
36528
+ return [
36529
+ "The user message includes link(s) to external integration resources (Linear, GitHub, Jira, Notion, Slack thread, Zoom, or Asana).",
36530
+ "Use the get_integration_content MCP tool on the buildautomaton-bridge server to fetch the full content of each link.",
36531
+ `When calling the tool, pass sessionId "${sessionRef}" and the URL as url.`,
36532
+ "By default the tool links the fetched URL as this session external ticket when the session has none yet. Pass associateAsSessionTicket: false when fetching additional links for context only (after the primary ticket is linked, or when you do not want association).",
36533
+ "If the tool reports unsupported_url, do not retry with the same URL. If it reports temporarily_unavailable, you may retry later."
36534
+ ].join("\n");
36535
+ }
36536
+ function injectIntegrationContentAgentPromptNote(agentPrompt, sessionId) {
36537
+ const note = buildIntegrationContentAgentPromptNote(sessionId);
36538
+ const marker = "\nUser request:\n";
36539
+ const idx = agentPrompt.indexOf(marker);
36540
+ if (idx >= 0) {
36541
+ return `${agentPrompt.slice(0, idx)}
36542
+ ${note}${agentPrompt.slice(idx)}`;
36543
+ }
36544
+ return `${note}
36545
+
36546
+ ${agentPrompt.trim()}`;
36547
+ }
36548
+
36549
+ // src/agents/acp/enrich-integration-content-prompt-for-agent.ts
36550
+ function enrichIntegrationContentPromptForAgent(params) {
36551
+ if (!params.sessionId.trim()) return params.agentPromptText;
36552
+ if (extractFetchableIntegrationLinks(params.originalPromptText).length === 0) {
36553
+ return params.agentPromptText;
36554
+ }
36555
+ return injectIntegrationContentAgentPromptNote(params.agentPromptText, params.sessionId);
36556
+ }
36557
+
36275
36558
  // src/agents/acp/send-prompt-to-agent.ts
36276
36559
  async function sendPromptToAgent(options) {
36277
36560
  const {
@@ -36302,6 +36585,13 @@ async function sendPromptToAgent(options) {
36302
36585
  getCloudAccessToken
36303
36586
  });
36304
36587
  }
36588
+ if (sessionId) {
36589
+ agentPromptText = enrichIntegrationContentPromptForAgent({
36590
+ sessionId,
36591
+ originalPromptText: promptText,
36592
+ agentPromptText
36593
+ });
36594
+ }
36305
36595
  let sendOpts = {};
36306
36596
  if (attachments && attachments.length > 0) {
36307
36597
  if (!sessionId || !cloudApiBaseUrl || !getCloudAccessToken) {
@@ -42576,8 +42866,8 @@ async function callListParentSessionPromptsTool(ctx, cloud, childSessionId, pare
42576
42866
  }
42577
42867
 
42578
42868
  // src/mcp/tools/session-history/fork/tool-names.ts
42579
- var LIST_PARENT_SESSION_PROMPTS_TOOL = "list_parent_session_prompts";
42580
- var GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL = "get_parent_session_turn_transcript";
42869
+ var LIST_PARENT_SESSION_PROMPTS_TOOL2 = "list_parent_session_prompts";
42870
+ var GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL2 = "get_parent_session_turn_transcript";
42581
42871
 
42582
42872
  // src/mcp/tools/session-history/fork/call-fork-session-mcp-tool.ts
42583
42873
  async function callForkSessionMcpTool(ctx, cloud, name, args) {
@@ -42594,10 +42884,10 @@ async function callForkSessionMcpTool(ctx, cloud, name, args) {
42594
42884
  return mcpTextResult(parentResolved.error, true);
42595
42885
  }
42596
42886
  const parentSessionId = parentResolved.parentSessionId;
42597
- if (name === LIST_PARENT_SESSION_PROMPTS_TOOL) {
42887
+ if (name === LIST_PARENT_SESSION_PROMPTS_TOOL2) {
42598
42888
  return callListParentSessionPromptsTool(ctx, cloud, childSessionId, parentSessionId);
42599
42889
  }
42600
- if (name === GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL) {
42890
+ if (name === GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL2) {
42601
42891
  return callGetParentSessionTurnTranscriptTool(ctx, cloud, childSessionId, args);
42602
42892
  }
42603
42893
  return mcpTextResult(`Unknown fork session tool: ${name}`, true);
@@ -42610,7 +42900,7 @@ var SESSION_ID_SCHEMA = {
42610
42900
  };
42611
42901
  var FORK_SESSION_MCP_TOOL_DEFINITIONS = [
42612
42902
  {
42613
- name: LIST_PARENT_SESSION_PROMPTS_TOOL,
42903
+ name: LIST_PARENT_SESSION_PROMPTS_TOOL2,
42614
42904
  description: "List user prompts (main turns) from the parent session a fork was created from. Requires sessionId. Returns an error if the session has no parent history (not a fork).",
42615
42905
  inputSchema: {
42616
42906
  type: "object",
@@ -42620,7 +42910,7 @@ var FORK_SESSION_MCP_TOOL_DEFINITIONS = [
42620
42910
  }
42621
42911
  },
42622
42912
  {
42623
- name: GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL,
42913
+ name: GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL2,
42624
42914
  description: "Full transcript for one parent-session turn, including tool calls and agent messages. Requires sessionId and turnId. Returns an error if the session has no parent history (not a fork).",
42625
42915
  inputSchema: {
42626
42916
  type: "object",
@@ -42636,7 +42926,130 @@ var FORK_SESSION_MCP_TOOL_DEFINITIONS = [
42636
42926
 
42637
42927
  // src/mcp/tools/session-history/fork/is-fork-session-mcp-tool-name.ts
42638
42928
  function isForkSessionMcpToolName(name) {
42639
- return name === LIST_PARENT_SESSION_PROMPTS_TOOL || name === GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL;
42929
+ return name === LIST_PARENT_SESSION_PROMPTS_TOOL2 || name === GET_PARENT_SESSION_TURN_TRANSCRIPT_TOOL2;
42930
+ }
42931
+
42932
+ // src/mcp/tools/integration-content/tool-names.ts
42933
+ var GET_INTEGRATION_CONTENT_TOOL2 = "get_integration_content";
42934
+
42935
+ // src/mcp/tools/integration-content/cloud/fetch-integration-content.ts
42936
+ async function fetchCloudIntegrationContent(params) {
42937
+ return fetchInternalApiJson({
42938
+ ...params,
42939
+ path: `/internal/sessions/${encodeURIComponent(params.sessionId)}/integrations/content`,
42940
+ errorLabel: "Integration content fetch failed",
42941
+ method: "POST",
42942
+ body: {
42943
+ url: params.url,
42944
+ associateAsSessionTicket: params.associateAsSessionTicket !== false
42945
+ }
42946
+ });
42947
+ }
42948
+
42949
+ // src/mcp/tools/integration-content/format-integration-content-for-mcp.ts
42950
+ function formatIntegrationContentForMcp(result) {
42951
+ if (!result.ok) {
42952
+ const lines2 = [`status: ${result.code}`, `message: ${result.message}`];
42953
+ if (result.integrationType) lines2.push(`integrationType: ${result.integrationType}`);
42954
+ if (result.retryable) lines2.push("retryable: true");
42955
+ lines2.push(...formatSessionTicketAssociationLines(result.sessionTicketAssociation));
42956
+ return lines2.join("\n");
42957
+ }
42958
+ const lines = [
42959
+ formatIntegrationContentBody(result.integrationType, result.content),
42960
+ ...formatSessionTicketAssociationLines(result.sessionTicketAssociation)
42961
+ ];
42962
+ return lines.join("\n");
42963
+ }
42964
+ function formatSessionTicketAssociationLines(association) {
42965
+ if (association.status === "associated") {
42966
+ const title = association.externalTicket.displayTitle?.trim() || association.externalTicket.normalizedUrl;
42967
+ return ["", "--- session ticket ---", "status: associated", `displayTitle: ${title}`];
42968
+ }
42969
+ if (association.status === "failed") {
42970
+ return ["", "--- session ticket ---", "status: failed", `reason: ${association.reason}`];
42971
+ }
42972
+ return ["", "--- session ticket ---", `status: ${association.status}`, `reason: ${association.reason}`];
42973
+ }
42974
+ function formatIntegrationContentBody(integrationType, content) {
42975
+ const lines = [
42976
+ `integrationType: ${integrationType}`,
42977
+ `title: ${content.title}`,
42978
+ `url: ${content.url}`,
42979
+ "",
42980
+ "--- body ---",
42981
+ content.body
42982
+ ];
42983
+ if (content.comments?.length) {
42984
+ lines.push("", "--- comments ---");
42985
+ for (const comment of content.comments) {
42986
+ lines.push(`[${comment.createdAt}] ${comment.author}:`, comment.body, "");
42987
+ }
42988
+ }
42989
+ const threadMessages = content.threadMessages;
42990
+ if (threadMessages?.length) {
42991
+ lines.push("", "--- thread messages ---");
42992
+ for (const msg of threadMessages) {
42993
+ lines.push(`[${msg.ts}] ${msg.displayName}: ${msg.text}`);
42994
+ }
42995
+ }
42996
+ if (content.metadata && Object.keys(content.metadata).length > 0) {
42997
+ lines.push("", "--- metadata ---", JSON.stringify(content.metadata, null, 2));
42998
+ }
42999
+ return lines.join("\n");
43000
+ }
43001
+
43002
+ // src/mcp/tools/integration-content/call-integration-content-mcp-tool.ts
43003
+ async function callIntegrationContentMcpTool(ctx, cloud, name, args) {
43004
+ if (name !== GET_INTEGRATION_CONTENT_TOOL2) {
43005
+ return mcpTextResult(`Unknown integration content tool: ${name}`, true);
43006
+ }
43007
+ const sessionId = ctx.sessionId.trim();
43008
+ if (!sessionId) return mcpTextResult("sessionId is required.", true);
43009
+ const url2 = typeof args.url === "string" ? args.url.trim() : "";
43010
+ if (!url2) return mcpTextResult("url is required.", true);
43011
+ const associateAsSessionTicket = args.associateAsSessionTicket !== false;
43012
+ const fetched = await fetchCloudIntegrationContent({
43013
+ sessionId,
43014
+ url: url2,
43015
+ associateAsSessionTicket,
43016
+ cloudApiBaseUrl: cloud.cloudApiBaseUrl,
43017
+ getCloudAccessToken: cloud.getCloudAccessToken
43018
+ });
43019
+ if (!fetched.ok) return mcpTextResult(fetched.error, true);
43020
+ const text = formatIntegrationContentForMcp(fetched.data);
43021
+ const isError = !fetched.data.ok;
43022
+ return mcpTextResult(text, isError);
43023
+ }
43024
+
43025
+ // src/mcp/tools/integration-content/tool-definitions.ts
43026
+ var SESSION_ID_SCHEMA2 = {
43027
+ type: "string",
43028
+ description: "Id of the current session. Required on every tool call so the workspace integration credentials can be resolved."
43029
+ };
43030
+ var INTEGRATION_CONTENT_MCP_TOOL_DEFINITIONS = [
43031
+ {
43032
+ name: GET_INTEGRATION_CONTENT_TOOL2,
43033
+ description: "Fetch the full content of a supported external integration link (Linear, GitHub, Jira, Notion, Slack thread, Zoom meeting, Asana). Requires sessionId and url. By default, links the URL as this session external ticket when the session has none yet. Pass associateAsSessionTicket: false to fetch content only (e.g. additional context links). Returns an error when the URL is unsupported, the integration is not connected, or content is temporarily unavailable (retry may succeed).",
43034
+ inputSchema: {
43035
+ type: "object",
43036
+ properties: {
43037
+ sessionId: SESSION_ID_SCHEMA2,
43038
+ url: { type: "string", description: "External integration URL to fetch" },
43039
+ associateAsSessionTicket: {
43040
+ type: "boolean",
43041
+ description: "Defaults to true. When true and the session has no linked external ticket yet, links this URL as the session external ticket. Pass false when fetching additional links for context only."
43042
+ }
43043
+ },
43044
+ required: ["sessionId", "url"],
43045
+ additionalProperties: false
43046
+ }
43047
+ }
43048
+ ];
43049
+
43050
+ // src/mcp/tools/integration-content/index.ts
43051
+ function isIntegrationContentMcpToolName(name) {
43052
+ return name === GET_INTEGRATION_CONTENT_TOOL2;
42640
43053
  }
42641
43054
 
42642
43055
  // src/mcp/bridge-mcp-tools.ts
@@ -42649,7 +43062,7 @@ function requireCloud(shared) {
42649
43062
  function createBridgeMcpToolRegistry(shared) {
42650
43063
  const cloud = requireCloud(shared);
42651
43064
  return {
42652
- listTools: async () => [...FORK_SESSION_MCP_TOOL_DEFINITIONS],
43065
+ listTools: async () => [...FORK_SESSION_MCP_TOOL_DEFINITIONS, ...INTEGRATION_CONTENT_MCP_TOOL_DEFINITIONS],
42653
43066
  callTool: async (name, args) => {
42654
43067
  if (isForkSessionMcpToolName(name)) {
42655
43068
  if (!cloud) {
@@ -42667,6 +43080,22 @@ function createBridgeMcpToolRegistry(shared) {
42667
43080
  }
42668
43081
  return callForkSessionMcpTool({ ...shared, sessionId }, cloud, name, args);
42669
43082
  }
43083
+ if (isIntegrationContentMcpToolName(name)) {
43084
+ if (!cloud) {
43085
+ return {
43086
+ content: [{ type: "text", text: "Bridge MCP tools require cloud API credentials." }],
43087
+ isError: true
43088
+ };
43089
+ }
43090
+ const sessionId = typeof args.sessionId === "string" ? args.sessionId.trim() : "";
43091
+ if (!sessionId) {
43092
+ return {
43093
+ content: [{ type: "text", text: "sessionId is required." }],
43094
+ isError: true
43095
+ };
43096
+ }
43097
+ return callIntegrationContentMcpTool({ ...shared, sessionId }, cloud, name, args);
43098
+ }
42670
43099
  throw new Error(`Unknown bridge MCP tool: ${name}`);
42671
43100
  }
42672
43101
  };