Skip to content

Commit 343fc74

Browse files
committed
fix: wrap more tool responses in untrusted-user-data tags
1 parent c4ba2c9 commit 343fc74

34 files changed

+297
-303
lines changed

src/tools/atlas/create/createDBUser.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ export class CreateDBUserTool extends AtlasToolBase {
2121
.optional()
2222
.nullable()
2323
.describe(
24-
"Password for the new user. If the user hasn't supplied an explicit password, leave it unset and under no circumstances try to generate a random one. A secure password will be generated by the MCP server if necessary."
24+
"Password for the new user. IMPORTANT: If the user hasn't supplied an explicit password, leave it unset and under no circumstances try to generate a random one. A secure password will be generated by the MCP server if necessary."
2525
),
2626
roles: z
2727
.array(
Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { z } from "zod";
22
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
33
import { AtlasToolBase } from "../atlasTool.js";
4-
import { ToolArgs, OperationType } from "../../tool.js";
4+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
55

66
export class InspectAccessListTool extends AtlasToolBase {
77
public name = "atlas-inspect-access-list";
@@ -20,23 +20,25 @@ export class InspectAccessListTool extends AtlasToolBase {
2020
},
2121
});
2222

23-
if (!accessList?.results?.length) {
24-
throw new Error("No access list entries found.");
23+
const results = accessList.results ?? [];
24+
25+
if (!results.length) {
26+
return {
27+
content: [{ type: "text", text: "No access list entries found." }],
28+
};
2529
}
2630

2731
return {
28-
content: [
29-
{
30-
type: "text",
31-
text: `IP ADDRESS | CIDR | COMMENT
32+
content: formatUntrustedData(
33+
`Found ${results.length} access list entries`,
34+
`IP ADDRESS | CIDR | COMMENT
3235
------|------|------
33-
${(accessList.results || [])
36+
${results
3437
.map((entry) => {
3538
return `${entry.ipAddress} | ${entry.cidrBlock} | ${entry.comment}`;
3639
})
37-
.join("\n")}`,
38-
},
39-
],
40+
.join("\n")}`
41+
),
4042
};
4143
}
4244
}

src/tools/atlas/read/inspectCluster.ts

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { z } from "zod";
22
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
33
import { AtlasToolBase } from "../atlasTool.js";
4-
import { ToolArgs, OperationType } from "../../tool.js";
4+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
55
import { Cluster, inspectCluster } from "../../../common/atlas/cluster.js";
66

77
export class InspectClusterTool extends AtlasToolBase {
@@ -21,14 +21,12 @@ export class InspectClusterTool extends AtlasToolBase {
2121

2222
private formatOutput(formattedCluster: Cluster): CallToolResult {
2323
return {
24-
content: [
25-
{
26-
type: "text",
27-
text: `Cluster Name | Cluster Type | Tier | State | MongoDB Version | Connection String
24+
content: formatUntrustedData(
25+
"Cluster details:",
26+
`Cluster Name | Cluster Type | Tier | State | MongoDB Version | Connection String
2827
----------------|----------------|----------------|----------------|----------------|----------------
29-
${formattedCluster.name || "Unknown"} | ${formattedCluster.instanceType} | ${formattedCluster.instanceSize || "N/A"} | ${formattedCluster.state || "UNKNOWN"} | ${formattedCluster.mongoDBVersion || "N/A"} | ${formattedCluster.connectionString || "N/A"}`,
30-
},
31-
],
28+
${formattedCluster.name || "Unknown"} | ${formattedCluster.instanceType} | ${formattedCluster.instanceSize || "N/A"} | ${formattedCluster.state || "UNKNOWN"} | ${formattedCluster.mongoDBVersion || "N/A"} | ${formattedCluster.connectionString || "N/A"}`
29+
),
3230
};
3331
}
3432
}

src/tools/atlas/read/listAlerts.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { z } from "zod";
22
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
33
import { AtlasToolBase } from "../atlasTool.js";
4-
import { ToolArgs, OperationType } from "../../tool.js";
4+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
55

66
export class ListAlertsTool extends AtlasToolBase {
77
public name = "atlas-list-alerts";
@@ -39,7 +39,7 @@ export class ListAlertsTool extends AtlasToolBase {
3939
.join("\n");
4040

4141
return {
42-
content: [{ type: "text", text: output }],
42+
content: formatUntrustedData(`Found ${data.results.length} alerts in project ${projectId}`, output),
4343
};
4444
}
4545
}

src/tools/atlas/read/listClusters.ts

Lines changed: 9 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { z } from "zod";
22
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
33
import { AtlasToolBase } from "../atlasTool.js";
4-
import { ToolArgs, OperationType } from "../../tool.js";
4+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
55
import {
66
PaginatedClusterDescription20240805,
77
PaginatedOrgGroupView,
@@ -86,7 +86,9 @@ ${rows}`,
8686
): CallToolResult {
8787
// Check if both traditional clusters and flex clusters are absent
8888
if (!clusters?.results?.length && !flexClusters?.results?.length) {
89-
throw new Error("No clusters found.");
89+
return {
90+
content: [{ type: "text", text: "No clusters found." }],
91+
};
9092
}
9193
const formattedClusters = clusters?.results?.map((cluster) => formatCluster(cluster)) || [];
9294
const formattedFlexClusters = flexClusters?.results?.map((cluster) => formatFlexCluster(cluster)) || [];
@@ -96,18 +98,12 @@ ${rows}`,
9698
})
9799
.join("\n");
98100
return {
99-
content: [
100-
{
101-
type: "text",
102-
text: `Here are your MongoDB Atlas clusters in project "${project.name}" (${project.id}):`,
103-
},
104-
{
105-
type: "text",
106-
text: `Cluster Name | Cluster Type | Tier | State | MongoDB Version | Connection String
101+
content: formatUntrustedData(
102+
`Found ${rows.length} clusters in project "${project.name}" (${project.id}):`,
103+
`Cluster Name | Cluster Type | Tier | State | MongoDB Version | Connection String
107104
----------------|----------------|----------------|----------------|----------------|----------------
108-
${rows}`,
109-
},
110-
],
105+
${rows}`
106+
),
111107
};
112108
}
113109
}

src/tools/atlas/read/listDBUsers.ts

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { z } from "zod";
22
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
33
import { AtlasToolBase } from "../atlasTool.js";
4-
import { ToolArgs, OperationType } from "../../tool.js";
4+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
55
import { DatabaseUserRole, UserScope } from "../../../common/atlas/openapi.js";
66

77
export class ListDBUsersTool extends AtlasToolBase {
@@ -22,7 +22,9 @@ export class ListDBUsersTool extends AtlasToolBase {
2222
});
2323

2424
if (!data?.results?.length) {
25-
throw new Error("No database users found.");
25+
return {
26+
content: [{ type: "text", text: " No database users found" }],
27+
};
2628
}
2729

2830
const output =
@@ -35,7 +37,7 @@ export class ListDBUsersTool extends AtlasToolBase {
3537
})
3638
.join("\n");
3739
return {
38-
content: [{ type: "text", text: output }],
40+
content: formatUntrustedData(`Found ${data.results.length} database users in project ${projectId}`, output),
3941
};
4042
}
4143
}

src/tools/atlas/read/listOrgs.ts

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
22
import { AtlasToolBase } from "../atlasTool.js";
3-
import { OperationType } from "../../tool.js";
3+
import { formatUntrustedData, OperationType } from "../../tool.js";
44

55
export class ListOrganizationsTool extends AtlasToolBase {
66
public name = "atlas-list-orgs";
@@ -12,10 +12,12 @@ export class ListOrganizationsTool extends AtlasToolBase {
1212
const data = await this.session.apiClient.listOrganizations();
1313

1414
if (!data?.results?.length) {
15-
throw new Error("No projects found in your MongoDB Atlas account.");
15+
return {
16+
content: [{ type: "text", text: "No organizations found in your MongoDB Atlas account." }],
17+
};
1618
}
1719

18-
// Format projects as a table
20+
// Format organizations as a table
1921
const output =
2022
`Organization Name | Organization ID
2123
----------------| ----------------
@@ -26,7 +28,10 @@ export class ListOrganizationsTool extends AtlasToolBase {
2628
})
2729
.join("\n");
2830
return {
29-
content: [{ type: "text", text: output }],
31+
content: formatUntrustedData(
32+
`Found ${data.results.length} organizations in your MongoDB Atlas account.`,
33+
output
34+
),
3035
};
3136
}
3237
}

src/tools/atlas/read/listProjects.ts

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
22
import { AtlasToolBase } from "../atlasTool.js";
3-
import { OperationType } from "../../tool.js";
3+
import { formatUntrustedData, OperationType } from "../../tool.js";
44
import { z } from "zod";
55
import { ToolArgs } from "../../tool.js";
66

@@ -16,7 +16,9 @@ export class ListProjectsTool extends AtlasToolBase {
1616
const orgData = await this.session.apiClient.listOrganizations();
1717

1818
if (!orgData?.results?.length) {
19-
throw new Error("No organizations found in your MongoDB Atlas account.");
19+
return {
20+
content: [{ type: "text", text: "No organizations found in your MongoDB Atlas account." }],
21+
};
2022
}
2123

2224
const orgs: Record<string, string> = orgData.results
@@ -35,7 +37,9 @@ export class ListProjectsTool extends AtlasToolBase {
3537
: await this.session.apiClient.listProjects();
3638

3739
if (!data?.results?.length) {
38-
throw new Error("No projects found in your MongoDB Atlas account.");
40+
return {
41+
content: [{ type: "text", text: `No projects found in organization ${orgId}.` }],
42+
};
3943
}
4044

4145
// Format projects as a table
@@ -50,7 +54,7 @@ export class ListProjectsTool extends AtlasToolBase {
5054
----------------| ----------------| ----------------| ----------------| ----------------
5155
${rows}`;
5256
return {
53-
content: [{ type: "text", text: formattedProjects }],
57+
content: formatUntrustedData(`Found ${rows.length} projects`, formattedProjects),
5458
};
5559
}
5660
}

src/tools/mongodb/metadata/collectionSchema.ts

Lines changed: 5 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
22
import { DbOperationArgs, MongoDBToolBase } from "../mongodbTool.js";
3-
import { ToolArgs, OperationType } from "../../tool.js";
3+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
44
import { getSimplifiedSchema } from "mongodb-schema";
55

66
export class CollectionSchemaTool extends MongoDBToolBase {
@@ -28,16 +28,10 @@ export class CollectionSchemaTool extends MongoDBToolBase {
2828
}
2929

3030
return {
31-
content: [
32-
{
33-
text: `Found ${fieldsCount} fields in the schema for "${database}.${collection}"`,
34-
type: "text",
35-
},
36-
{
37-
text: JSON.stringify(schema),
38-
type: "text",
39-
},
40-
],
31+
content: formatUntrustedData(
32+
`Found ${fieldsCount} fields in the schema for "${database}.${collection}"`,
33+
JSON.stringify(schema)
34+
),
4135
};
4236
}
4337
}

src/tools/mongodb/metadata/dbStats.ts

Lines changed: 2 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { CallToolResult } from "@modelcontextprotocol/sdk/types.js";
22
import { DbOperationArgs, MongoDBToolBase } from "../mongodbTool.js";
3-
import { ToolArgs, OperationType } from "../../tool.js";
3+
import { ToolArgs, OperationType, formatUntrustedData } from "../../tool.js";
44
import { EJSON } from "bson";
55

66
export class DbStatsTool extends MongoDBToolBase {
@@ -20,16 +20,7 @@ export class DbStatsTool extends MongoDBToolBase {
2020
});
2121

2222
return {
23-
content: [
24-
{
25-
text: `Statistics for database ${database}`,
26-
type: "text",
27-
},
28-
{
29-
text: EJSON.stringify(result),
30-
type: "text",
31-
},
32-
],
23+
content: formatUntrustedData(`Statistics for database ${database}`, EJSON.stringify(result)),
3324
};
3425
}
3526
}

0 commit comments

Comments
 (0)