mongodb-mcp-server 0.1.2 → 0.2.0
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/.github/pull_request_template.md +5 -0
- package/.github/workflows/accuracy-tests.yml +55 -0
- package/.github/workflows/check.yml +1 -1
- package/.github/workflows/code_health.yaml +4 -4
- package/.github/workflows/code_health_fork.yaml +0 -14
- package/.github/workflows/dependabot_pr.yaml +26 -0
- package/.github/workflows/docker.yaml +1 -1
- package/.github/workflows/jira-issue.yml +72 -0
- package/.smithery/smithery.yaml +10 -0
- package/.vscode/extensions.json +1 -1
- package/.vscode/launch.json +11 -1
- package/.vscode/settings.json +1 -11
- package/Dockerfile +1 -0
- package/README.md +132 -31
- package/dist/common/atlas/accessListUtils.js +36 -0
- package/dist/common/atlas/accessListUtils.js.map +1 -0
- package/dist/common/atlas/apiClient.js +25 -6
- package/dist/common/atlas/apiClient.js.map +1 -1
- package/dist/common/atlas/cluster.js +1 -1
- package/dist/common/atlas/cluster.js.map +1 -1
- package/dist/{config.js → common/config.js} +8 -1
- package/dist/common/config.js.map +1 -0
- package/dist/{errors.js → common/errors.js} +1 -0
- package/dist/common/errors.js.map +1 -0
- package/dist/{logger.js → common/logger.js} +20 -19
- package/dist/common/logger.js.map +1 -0
- package/dist/common/managedTimeout.js +20 -0
- package/dist/common/managedTimeout.js.map +1 -0
- package/dist/common/packageInfo.js.map +1 -0
- package/dist/{session.js → common/session.js} +20 -21
- package/dist/common/session.js.map +1 -0
- package/dist/common/sessionStore.js +73 -0
- package/dist/common/sessionStore.js.map +1 -0
- package/dist/helpers/container.js +28 -0
- package/dist/helpers/container.js.map +1 -0
- package/dist/helpers/generatePassword.js.map +1 -0
- package/dist/helpers/indexCheck.js +63 -0
- package/dist/helpers/indexCheck.js.map +1 -0
- package/dist/index.js +30 -37
- package/dist/index.js.map +1 -1
- package/dist/server.js +44 -7
- package/dist/server.js.map +1 -1
- package/dist/telemetry/constants.js +1 -1
- package/dist/telemetry/constants.js.map +1 -1
- package/dist/telemetry/telemetry.js +86 -116
- package/dist/telemetry/telemetry.js.map +1 -1
- package/dist/tools/atlas/atlasTool.js +3 -3
- package/dist/tools/atlas/atlasTool.js.map +1 -1
- package/dist/tools/atlas/connect/connectCluster.js +198 -0
- package/dist/tools/atlas/connect/connectCluster.js.map +1 -0
- package/dist/tools/atlas/create/createAccessList.js +9 -10
- package/dist/tools/atlas/create/createAccessList.js.map +1 -1
- package/dist/tools/atlas/create/createDBUser.js +3 -1
- package/dist/tools/atlas/create/createDBUser.js.map +1 -1
- package/dist/tools/atlas/create/createFreeCluster.js +2 -0
- package/dist/tools/atlas/create/createFreeCluster.js.map +1 -1
- package/dist/tools/atlas/create/createProject.js.map +1 -1
- package/dist/tools/atlas/read/inspectAccessList.js.map +1 -1
- package/dist/tools/atlas/read/inspectCluster.js.map +1 -1
- package/dist/tools/atlas/read/listAlerts.js.map +1 -1
- package/dist/tools/atlas/read/listClusters.js.map +1 -1
- package/dist/tools/atlas/read/listDBUsers.js.map +1 -1
- package/dist/tools/atlas/read/listOrgs.js.map +1 -1
- package/dist/tools/atlas/read/listProjects.js.map +1 -1
- package/dist/tools/atlas/tools.js +1 -1
- package/dist/tools/atlas/tools.js.map +1 -1
- package/dist/tools/mongodb/{metadata → connect}/connect.js +7 -4
- package/dist/tools/mongodb/connect/connect.js.map +1 -0
- package/dist/tools/mongodb/create/createCollection.js.map +1 -1
- package/dist/tools/mongodb/create/createIndex.js +1 -1
- package/dist/tools/mongodb/create/createIndex.js.map +1 -1
- package/dist/tools/mongodb/create/insertMany.js +1 -1
- package/dist/tools/mongodb/create/insertMany.js.map +1 -1
- package/dist/tools/mongodb/delete/deleteMany.js +20 -1
- package/dist/tools/mongodb/delete/deleteMany.js.map +1 -1
- package/dist/tools/mongodb/delete/dropCollection.js.map +1 -1
- package/dist/tools/mongodb/delete/dropDatabase.js.map +1 -1
- package/dist/tools/mongodb/metadata/collectionSchema.js.map +1 -1
- package/dist/tools/mongodb/metadata/collectionStorageSize.js.map +1 -1
- package/dist/tools/mongodb/metadata/dbStats.js.map +1 -1
- package/dist/tools/mongodb/metadata/explain.js +2 -2
- package/dist/tools/mongodb/metadata/explain.js.map +1 -1
- package/dist/tools/mongodb/metadata/listCollections.js.map +1 -1
- package/dist/tools/mongodb/metadata/listDatabases.js.map +1 -1
- package/dist/tools/mongodb/metadata/logs.js.map +1 -1
- package/dist/tools/mongodb/mongodbTool.js +47 -10
- package/dist/tools/mongodb/mongodbTool.js.map +1 -1
- package/dist/tools/mongodb/read/aggregate.js +10 -1
- package/dist/tools/mongodb/read/aggregate.js.map +1 -1
- package/dist/tools/mongodb/read/collectionIndexes.js.map +1 -1
- package/dist/tools/mongodb/read/count.js +15 -1
- package/dist/tools/mongodb/read/count.js.map +1 -1
- package/dist/tools/mongodb/read/find.js +14 -4
- package/dist/tools/mongodb/read/find.js.map +1 -1
- package/dist/tools/mongodb/tools.js +1 -1
- package/dist/tools/mongodb/tools.js.map +1 -1
- package/dist/tools/mongodb/update/renameCollection.js.map +1 -1
- package/dist/tools/mongodb/update/updateMany.js +24 -2
- package/dist/tools/mongodb/update/updateMany.js.map +1 -1
- package/dist/tools/tool.js +12 -9
- package/dist/tools/tool.js.map +1 -1
- package/dist/transports/base.js +26 -0
- package/dist/transports/base.js.map +1 -0
- package/dist/{helpers/EJsonTransport.js → transports/stdio.js} +24 -2
- package/dist/transports/stdio.js.map +1 -0
- package/dist/transports/streamableHttp.js +140 -0
- package/dist/transports/streamableHttp.js.map +1 -0
- package/eslint.config.js +13 -4
- package/package.json +43 -33
- package/resources/test-summary-template.html +415 -0
- package/scripts/accuracy/generateTestSummary.ts +335 -0
- package/scripts/accuracy/runAccuracyTests.sh +45 -0
- package/scripts/accuracy/updateAccuracyRunStatus.ts +21 -0
- package/src/common/atlas/accessListUtils.ts +54 -0
- package/src/common/atlas/apiClient.ts +25 -6
- package/src/common/atlas/cluster.ts +1 -1
- package/src/{config.ts → common/config.ts} +16 -2
- package/src/{errors.ts → common/errors.ts} +1 -0
- package/src/{logger.ts → common/logger.ts} +21 -24
- package/src/common/managedTimeout.ts +27 -0
- package/src/{session.ts → common/session.ts} +24 -26
- package/src/common/sessionStore.ts +111 -0
- package/src/helpers/container.ts +35 -0
- package/src/helpers/indexCheck.ts +83 -0
- package/src/index.ts +30 -40
- package/src/server.ts +55 -11
- package/src/telemetry/constants.ts +1 -1
- package/src/telemetry/telemetry.ts +109 -153
- package/src/telemetry/types.ts +2 -1
- package/src/tools/atlas/atlasTool.ts +4 -4
- package/src/tools/atlas/connect/connectCluster.ts +259 -0
- package/src/tools/atlas/create/createAccessList.ts +15 -13
- package/src/tools/atlas/create/createDBUser.ts +5 -3
- package/src/tools/atlas/create/createFreeCluster.ts +4 -2
- package/src/tools/atlas/create/createProject.ts +2 -2
- package/src/tools/atlas/read/inspectAccessList.ts +2 -2
- package/src/tools/atlas/read/inspectCluster.ts +2 -2
- package/src/tools/atlas/read/listAlerts.ts +2 -2
- package/src/tools/atlas/read/listClusters.ts +2 -2
- package/src/tools/atlas/read/listDBUsers.ts +2 -2
- package/src/tools/atlas/read/listOrgs.ts +2 -2
- package/src/tools/atlas/read/listProjects.ts +2 -2
- package/src/tools/atlas/tools.ts +1 -1
- package/src/tools/mongodb/{metadata → connect}/connect.ts +12 -9
- package/src/tools/mongodb/create/createCollection.ts +2 -2
- package/src/tools/mongodb/create/createIndex.ts +3 -3
- package/src/tools/mongodb/create/insertMany.ts +3 -3
- package/src/tools/mongodb/delete/deleteMany.ts +24 -3
- package/src/tools/mongodb/delete/dropCollection.ts +2 -2
- package/src/tools/mongodb/delete/dropDatabase.ts +2 -2
- package/src/tools/mongodb/metadata/collectionSchema.ts +2 -2
- package/src/tools/mongodb/metadata/collectionStorageSize.ts +2 -2
- package/src/tools/mongodb/metadata/dbStats.ts +2 -2
- package/src/tools/mongodb/metadata/explain.ts +4 -4
- package/src/tools/mongodb/metadata/listCollections.ts +2 -2
- package/src/tools/mongodb/metadata/listDatabases.ts +2 -2
- package/src/tools/mongodb/metadata/logs.ts +2 -2
- package/src/tools/mongodb/mongodbTool.ts +60 -14
- package/src/tools/mongodb/read/aggregate.ts +14 -3
- package/src/tools/mongodb/read/collectionIndexes.ts +2 -2
- package/src/tools/mongodb/read/count.ts +19 -3
- package/src/tools/mongodb/read/find.ts +20 -6
- package/src/tools/mongodb/tools.ts +1 -1
- package/src/tools/mongodb/update/renameCollection.ts +2 -2
- package/src/tools/mongodb/update/updateMany.ts +28 -4
- package/src/tools/tool.ts +23 -18
- package/src/transports/base.ts +34 -0
- package/src/{helpers/EJsonTransport.ts → transports/stdio.ts} +30 -1
- package/src/transports/streamableHttp.ts +178 -0
- package/tests/accuracy/aggregate.test.ts +27 -0
- package/tests/accuracy/collectionIndexes.test.ts +40 -0
- package/tests/accuracy/collectionSchema.test.ts +28 -0
- package/tests/accuracy/collectionStorageSize.test.ts +41 -0
- package/tests/accuracy/count.test.ts +44 -0
- package/tests/accuracy/createCollection.test.ts +46 -0
- package/tests/accuracy/createIndex.test.ts +37 -0
- package/tests/accuracy/dbStats.test.ts +15 -0
- package/tests/accuracy/deleteMany.test.ts +44 -0
- package/tests/accuracy/dropCollection.test.ts +74 -0
- package/tests/accuracy/dropDatabase.test.ts +41 -0
- package/tests/accuracy/explain.test.ts +73 -0
- package/tests/accuracy/find.test.ts +114 -0
- package/tests/accuracy/insertMany.test.ts +48 -0
- package/tests/accuracy/listCollections.test.ts +60 -0
- package/tests/accuracy/listDatabases.test.ts +31 -0
- package/tests/accuracy/logs.test.ts +28 -0
- package/tests/accuracy/renameCollection.test.ts +31 -0
- package/tests/accuracy/sdk/accuracyResultStorage/diskStorage.ts +189 -0
- package/tests/accuracy/sdk/accuracyResultStorage/getAccuracyResultStorage.ts +11 -0
- package/tests/accuracy/sdk/accuracyResultStorage/mongodbStorage.ts +151 -0
- package/tests/accuracy/sdk/accuracyResultStorage/resultStorage.ts +117 -0
- package/tests/accuracy/sdk/accuracyScorer.ts +93 -0
- package/tests/accuracy/sdk/accuracyTestingClient.ts +94 -0
- package/tests/accuracy/sdk/agent.ts +56 -0
- package/tests/accuracy/sdk/constants.ts +26 -0
- package/tests/accuracy/sdk/describeAccuracyTests.ts +126 -0
- package/tests/accuracy/sdk/gitInfo.ts +7 -0
- package/tests/accuracy/sdk/matcher.ts +193 -0
- package/tests/accuracy/sdk/models.ts +95 -0
- package/tests/accuracy/test-data-dumps/comics.books.json +417 -0
- package/tests/accuracy/test-data-dumps/comics.characters.json +402 -0
- package/tests/accuracy/test-data-dumps/mflix.movies.json +496 -0
- package/tests/accuracy/test-data-dumps/mflix.shows.json +572 -0
- package/tests/accuracy/updateMany.test.ts +42 -0
- package/tests/integration/helpers.ts +9 -9
- package/tests/integration/indexCheck.test.ts +464 -0
- package/tests/integration/server.test.ts +6 -4
- package/tests/integration/telemetry.test.ts +29 -0
- package/tests/integration/tools/atlas/accessLists.test.ts +22 -2
- package/tests/integration/tools/atlas/alerts.test.ts +3 -2
- package/tests/integration/tools/atlas/atlasHelpers.ts +3 -0
- package/tests/integration/tools/atlas/clusters.test.ts +68 -16
- package/tests/integration/tools/atlas/dbUsers.test.ts +14 -1
- package/tests/integration/tools/atlas/orgs.test.ts +2 -1
- package/tests/integration/tools/atlas/projects.test.ts +4 -3
- package/tests/integration/tools/mongodb/{metadata → connect}/connect.test.ts +34 -3
- package/tests/integration/tools/mongodb/create/createCollection.test.ts +1 -0
- package/tests/integration/tools/mongodb/create/createIndex.test.ts +1 -0
- package/tests/integration/tools/mongodb/create/insertMany.test.ts +1 -0
- package/tests/integration/tools/mongodb/delete/deleteMany.test.ts +1 -0
- package/tests/integration/tools/mongodb/delete/dropCollection.test.ts +1 -1
- package/tests/integration/tools/mongodb/delete/dropDatabase.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/collectionSchema.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/collectionStorageSize.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/dbStats.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/explain.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/listCollections.test.ts +1 -0
- package/tests/integration/tools/mongodb/metadata/listDatabases.test.ts +3 -2
- package/tests/integration/tools/mongodb/metadata/logs.test.ts +1 -0
- package/tests/integration/tools/mongodb/mongodbHelpers.ts +67 -2
- package/tests/integration/tools/mongodb/read/aggregate.test.ts +2 -1
- package/tests/integration/tools/mongodb/read/collectionIndexes.test.ts +1 -0
- package/tests/integration/tools/mongodb/read/count.test.ts +1 -0
- package/tests/integration/tools/mongodb/read/find.test.ts +2 -1
- package/tests/integration/tools/mongodb/update/renameCollection.test.ts +1 -0
- package/tests/integration/tools/mongodb/update/updateMany.test.ts +1 -0
- package/tests/integration/transports/stdio.test.ts +40 -0
- package/tests/integration/transports/streamableHttp.test.ts +56 -0
- package/tests/matchers/toIncludeSameMembers.test.ts +59 -0
- package/tests/matchers/toIncludeSameMembers.ts +12 -0
- package/tests/setup.ts +7 -0
- package/tests/unit/accessListUtils.test.ts +39 -0
- package/tests/unit/accuracyScorer.test.ts +390 -0
- package/tests/unit/{apiClient.test.ts → common/apiClient.test.ts} +15 -15
- package/tests/unit/common/managedTimeout.test.ts +67 -0
- package/tests/unit/{session.test.ts → common/session.test.ts} +7 -12
- package/tests/unit/helpers/indexCheck.test.ts +150 -0
- package/tests/unit/telemetry.test.ts +99 -137
- package/tests/unit/{EJsonTransport.test.ts → transports/stdio.test.ts} +4 -4
- package/tests/vitest.d.ts +11 -0
- package/tsconfig.json +0 -1
- package/{tsconfig.jest.json → tsconfig.test.json} +1 -2
- package/vitest.config.ts +41 -0
- package/dist/common/atlas/generatePassword.js.map +0 -1
- package/dist/config.js.map +0 -1
- package/dist/errors.js.map +0 -1
- package/dist/helpers/EJsonTransport.js.map +0 -1
- package/dist/helpers/packageInfo.js.map +0 -1
- package/dist/logger.js.map +0 -1
- package/dist/session.js.map +0 -1
- package/dist/tools/atlas/metadata/connectCluster.js +0 -100
- package/dist/tools/atlas/metadata/connectCluster.js.map +0 -1
- package/dist/tools/mongodb/metadata/connect.js.map +0 -1
- package/global.d.ts +0 -1
- package/jest.config.cjs +0 -22
- package/src/tools/atlas/metadata/connectCluster.ts +0 -121
- /package/dist/{helpers → common}/packageInfo.js +0 -0
- /package/dist/{common/atlas → helpers}/generatePassword.js +0 -0
- /package/src/{helpers → common}/packageInfo.ts +0 -0
- /package/src/{common/atlas → helpers}/generatePassword.ts +0 -0
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import { afterAll, beforeAll, describe, expect, it, vi } from "vitest";
|
|
2
|
+
import { setManagedTimeout } from "../../../src/common/managedTimeout.js";
|
|
3
|
+
|
|
4
|
+
describe("setManagedTimeout", () => {
|
|
5
|
+
beforeAll(() => {
|
|
6
|
+
vi.useFakeTimers();
|
|
7
|
+
});
|
|
8
|
+
|
|
9
|
+
afterAll(() => {
|
|
10
|
+
vi.useRealTimers();
|
|
11
|
+
});
|
|
12
|
+
|
|
13
|
+
it("calls the timeout callback", () => {
|
|
14
|
+
const callback = vi.fn();
|
|
15
|
+
|
|
16
|
+
setManagedTimeout(callback, 1000);
|
|
17
|
+
|
|
18
|
+
vi.advanceTimersByTime(1000);
|
|
19
|
+
expect(callback).toHaveBeenCalled();
|
|
20
|
+
});
|
|
21
|
+
|
|
22
|
+
it("does not call the timeout callback if the timeout is cleared", () => {
|
|
23
|
+
const callback = vi.fn();
|
|
24
|
+
|
|
25
|
+
const timeout = setManagedTimeout(callback, 1000);
|
|
26
|
+
|
|
27
|
+
vi.advanceTimersByTime(500);
|
|
28
|
+
timeout.cancel();
|
|
29
|
+
vi.advanceTimersByTime(500);
|
|
30
|
+
|
|
31
|
+
expect(callback).not.toHaveBeenCalled();
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
it("does not call the timeout callback if the timeout is reset", () => {
|
|
35
|
+
const callback = vi.fn();
|
|
36
|
+
|
|
37
|
+
const timeout = setManagedTimeout(callback, 1000);
|
|
38
|
+
|
|
39
|
+
vi.advanceTimersByTime(500);
|
|
40
|
+
timeout.restart();
|
|
41
|
+
vi.advanceTimersByTime(500);
|
|
42
|
+
expect(callback).not.toHaveBeenCalled();
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
describe("if timeout is reset", () => {
|
|
46
|
+
it("does not call the timeout callback within the timeout period", () => {
|
|
47
|
+
const callback = vi.fn();
|
|
48
|
+
|
|
49
|
+
const timeout = setManagedTimeout(callback, 1000);
|
|
50
|
+
|
|
51
|
+
vi.advanceTimersByTime(500);
|
|
52
|
+
timeout.restart();
|
|
53
|
+
vi.advanceTimersByTime(500);
|
|
54
|
+
expect(callback).not.toHaveBeenCalled();
|
|
55
|
+
});
|
|
56
|
+
it("calls the timeout callback after the timeout period", () => {
|
|
57
|
+
const callback = vi.fn();
|
|
58
|
+
|
|
59
|
+
const timeout = setManagedTimeout(callback, 1000);
|
|
60
|
+
|
|
61
|
+
vi.advanceTimersByTime(500);
|
|
62
|
+
timeout.restart();
|
|
63
|
+
vi.advanceTimersByTime(1000);
|
|
64
|
+
expect(callback).toHaveBeenCalled();
|
|
65
|
+
});
|
|
66
|
+
});
|
|
67
|
+
});
|
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { beforeEach, describe, expect, it, vi } from "vitest";
|
|
2
2
|
import { NodeDriverServiceProvider } from "@mongosh/service-provider-node-driver";
|
|
3
|
-
import { Session } from "
|
|
4
|
-
import { config } from "
|
|
3
|
+
import { Session } from "../../../src/common/session.js";
|
|
4
|
+
import { config } from "../../../src/common/config.js";
|
|
5
5
|
|
|
6
|
-
|
|
7
|
-
const MockNodeDriverServiceProvider =
|
|
6
|
+
vi.mock("@mongosh/service-provider-node-driver");
|
|
7
|
+
const MockNodeDriverServiceProvider = vi.mocked(NodeDriverServiceProvider);
|
|
8
8
|
|
|
9
9
|
describe("Session", () => {
|
|
10
10
|
let session: Session;
|
|
@@ -14,9 +14,7 @@ describe("Session", () => {
|
|
|
14
14
|
apiBaseUrl: "https://api.test.com",
|
|
15
15
|
});
|
|
16
16
|
|
|
17
|
-
MockNodeDriverServiceProvider.connect =
|
|
18
|
-
Promise.resolve({} as unknown as NodeDriverServiceProvider)
|
|
19
|
-
);
|
|
17
|
+
MockNodeDriverServiceProvider.connect = vi.fn().mockResolvedValue({} as unknown as NodeDriverServiceProvider);
|
|
20
18
|
});
|
|
21
19
|
|
|
22
20
|
describe("connectToMongoDB", () => {
|
|
@@ -48,10 +46,7 @@ describe("Session", () => {
|
|
|
48
46
|
await session.connectToMongoDB(testCase.connectionString, config.connectOptions);
|
|
49
47
|
expect(session.serviceProvider).toBeDefined();
|
|
50
48
|
|
|
51
|
-
|
|
52
|
-
const connectMock = MockNodeDriverServiceProvider.connect as jest.Mock<
|
|
53
|
-
typeof NodeDriverServiceProvider.connect
|
|
54
|
-
>;
|
|
49
|
+
const connectMock = MockNodeDriverServiceProvider.connect;
|
|
55
50
|
expect(connectMock).toHaveBeenCalledOnce();
|
|
56
51
|
const connectionString = connectMock.mock.calls[0]?.[0];
|
|
57
52
|
if (testCase.expectAppName) {
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
import { describe, expect, it } from "vitest";
|
|
2
|
+
import { usesIndex, getIndexCheckErrorMessage } from "../../../src/helpers/indexCheck.js";
|
|
3
|
+
import { Document } from "mongodb";
|
|
4
|
+
|
|
5
|
+
describe("indexCheck", () => {
|
|
6
|
+
describe("usesIndex", () => {
|
|
7
|
+
it("should return true for IXSCAN", () => {
|
|
8
|
+
const explainResult: Document = {
|
|
9
|
+
queryPlanner: {
|
|
10
|
+
winningPlan: {
|
|
11
|
+
stage: "IXSCAN",
|
|
12
|
+
},
|
|
13
|
+
},
|
|
14
|
+
};
|
|
15
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
it("should return true for COUNT_SCAN", () => {
|
|
19
|
+
const explainResult: Document = {
|
|
20
|
+
queryPlanner: {
|
|
21
|
+
winningPlan: {
|
|
22
|
+
stage: "COUNT_SCAN",
|
|
23
|
+
},
|
|
24
|
+
},
|
|
25
|
+
};
|
|
26
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
it("should return true for IDHACK", () => {
|
|
30
|
+
const explainResult: Document = {
|
|
31
|
+
queryPlanner: {
|
|
32
|
+
winningPlan: {
|
|
33
|
+
stage: "IDHACK",
|
|
34
|
+
},
|
|
35
|
+
},
|
|
36
|
+
};
|
|
37
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
it("should return true for EXPRESS_IXSCAN (MongoDB 8.0+)", () => {
|
|
41
|
+
const explainResult: Document = {
|
|
42
|
+
queryPlanner: {
|
|
43
|
+
winningPlan: {
|
|
44
|
+
stage: "EXPRESS_IXSCAN",
|
|
45
|
+
},
|
|
46
|
+
},
|
|
47
|
+
};
|
|
48
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
it("should return true for EXPRESS_CLUSTERED_IXSCAN (MongoDB 8.0+)", () => {
|
|
52
|
+
const explainResult: Document = {
|
|
53
|
+
queryPlanner: {
|
|
54
|
+
winningPlan: {
|
|
55
|
+
stage: "EXPRESS_CLUSTERED_IXSCAN",
|
|
56
|
+
},
|
|
57
|
+
},
|
|
58
|
+
};
|
|
59
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
it("should return true for EXPRESS_UPDATE (MongoDB 8.0+)", () => {
|
|
63
|
+
const explainResult: Document = {
|
|
64
|
+
queryPlanner: {
|
|
65
|
+
winningPlan: {
|
|
66
|
+
stage: "EXPRESS_UPDATE",
|
|
67
|
+
},
|
|
68
|
+
},
|
|
69
|
+
};
|
|
70
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
71
|
+
});
|
|
72
|
+
|
|
73
|
+
it("should return true for EXPRESS_DELETE (MongoDB 8.0+)", () => {
|
|
74
|
+
const explainResult: Document = {
|
|
75
|
+
queryPlanner: {
|
|
76
|
+
winningPlan: {
|
|
77
|
+
stage: "EXPRESS_DELETE",
|
|
78
|
+
},
|
|
79
|
+
},
|
|
80
|
+
};
|
|
81
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
82
|
+
});
|
|
83
|
+
|
|
84
|
+
it("should return false for COLLSCAN", () => {
|
|
85
|
+
const explainResult: Document = {
|
|
86
|
+
queryPlanner: {
|
|
87
|
+
winningPlan: {
|
|
88
|
+
stage: "COLLSCAN",
|
|
89
|
+
},
|
|
90
|
+
},
|
|
91
|
+
};
|
|
92
|
+
expect(usesIndex(explainResult)).toBe(false);
|
|
93
|
+
});
|
|
94
|
+
|
|
95
|
+
it("should return true for nested IXSCAN in inputStage", () => {
|
|
96
|
+
const explainResult: Document = {
|
|
97
|
+
queryPlanner: {
|
|
98
|
+
winningPlan: {
|
|
99
|
+
stage: "LIMIT",
|
|
100
|
+
inputStage: {
|
|
101
|
+
stage: "IXSCAN",
|
|
102
|
+
},
|
|
103
|
+
},
|
|
104
|
+
},
|
|
105
|
+
};
|
|
106
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
it("should return true for nested EXPRESS_IXSCAN in inputStage", () => {
|
|
110
|
+
const explainResult: Document = {
|
|
111
|
+
queryPlanner: {
|
|
112
|
+
winningPlan: {
|
|
113
|
+
stage: "SORT",
|
|
114
|
+
inputStage: {
|
|
115
|
+
stage: "EXPRESS_IXSCAN",
|
|
116
|
+
},
|
|
117
|
+
},
|
|
118
|
+
},
|
|
119
|
+
};
|
|
120
|
+
expect(usesIndex(explainResult)).toBe(true);
|
|
121
|
+
});
|
|
122
|
+
|
|
123
|
+
it("should return false for unknown stage types", () => {
|
|
124
|
+
const explainResult: Document = {
|
|
125
|
+
queryPlanner: {
|
|
126
|
+
winningPlan: {
|
|
127
|
+
stage: "UNKNOWN_STAGE",
|
|
128
|
+
},
|
|
129
|
+
},
|
|
130
|
+
};
|
|
131
|
+
expect(usesIndex(explainResult)).toBe(false);
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
it("should handle missing queryPlanner", () => {
|
|
135
|
+
const explainResult: Document = {};
|
|
136
|
+
expect(usesIndex(explainResult)).toBe(false);
|
|
137
|
+
});
|
|
138
|
+
});
|
|
139
|
+
|
|
140
|
+
describe("getIndexCheckErrorMessage", () => {
|
|
141
|
+
it("should generate appropriate error message", () => {
|
|
142
|
+
const message = getIndexCheckErrorMessage("testdb", "testcoll", "find");
|
|
143
|
+
expect(message).toContain("Index check failed");
|
|
144
|
+
expect(message).toContain("testdb.testcoll");
|
|
145
|
+
expect(message).toContain("find operation");
|
|
146
|
+
expect(message).toContain("collection scan (COLLSCAN)");
|
|
147
|
+
expect(message).toContain("MDB_MCP_INDEX_CHECK");
|
|
148
|
+
});
|
|
149
|
+
});
|
|
150
|
+
});
|
|
@@ -1,36 +1,37 @@
|
|
|
1
1
|
import { ApiClient } from "../../src/common/atlas/apiClient.js";
|
|
2
|
-
import { Session } from "../../src/session.js";
|
|
3
|
-
import { Telemetry } from "../../src/telemetry/telemetry.js";
|
|
2
|
+
import { Session } from "../../src/common/session.js";
|
|
3
|
+
import { DEVICE_ID_TIMEOUT, Telemetry } from "../../src/telemetry/telemetry.js";
|
|
4
4
|
import { BaseEvent, TelemetryResult } from "../../src/telemetry/types.js";
|
|
5
5
|
import { EventCache } from "../../src/telemetry/eventCache.js";
|
|
6
|
-
import { config } from "../../src/config.js";
|
|
7
|
-
import {
|
|
8
|
-
import logger, { LogId } from "../../src/logger.js";
|
|
6
|
+
import { config } from "../../src/common/config.js";
|
|
7
|
+
import { afterEach, beforeEach, describe, it, vi, expect } from "vitest";
|
|
8
|
+
import logger, { LogId } from "../../src/common/logger.js";
|
|
9
9
|
import { createHmac } from "crypto";
|
|
10
|
+
import type { MockedFunction } from "vitest";
|
|
10
11
|
|
|
11
12
|
// Mock the ApiClient to avoid real API calls
|
|
12
|
-
|
|
13
|
-
const MockApiClient =
|
|
13
|
+
vi.mock("../../src/common/atlas/apiClient.js");
|
|
14
|
+
const MockApiClient = vi.mocked(ApiClient);
|
|
14
15
|
|
|
15
16
|
// Mock EventCache to control and verify caching behavior
|
|
16
|
-
|
|
17
|
-
const MockEventCache =
|
|
18
|
-
|
|
19
|
-
const nextTick = () => new Promise((resolve) => process.nextTick(resolve));
|
|
17
|
+
vi.mock("../../src/telemetry/eventCache.js");
|
|
18
|
+
const MockEventCache = vi.mocked(EventCache);
|
|
20
19
|
|
|
21
20
|
describe("Telemetry", () => {
|
|
22
21
|
const machineId = "test-machine-id";
|
|
23
22
|
const hashedMachineId = createHmac("sha256", machineId.toUpperCase()).update("atlascli").digest("hex");
|
|
24
23
|
|
|
25
|
-
let mockApiClient:
|
|
26
|
-
|
|
24
|
+
let mockApiClient: {
|
|
25
|
+
sendEvents: MockedFunction<(events: BaseEvent[]) => Promise<void>>;
|
|
26
|
+
hasCredentials: MockedFunction<() => boolean>;
|
|
27
|
+
};
|
|
28
|
+
let mockEventCache: {
|
|
29
|
+
getEvents: MockedFunction<() => BaseEvent[]>;
|
|
30
|
+
clearEvents: MockedFunction<() => Promise<void>>;
|
|
31
|
+
appendEvents: MockedFunction<(events: BaseEvent[]) => Promise<void>>;
|
|
32
|
+
};
|
|
27
33
|
let session: Session;
|
|
28
34
|
let telemetry: Telemetry;
|
|
29
|
-
let telemetryConfig: {
|
|
30
|
-
eventCache: EventCache;
|
|
31
|
-
getRawMachineId: () => Promise<string>;
|
|
32
|
-
getContainerEnv: () => Promise<boolean>;
|
|
33
|
-
};
|
|
34
35
|
|
|
35
36
|
// Helper function to create properly typed test events
|
|
36
37
|
function createTestEvent(options?: {
|
|
@@ -84,53 +85,52 @@ describe("Telemetry", () => {
|
|
|
84
85
|
expect(appendEvents.length).toBe(appendEventsCalls);
|
|
85
86
|
|
|
86
87
|
if (sendEventsCalledWith) {
|
|
87
|
-
expect(sendEvents[0]?.[0]).
|
|
88
|
+
expect(sendEvents[0]?.[0]).toEqual(
|
|
89
|
+
sendEventsCalledWith.map((event) => ({
|
|
90
|
+
...event,
|
|
91
|
+
properties: {
|
|
92
|
+
...telemetry.getCommonProperties(),
|
|
93
|
+
...event.properties,
|
|
94
|
+
},
|
|
95
|
+
}))
|
|
96
|
+
);
|
|
88
97
|
}
|
|
89
98
|
|
|
90
99
|
if (appendEventsCalledWith) {
|
|
91
|
-
expect(appendEvents[0]?.[0]).
|
|
100
|
+
expect(appendEvents[0]?.[0]).toEqual(appendEventsCalledWith);
|
|
92
101
|
}
|
|
93
102
|
}
|
|
94
103
|
|
|
95
104
|
beforeEach(() => {
|
|
96
105
|
// Reset mocks before each test
|
|
97
|
-
|
|
106
|
+
vi.clearAllMocks();
|
|
98
107
|
|
|
99
108
|
// Setup mocked API client
|
|
100
|
-
mockApiClient = new MockApiClient({ baseUrl: "" })
|
|
101
|
-
|
|
102
|
-
mockApiClient.sendEvents =
|
|
103
|
-
mockApiClient.hasCredentials =
|
|
109
|
+
mockApiClient = vi.mocked(new MockApiClient({ baseUrl: "" }));
|
|
110
|
+
|
|
111
|
+
mockApiClient.sendEvents = vi.fn().mockResolvedValue(undefined);
|
|
112
|
+
mockApiClient.hasCredentials = vi.fn().mockReturnValue(true);
|
|
104
113
|
|
|
105
114
|
// Setup mocked EventCache
|
|
106
|
-
mockEventCache = new MockEventCache() as
|
|
107
|
-
|
|
108
|
-
mockEventCache.
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
//@ts-expect-error This is a workaround
|
|
112
|
-
mockEventCache.appendEvents = jest.fn().mockResolvedValue(undefined);
|
|
113
|
-
//@ts-expect-error This is a workaround
|
|
114
|
-
MockEventCache.getInstance = jest.fn().mockReturnValue(mockEventCache);
|
|
115
|
+
mockEventCache = new MockEventCache() as unknown as typeof mockEventCache;
|
|
116
|
+
mockEventCache.getEvents = vi.fn().mockReturnValue([]);
|
|
117
|
+
mockEventCache.clearEvents = vi.fn().mockResolvedValue(undefined);
|
|
118
|
+
mockEventCache.appendEvents = vi.fn().mockResolvedValue(undefined);
|
|
119
|
+
MockEventCache.getInstance = vi.fn().mockReturnValue(mockEventCache as unknown as EventCache);
|
|
115
120
|
|
|
116
121
|
// Create a simplified session with our mocked API client
|
|
117
122
|
session = {
|
|
118
|
-
apiClient: mockApiClient,
|
|
123
|
+
apiClient: mockApiClient as unknown as ApiClient,
|
|
119
124
|
sessionId: "test-session-id",
|
|
120
125
|
agentRunner: { name: "test-agent", version: "1.0.0" } as const,
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
//@ts-expect-error This is a workaround
|
|
124
|
-
setAgentRunner: jest.fn().mockResolvedValue(undefined),
|
|
126
|
+
close: vi.fn().mockResolvedValue(undefined),
|
|
127
|
+
setAgentRunner: vi.fn().mockResolvedValue(undefined),
|
|
125
128
|
} as unknown as Session;
|
|
126
129
|
|
|
127
|
-
|
|
128
|
-
eventCache: mockEventCache,
|
|
130
|
+
telemetry = Telemetry.create(session, config, {
|
|
131
|
+
eventCache: mockEventCache as unknown as EventCache,
|
|
129
132
|
getRawMachineId: () => Promise.resolve(machineId),
|
|
130
|
-
|
|
131
|
-
};
|
|
132
|
-
|
|
133
|
-
telemetry = Telemetry.create(session, config, telemetryConfig);
|
|
133
|
+
});
|
|
134
134
|
|
|
135
135
|
config.telemetry = "enabled";
|
|
136
136
|
});
|
|
@@ -140,8 +140,9 @@ describe("Telemetry", () => {
|
|
|
140
140
|
it("should send events successfully", async () => {
|
|
141
141
|
const testEvent = createTestEvent();
|
|
142
142
|
|
|
143
|
-
telemetry.
|
|
144
|
-
|
|
143
|
+
await telemetry.setupPromise;
|
|
144
|
+
|
|
145
|
+
await telemetry.emitEvents([testEvent]);
|
|
145
146
|
|
|
146
147
|
verifyMockCalls({
|
|
147
148
|
sendEventsCalls: 1,
|
|
@@ -155,8 +156,9 @@ describe("Telemetry", () => {
|
|
|
155
156
|
|
|
156
157
|
const testEvent = createTestEvent();
|
|
157
158
|
|
|
158
|
-
telemetry.
|
|
159
|
-
|
|
159
|
+
await telemetry.setupPromise;
|
|
160
|
+
|
|
161
|
+
await telemetry.emitEvents([testEvent]);
|
|
160
162
|
|
|
161
163
|
verifyMockCalls({
|
|
162
164
|
sendEventsCalls: 1,
|
|
@@ -179,8 +181,9 @@ describe("Telemetry", () => {
|
|
|
179
181
|
// Set up mock to return cached events
|
|
180
182
|
mockEventCache.getEvents.mockReturnValueOnce([cachedEvent]);
|
|
181
183
|
|
|
182
|
-
telemetry.
|
|
183
|
-
|
|
184
|
+
await telemetry.setupPromise;
|
|
185
|
+
|
|
186
|
+
await telemetry.emitEvents([newEvent]);
|
|
184
187
|
|
|
185
188
|
verifyMockCalls({
|
|
186
189
|
sendEventsCalls: 1,
|
|
@@ -190,6 +193,10 @@ describe("Telemetry", () => {
|
|
|
190
193
|
});
|
|
191
194
|
|
|
192
195
|
it("should correctly add common properties to events", async () => {
|
|
196
|
+
await telemetry.setupPromise;
|
|
197
|
+
|
|
198
|
+
const commonProps = telemetry.getCommonProperties();
|
|
199
|
+
|
|
193
200
|
// Use explicit type assertion
|
|
194
201
|
const expectedProps: Record<string, string> = {
|
|
195
202
|
mcp_client_version: "1.0.0",
|
|
@@ -200,86 +207,48 @@ describe("Telemetry", () => {
|
|
|
200
207
|
device_id: hashedMachineId,
|
|
201
208
|
};
|
|
202
209
|
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
telemetry.emitEvents([testEvent]);
|
|
206
|
-
await nextTick(); // wait for the event to be sent
|
|
207
|
-
|
|
208
|
-
const checkEvent = {
|
|
209
|
-
...testEvent,
|
|
210
|
-
properties: {
|
|
211
|
-
...testEvent.properties,
|
|
212
|
-
...expectedProps,
|
|
213
|
-
},
|
|
214
|
-
};
|
|
215
|
-
|
|
216
|
-
verifyMockCalls({
|
|
217
|
-
sendEventsCalls: 1,
|
|
218
|
-
clearEventsCalls: 1,
|
|
219
|
-
sendEventsCalledWith: [checkEvent],
|
|
220
|
-
});
|
|
210
|
+
expect(commonProps).toMatchObject(expectedProps);
|
|
221
211
|
});
|
|
222
212
|
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
213
|
+
describe("machine ID resolution", () => {
|
|
214
|
+
beforeEach(() => {
|
|
215
|
+
vi.clearAllMocks();
|
|
216
|
+
vi.useFakeTimers();
|
|
227
217
|
});
|
|
228
218
|
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
219
|
+
afterEach(() => {
|
|
220
|
+
vi.clearAllMocks();
|
|
221
|
+
vi.useRealTimers();
|
|
232
222
|
});
|
|
233
223
|
|
|
234
|
-
|
|
235
|
-
|
|
224
|
+
it("should successfully resolve the machine ID", async () => {
|
|
225
|
+
telemetry = Telemetry.create(session, config, {
|
|
226
|
+
getRawMachineId: () => Promise.resolve(machineId),
|
|
227
|
+
});
|
|
236
228
|
|
|
237
|
-
|
|
229
|
+
expect(telemetry["isBufferingEvents"]).toBe(true);
|
|
230
|
+
expect(telemetry.getCommonProperties().device_id).toBe(undefined);
|
|
238
231
|
|
|
239
|
-
|
|
240
|
-
sendEventsCalls: 1,
|
|
241
|
-
clearEventsCalls: 1,
|
|
242
|
-
appendEventsCalls: 1,
|
|
243
|
-
sendEventsCalledWith: [newEvent],
|
|
244
|
-
appendEventsCalledWith: [newEvent2],
|
|
245
|
-
});
|
|
246
|
-
});
|
|
232
|
+
await telemetry.setupPromise;
|
|
247
233
|
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
const testEvent = createTestEvent();
|
|
251
|
-
|
|
252
|
-
telemetry.emitEvents([testEvent]);
|
|
253
|
-
await nextTick(); // wait for the event to be sent
|
|
254
|
-
|
|
255
|
-
const checkEvent = {
|
|
256
|
-
...testEvent,
|
|
257
|
-
properties: {
|
|
258
|
-
...testEvent.properties,
|
|
259
|
-
device_id: hashedMachineId,
|
|
260
|
-
},
|
|
261
|
-
};
|
|
262
|
-
|
|
263
|
-
verifyMockCalls({
|
|
264
|
-
sendEventsCalls: 1,
|
|
265
|
-
clearEventsCalls: 1,
|
|
266
|
-
sendEventsCalledWith: [checkEvent],
|
|
267
|
-
});
|
|
234
|
+
expect(telemetry["isBufferingEvents"]).toBe(false);
|
|
235
|
+
expect(telemetry.getCommonProperties().device_id).toBe(hashedMachineId);
|
|
268
236
|
});
|
|
269
237
|
|
|
270
238
|
it("should handle machine ID resolution failure", async () => {
|
|
271
|
-
const loggerSpy =
|
|
239
|
+
const loggerSpy = vi.spyOn(logger, "debug");
|
|
272
240
|
|
|
273
241
|
telemetry = Telemetry.create(session, config, {
|
|
274
|
-
...telemetryConfig,
|
|
275
242
|
getRawMachineId: () => Promise.reject(new Error("Failed to get device ID")),
|
|
276
243
|
});
|
|
277
244
|
|
|
278
|
-
|
|
245
|
+
expect(telemetry["isBufferingEvents"]).toBe(true);
|
|
246
|
+
expect(telemetry.getCommonProperties().device_id).toBe(undefined);
|
|
279
247
|
|
|
280
|
-
telemetry.
|
|
248
|
+
await telemetry.setupPromise;
|
|
281
249
|
|
|
282
|
-
|
|
250
|
+
expect(telemetry["isBufferingEvents"]).toBe(false);
|
|
251
|
+
expect(telemetry.getCommonProperties().device_id).toBe("unknown");
|
|
283
252
|
|
|
284
253
|
expect(loggerSpy).toHaveBeenCalledWith(
|
|
285
254
|
LogId.telemetryDeviceIdFailure,
|
|
@@ -288,28 +257,27 @@ describe("Telemetry", () => {
|
|
|
288
257
|
);
|
|
289
258
|
});
|
|
290
259
|
|
|
291
|
-
it("should timeout if machine ID resolution takes too long", () => {
|
|
292
|
-
const loggerSpy =
|
|
293
|
-
|
|
294
|
-
jest.useFakeTimers();
|
|
260
|
+
it("should timeout if machine ID resolution takes too long", async () => {
|
|
261
|
+
const loggerSpy = vi.spyOn(logger, "debug");
|
|
295
262
|
|
|
296
|
-
telemetry = Telemetry.create(session, config, {
|
|
297
|
-
...telemetryConfig,
|
|
298
|
-
getRawMachineId: () => new Promise(() => {}), // Never resolves
|
|
299
|
-
});
|
|
263
|
+
telemetry = Telemetry.create(session, config, { getRawMachineId: () => new Promise(() => {}) });
|
|
300
264
|
|
|
301
|
-
|
|
265
|
+
expect(telemetry["isBufferingEvents"]).toBe(true);
|
|
266
|
+
expect(telemetry.getCommonProperties().device_id).toBe(undefined);
|
|
302
267
|
|
|
303
|
-
|
|
268
|
+
vi.advanceTimersByTime(DEVICE_ID_TIMEOUT / 2);
|
|
304
269
|
|
|
305
|
-
|
|
270
|
+
// Make sure the timeout doesn't happen prematurely.
|
|
271
|
+
expect(telemetry["isBufferingEvents"]).toBe(true);
|
|
272
|
+
expect(telemetry.getCommonProperties().device_id).toBe(undefined);
|
|
306
273
|
|
|
307
|
-
|
|
274
|
+
vi.advanceTimersByTime(DEVICE_ID_TIMEOUT);
|
|
308
275
|
|
|
309
|
-
|
|
276
|
+
await telemetry.setupPromise;
|
|
310
277
|
|
|
311
|
-
expect(
|
|
312
|
-
|
|
278
|
+
expect(telemetry.getCommonProperties().device_id).toBe("unknown");
|
|
279
|
+
expect(telemetry["isBufferingEvents"]).toBe(false);
|
|
280
|
+
expect(loggerSpy).toHaveBeenCalledWith(
|
|
313
281
|
LogId.telemetryDeviceIdTimeout,
|
|
314
282
|
"telemetry",
|
|
315
283
|
"Device ID retrieval timed out"
|
|
@@ -330,12 +298,9 @@ describe("Telemetry", () => {
|
|
|
330
298
|
it("should not send events", async () => {
|
|
331
299
|
const testEvent = createTestEvent();
|
|
332
300
|
|
|
333
|
-
telemetry.emitEvents([testEvent]);
|
|
334
|
-
await nextTick(); // wait for the event to be sent
|
|
301
|
+
await telemetry.emitEvents([testEvent]);
|
|
335
302
|
|
|
336
|
-
verifyMockCalls(
|
|
337
|
-
sendEventsCalls: 0,
|
|
338
|
-
});
|
|
303
|
+
verifyMockCalls();
|
|
339
304
|
});
|
|
340
305
|
});
|
|
341
306
|
|
|
@@ -358,12 +323,9 @@ describe("Telemetry", () => {
|
|
|
358
323
|
it("should not send events", async () => {
|
|
359
324
|
const testEvent = createTestEvent();
|
|
360
325
|
|
|
361
|
-
telemetry.emitEvents([testEvent]);
|
|
362
|
-
await nextTick(); // wait for the event to be sent
|
|
326
|
+
await telemetry.emitEvents([testEvent]);
|
|
363
327
|
|
|
364
|
-
verifyMockCalls(
|
|
365
|
-
sendEventsCalls: 0,
|
|
366
|
-
});
|
|
328
|
+
verifyMockCalls();
|
|
367
329
|
});
|
|
368
330
|
});
|
|
369
331
|
});
|
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import { Decimal128, MaxKey, MinKey, ObjectId, Timestamp, UUID } from "bson";
|
|
2
|
-
import {
|
|
2
|
+
import { createStdioTransport, EJsonReadBuffer } from "../../../src/transports/stdio.js";
|
|
3
3
|
import { JSONRPCMessage } from "@modelcontextprotocol/sdk/types.js";
|
|
4
4
|
import { AuthInfo } from "@modelcontextprotocol/sdk/server/auth/types.js";
|
|
5
5
|
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
6
6
|
import { Readable } from "stream";
|
|
7
7
|
import { ReadBuffer } from "@modelcontextprotocol/sdk/shared/stdio.js";
|
|
8
|
-
|
|
9
|
-
describe("
|
|
8
|
+
import { describe, expect, it, beforeEach, afterEach } from "vitest";
|
|
9
|
+
describe("stdioTransport", () => {
|
|
10
10
|
let transport: StdioServerTransport;
|
|
11
11
|
beforeEach(async () => {
|
|
12
|
-
transport =
|
|
12
|
+
transport = createStdioTransport();
|
|
13
13
|
await transport.start();
|
|
14
14
|
});
|
|
15
15
|
|
package/tsconfig.json
CHANGED