Skip to content

Commit 873560f

Browse files
committed
fix: updates count tool
1 parent d13f7c6 commit 873560f

File tree

2 files changed

+58
-4
lines changed

2 files changed

+58
-4
lines changed

src/tools/mongodb/read/count.ts

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,16 @@ import { ToolArgs, OperationType } from "../../tool.js";
44
import { z } from "zod";
55

66
export const CountArgs = {
7-
query: z
7+
filter: z
88
.record(z.string(), z.unknown())
99
.optional()
1010
.describe(
11-
"The query filter to count documents. Matches the syntax of the filter argument of db.collection.count()"
11+
"The query filter to count documents. Matches the syntax of the filter argument of db.collection.countDocuments()"
1212
),
13+
query: z
14+
.record(z.string(), z.unknown())
15+
.optional()
16+
.describe("Alternative old name for filter. Will be used in db.collection.countDocuments()"),
1317
};
1418

1519
export class CountTool extends MongoDBToolBase {
@@ -22,9 +26,16 @@ export class CountTool extends MongoDBToolBase {
2226

2327
protected operationType: OperationType = "read";
2428

25-
protected async execute({ database, collection, query }: ToolArgs<typeof this.argsShape>): Promise<CallToolResult> {
29+
protected async execute({
30+
database,
31+
collection,
32+
query,
33+
filter,
34+
}: ToolArgs<typeof this.argsShape>): Promise<CallToolResult> {
2635
const provider = await this.ensureConnected();
27-
const count = await provider.count(database, collection, query);
36+
// use either filter or query, since we're using countDocuments, prefer filter
37+
const queryFilter = filter || query;
38+
const count = await provider.countDocuments(database, collection, queryFilter);
2839

2940
return {
3041
content: [

tests/integration/tools/mongodb/read/count.test.ts

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,12 @@ describeWithMongoDB("count tool", (integration) => {
1616
type: "object",
1717
required: false,
1818
},
19+
{
20+
name: "filter",
21+
description: "Alternative name for query parameter. The query filter to count documents.",
22+
type: "object",
23+
required: false,
24+
},
1925
...databaseCollectionParameters,
2026
]);
2127

@@ -79,6 +85,43 @@ describeWithMongoDB("count tool", (integration) => {
7985
expect(content).toEqual(`Found ${testCase.expectedCount} documents in the collection "foo"`);
8086
});
8187
}
88+
89+
it("correctly filters documents when using 'filter' parameter", async () => {
90+
await integration.connectMcpClient();
91+
92+
// Using 'filter' parameter - should work correctly after the fix
93+
const response = await integration.mcpClient().callTool({
94+
name: "count",
95+
arguments: {
96+
database: integration.randomDbName(),
97+
collection: "foo",
98+
filter: { age: { $lt: 15 } },
99+
},
100+
});
101+
102+
const content = getResponseContent(response.content);
103+
expect(content).toEqual('Found 2 documents in the collection "foo"');
104+
});
105+
106+
it("prioritizes filter over query when both are provided", async () => {
107+
await integration.connectMcpClient();
108+
109+
// Using both 'filter' and 'query' parameters
110+
const response = await integration.mcpClient().callTool({
111+
name: "count",
112+
arguments: {
113+
database: integration.randomDbName(),
114+
collection: "foo",
115+
filter: { age: { $lt: 15 } },
116+
query: { age: { $gt: 10 } },
117+
},
118+
});
119+
120+
const content = getResponseContent(response.content);
121+
// Filter takes precedence over query
122+
// Filter is { age: { $lt: 15 } } which matches 2 documents
123+
expect(content).toEqual('Found 2 documents in the collection "foo"');
124+
});
82125
});
83126

84127
validateAutoConnectBehavior(integration, "count", () => {

0 commit comments

Comments
 (0)