@microsoft/agents-a365-tooling 0.1.0-preview.30
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 +33 -0
- package/dist/cjs/McpToolServerConfigurationService.d.ts +63 -0
- package/dist/cjs/McpToolServerConfigurationService.d.ts.map +1 -0
- package/dist/cjs/McpToolServerConfigurationService.js +146 -0
- package/dist/cjs/McpToolServerConfigurationService.js.map +1 -0
- package/dist/cjs/Utility.d.ts +67 -0
- package/dist/cjs/Utility.d.ts.map +1 -0
- package/dist/cjs/Utility.js +142 -0
- package/dist/cjs/Utility.js.map +1 -0
- package/dist/cjs/contracts.d.ts +21 -0
- package/dist/cjs/contracts.d.ts.map +1 -0
- package/dist/cjs/contracts.js +5 -0
- package/dist/cjs/contracts.js.map +1 -0
- package/dist/cjs/index.d.ts +4 -0
- package/dist/cjs/index.d.ts.map +1 -0
- package/dist/cjs/index.js +20 -0
- package/dist/cjs/index.js.map +1 -0
- package/dist/esm/McpToolServerConfigurationService.d.ts +63 -0
- package/dist/esm/McpToolServerConfigurationService.d.ts.map +1 -0
- package/dist/esm/McpToolServerConfigurationService.js +139 -0
- package/dist/esm/McpToolServerConfigurationService.js.map +1 -0
- package/dist/esm/Utility.d.ts +67 -0
- package/dist/esm/Utility.d.ts.map +1 -0
- package/dist/esm/Utility.js +138 -0
- package/dist/esm/Utility.js.map +1 -0
- package/dist/esm/contracts.d.ts +21 -0
- package/dist/esm/contracts.d.ts.map +1 -0
- package/dist/esm/contracts.js +4 -0
- package/dist/esm/contracts.js.map +1 -0
- package/dist/esm/index.d.ts +4 -0
- package/dist/esm/index.d.ts.map +1 -0
- package/dist/esm/index.js +4 -0
- package/dist/esm/index.js.map +1 -0
- package/package.json +60 -0
package/README.md
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
# @microsoft/agents-a365-tooling
|
|
2
|
+
|
|
3
|
+
[](https://www.npmjs.com/package/@microsoft/agents-a365-tooling)
|
|
4
|
+
[](https://www.npmjs.com/package/@microsoft/agents-a365-tooling)
|
|
5
|
+
|
|
6
|
+
Core tooling functionality for MCP (Model Context Protocol) tool server management in applications built with the Microsoft Agent 365 SDK. This package provides the foundation for discovering, registering, and managing tool servers across different AI frameworks.
|
|
7
|
+
|
|
8
|
+
## Installation
|
|
9
|
+
|
|
10
|
+
```bash
|
|
11
|
+
npm install @microsoft/agents-a365-tooling
|
|
12
|
+
```
|
|
13
|
+
|
|
14
|
+
## Usage
|
|
15
|
+
|
|
16
|
+
For detailed usage examples and implementation guidance, see the [Microsoft Agent 365 Tooling Documentation](https://learn.microsoft.com/microsoft-agent-365/developer/tooling?tabs=nodejs).
|
|
17
|
+
|
|
18
|
+
## Support
|
|
19
|
+
|
|
20
|
+
For issues, questions, or feedback:
|
|
21
|
+
|
|
22
|
+
- File issues in the [GitHub Issues](https://github.com/microsoft/Agent365-nodejs/issues) section
|
|
23
|
+
- See the [main documentation](../../README.md) for more information
|
|
24
|
+
|
|
25
|
+
## Trademarks
|
|
26
|
+
|
|
27
|
+
*Microsoft, Windows, Microsoft Azure and/or other Microsoft products and services referenced in the documentation may be either trademarks or registered trademarks of Microsoft in the United States and/or other countries. The licenses for this project do not grant you rights to use any Microsoft names, logos, or trademarks. Microsoft's general trademark guidelines can be found at http://go.microsoft.com/fwlink/?LinkID=254653.*
|
|
28
|
+
|
|
29
|
+
## License
|
|
30
|
+
|
|
31
|
+
Copyright (c) Microsoft Corporation. All rights reserved.
|
|
32
|
+
|
|
33
|
+
Licensed under the MIT License - see the [LICENSE](../../LICENSE.md) file for details
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { MCPServerConfig, McpClientTool } from './contracts';
|
|
2
|
+
/**
|
|
3
|
+
* Service responsible for discovering and normalizing MCP (Model Context Protocol)
|
|
4
|
+
* tool servers and producing configuration objects consumable by the Claude SDK.
|
|
5
|
+
*/
|
|
6
|
+
export declare class McpToolServerConfigurationService {
|
|
7
|
+
private readonly logger;
|
|
8
|
+
/**
|
|
9
|
+
* Construct a McpToolServerConfigurationService.
|
|
10
|
+
*/
|
|
11
|
+
constructor();
|
|
12
|
+
/**
|
|
13
|
+
* Return MCP server definitions for the given agent. In development (NODE_ENV=Development) this reads the local ToolingManifest.json; otherwise it queries the remote tooling gateway.
|
|
14
|
+
*
|
|
15
|
+
* @param agenticAppId The agentic app id for which to discover servers.
|
|
16
|
+
* @param authToken Optional bearer token used when querying the remote tooling gateway.
|
|
17
|
+
* @returns A promise resolving to an array of normalized MCP server configuration objects.
|
|
18
|
+
*/
|
|
19
|
+
listToolServers(agenticAppId: string, authToken: string): Promise<MCPServerConfig[]>;
|
|
20
|
+
/**
|
|
21
|
+
* Connect to the MCP server and return tools with names prefixed by the server name.
|
|
22
|
+
* Throws if the server URL is missing or the client fails to list tools.
|
|
23
|
+
*/
|
|
24
|
+
getMcpClientTools(mcpServerName: string, mcpServerConfig: MCPServerConfig): Promise<McpClientTool[]>;
|
|
25
|
+
/**
|
|
26
|
+
* Query the tooling gateway for MCP servers for the specified agent and normalize each entry's mcpServerUniqueName into a full URL using Utility.BuildMcpServerUrl.
|
|
27
|
+
* Throws an error if the gateway call fails.
|
|
28
|
+
*
|
|
29
|
+
* @param agenticAppId The agentic app id used by the tooling gateway to scope results.
|
|
30
|
+
* @param authToken Optional Bearer token to include in the Authorization header when calling the gateway.
|
|
31
|
+
* @throws Error when the gateway call fails or returns an unexpected payload.
|
|
32
|
+
*/
|
|
33
|
+
private getMCPServerConfigsFromToolingGateway;
|
|
34
|
+
/**
|
|
35
|
+
* Read MCP servers from a local ToolingManifest.json file (development only).
|
|
36
|
+
* Searches process.cwd() and process.argv[1] for the manifest file.
|
|
37
|
+
*
|
|
38
|
+
* Reads MCP server configurations from ToolingManifest.json in the application's content root.
|
|
39
|
+
* The file should be located at: [ProjectRoot]/ToolingManifest.json
|
|
40
|
+
*
|
|
41
|
+
* Example ToolingManifest.json:
|
|
42
|
+
* {
|
|
43
|
+
* "mcpServers": [
|
|
44
|
+
* {
|
|
45
|
+
* "mcpServerName": "mailMCPServerConfig",
|
|
46
|
+
* "mcpServerUniqueName": "mcp_MailTools"
|
|
47
|
+
* },
|
|
48
|
+
* {
|
|
49
|
+
* "mcpServerName": "sharePointMCPServerConfig",
|
|
50
|
+
* "mcpServerUniqueName": "mcp_SharePointTools"
|
|
51
|
+
* }
|
|
52
|
+
* ]
|
|
53
|
+
* }
|
|
54
|
+
*/
|
|
55
|
+
private getMCPServerConfigsFromManifest;
|
|
56
|
+
/**
|
|
57
|
+
* Detect if the process is running in a development scenario based on environment variables.
|
|
58
|
+
*
|
|
59
|
+
* @returns {boolean} True when running in a development environment.
|
|
60
|
+
*/
|
|
61
|
+
private isDevScenario;
|
|
62
|
+
}
|
|
63
|
+
//# sourceMappingURL=McpToolServerConfigurationService.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"McpToolServerConfigurationService.d.ts","sourceRoot":"","sources":["../../src/McpToolServerConfigurationService.ts"],"names":[],"mappings":"AAMA,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAM7D;;;GAGG;AACH,qBAAa,iCAAiC;IAC5C,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAW;IAElC;;OAEG;;IAIH;;;;;;OAMG;IACG,eAAe,CAAC,YAAY,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,EAAE,CAAC;IAI1F;;;OAGG;IACG,iBAAiB,CAAC,aAAa,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC;IA8B1G;;;;;;;OAOG;YACW,qCAAqC;IAwBnD;;;;;;;;;;;;;;;;;;;;OAoBG;YACW,+BAA+B;IA8B7C;;;;OAIG;IACH,OAAO,CAAC,aAAa;CAItB"}
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Copyright (c) Microsoft Corporation.
|
|
3
|
+
// Licensed under the MIT License.
|
|
4
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
5
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
6
|
+
};
|
|
7
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
|
+
exports.McpToolServerConfigurationService = void 0;
|
|
9
|
+
const fs_1 = __importDefault(require("fs"));
|
|
10
|
+
const path_1 = __importDefault(require("path"));
|
|
11
|
+
const axios_1 = __importDefault(require("axios"));
|
|
12
|
+
const Utility_1 = require("./Utility");
|
|
13
|
+
const streamableHttp_js_1 = require("@modelcontextprotocol/sdk/client/streamableHttp.js");
|
|
14
|
+
const index_js_1 = require("@modelcontextprotocol/sdk/client/index.js");
|
|
15
|
+
/**
|
|
16
|
+
* Service responsible for discovering and normalizing MCP (Model Context Protocol)
|
|
17
|
+
* tool servers and producing configuration objects consumable by the Claude SDK.
|
|
18
|
+
*/
|
|
19
|
+
class McpToolServerConfigurationService {
|
|
20
|
+
/**
|
|
21
|
+
* Construct a McpToolServerConfigurationService.
|
|
22
|
+
*/
|
|
23
|
+
constructor() {
|
|
24
|
+
this.logger = console;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Return MCP server definitions for the given agent. In development (NODE_ENV=Development) this reads the local ToolingManifest.json; otherwise it queries the remote tooling gateway.
|
|
28
|
+
*
|
|
29
|
+
* @param agenticAppId The agentic app id for which to discover servers.
|
|
30
|
+
* @param authToken Optional bearer token used when querying the remote tooling gateway.
|
|
31
|
+
* @returns A promise resolving to an array of normalized MCP server configuration objects.
|
|
32
|
+
*/
|
|
33
|
+
async listToolServers(agenticAppId, authToken) {
|
|
34
|
+
return await (this.isDevScenario() ? this.getMCPServerConfigsFromManifest() : this.getMCPServerConfigsFromToolingGateway(agenticAppId, authToken));
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Connect to the MCP server and return tools with names prefixed by the server name.
|
|
38
|
+
* Throws if the server URL is missing or the client fails to list tools.
|
|
39
|
+
*/
|
|
40
|
+
async getMcpClientTools(mcpServerName, mcpServerConfig) {
|
|
41
|
+
if (!mcpServerConfig) {
|
|
42
|
+
throw new Error('Invalid MCP Server Configuration');
|
|
43
|
+
}
|
|
44
|
+
if (!mcpServerConfig.url) {
|
|
45
|
+
throw new Error('MCP Server URL cannot be null or empty');
|
|
46
|
+
}
|
|
47
|
+
const transport = new streamableHttp_js_1.StreamableHTTPClientTransport(new URL(mcpServerConfig.url), {
|
|
48
|
+
requestInit: {
|
|
49
|
+
headers: mcpServerConfig.headers
|
|
50
|
+
}
|
|
51
|
+
});
|
|
52
|
+
const mcpClient = new index_js_1.Client({
|
|
53
|
+
name: mcpServerName + ' Client',
|
|
54
|
+
version: '1.0',
|
|
55
|
+
});
|
|
56
|
+
await mcpClient.connect(transport);
|
|
57
|
+
const toolsObj = await mcpClient.listTools();
|
|
58
|
+
await mcpClient.close();
|
|
59
|
+
return toolsObj.tools;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Query the tooling gateway for MCP servers for the specified agent and normalize each entry's mcpServerUniqueName into a full URL using Utility.BuildMcpServerUrl.
|
|
63
|
+
* Throws an error if the gateway call fails.
|
|
64
|
+
*
|
|
65
|
+
* @param agenticAppId The agentic app id used by the tooling gateway to scope results.
|
|
66
|
+
* @param authToken Optional Bearer token to include in the Authorization header when calling the gateway.
|
|
67
|
+
* @throws Error when the gateway call fails or returns an unexpected payload.
|
|
68
|
+
*/
|
|
69
|
+
async getMCPServerConfigsFromToolingGateway(agenticAppId, authToken) {
|
|
70
|
+
// Validate the authentication token
|
|
71
|
+
Utility_1.Utility.ValidateAuthToken(authToken);
|
|
72
|
+
const configEndpoint = Utility_1.Utility.GetToolingGatewayForDigitalWorker(agenticAppId);
|
|
73
|
+
try {
|
|
74
|
+
const response = await axios_1.default.get(configEndpoint, {
|
|
75
|
+
headers: {
|
|
76
|
+
'Authorization': authToken ? `Bearer ${authToken}` : undefined,
|
|
77
|
+
},
|
|
78
|
+
timeout: 10000 // 10 seconds timeout
|
|
79
|
+
});
|
|
80
|
+
return (response.data) || [];
|
|
81
|
+
}
|
|
82
|
+
catch (err) {
|
|
83
|
+
const error = err;
|
|
84
|
+
throw new Error(`Failed to read MCP servers from endpoint: ${error.code || 'UNKNOWN'} ${error.message || 'Unknown error'}`);
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Read MCP servers from a local ToolingManifest.json file (development only).
|
|
89
|
+
* Searches process.cwd() and process.argv[1] for the manifest file.
|
|
90
|
+
*
|
|
91
|
+
* Reads MCP server configurations from ToolingManifest.json in the application's content root.
|
|
92
|
+
* The file should be located at: [ProjectRoot]/ToolingManifest.json
|
|
93
|
+
*
|
|
94
|
+
* Example ToolingManifest.json:
|
|
95
|
+
* {
|
|
96
|
+
* "mcpServers": [
|
|
97
|
+
* {
|
|
98
|
+
* "mcpServerName": "mailMCPServerConfig",
|
|
99
|
+
* "mcpServerUniqueName": "mcp_MailTools"
|
|
100
|
+
* },
|
|
101
|
+
* {
|
|
102
|
+
* "mcpServerName": "sharePointMCPServerConfig",
|
|
103
|
+
* "mcpServerUniqueName": "mcp_SharePointTools"
|
|
104
|
+
* }
|
|
105
|
+
* ]
|
|
106
|
+
* }
|
|
107
|
+
*/
|
|
108
|
+
async getMCPServerConfigsFromManifest() {
|
|
109
|
+
let manifestPath = path_1.default.join(process.cwd(), 'ToolingManifest.json');
|
|
110
|
+
if (!fs_1.default.existsSync(manifestPath)) {
|
|
111
|
+
this.logger.warn(`ToolingManifest.json not found at ${manifestPath}, checking argv[1] location.`);
|
|
112
|
+
manifestPath = path_1.default.join(path_1.default.dirname(process.argv[1] || ''), 'ToolingManifest.json');
|
|
113
|
+
}
|
|
114
|
+
if (!fs_1.default.existsSync(manifestPath)) {
|
|
115
|
+
this.logger.warn(`ToolingManifest.json not found at ${manifestPath}`);
|
|
116
|
+
return [];
|
|
117
|
+
}
|
|
118
|
+
try {
|
|
119
|
+
const jsonContent = fs_1.default.readFileSync(manifestPath, 'utf-8');
|
|
120
|
+
const manifestData = JSON.parse(jsonContent);
|
|
121
|
+
const mcpServers = manifestData.mcpServers || [];
|
|
122
|
+
return mcpServers.map((s) => {
|
|
123
|
+
return {
|
|
124
|
+
mcpServerName: s.mcpServerName,
|
|
125
|
+
url: Utility_1.Utility.BuildMcpServerUrl(s.mcpServerName)
|
|
126
|
+
};
|
|
127
|
+
});
|
|
128
|
+
}
|
|
129
|
+
catch (err) {
|
|
130
|
+
const error = err;
|
|
131
|
+
this.logger.error(`Error reading or parsing ToolingManifest.json: ${error.message || 'Unknown error'}`);
|
|
132
|
+
return [];
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* Detect if the process is running in a development scenario based on environment variables.
|
|
137
|
+
*
|
|
138
|
+
* @returns {boolean} True when running in a development environment.
|
|
139
|
+
*/
|
|
140
|
+
isDevScenario() {
|
|
141
|
+
const environment = process.env.NODE_ENV || 'Development';
|
|
142
|
+
return environment.toLowerCase() === 'development';
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
exports.McpToolServerConfigurationService = McpToolServerConfigurationService;
|
|
146
|
+
//# sourceMappingURL=McpToolServerConfigurationService.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"McpToolServerConfigurationService.js","sourceRoot":"","sources":["../../src/McpToolServerConfigurationService.ts"],"names":[],"mappings":";AAAA,uCAAuC;AACvC,kCAAkC;;;;;;AAElC,4CAAoB;AACpB,gDAAwB;AACxB,kDAA0B;AAE1B,uCAAoC;AAEpC,0FAAmG;AACnG,wEAAmE;AAEnE;;;GAGG;AACH,MAAa,iCAAiC;IAG5C;;OAEG;IACH;QALiB,WAAM,GAAG,OAAO,CAAC;IAMlC,CAAC;IAED;;;;;;OAMG;IACH,KAAK,CAAC,eAAe,CAAC,YAAoB,EAAE,SAAiB;QAC3D,OAAO,MAAM,CAAC,IAAI,CAAC,aAAa,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,+BAA+B,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,qCAAqC,CAAC,YAAY,EAAE,SAAS,CAAC,CAAC,CAAC;IACrJ,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,iBAAiB,CAAC,aAAqB,EAAE,eAAgC;QAC7E,IAAI,CAAC,eAAe,EAAE,CAAC;YACrB,MAAM,IAAI,KAAK,CAAC,kCAAkC,CAAC,CAAC;QACtD,CAAC;QAED,IAAI,CAAC,eAAe,CAAC,GAAG,EAAE,CAAC;YACzB,MAAM,IAAI,KAAK,CAAC,wCAAwC,CAAC,CAAC;QAC5D,CAAC;QAED,MAAM,SAAS,GAAG,IAAI,iDAA6B,CACjD,IAAI,GAAG,CAAC,eAAe,CAAC,GAAG,CAAC,EAC5B;YACE,WAAW,EAAE;gBACX,OAAO,EAAE,eAAe,CAAC,OAAO;aACjC;SACF,CACF,CAAC;QAEF,MAAM,SAAS,GAAG,IAAI,iBAAM,CAAC;YAC3B,IAAI,EAAE,aAAa,GAAG,SAAS;YAC/B,OAAO,EAAE,KAAK;SACf,CAAC,CAAC;QAEH,MAAM,SAAS,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC;QACnC,MAAM,QAAQ,GAAG,MAAM,SAAS,CAAC,SAAS,EAAE,CAAC;QAC7C,MAAM,SAAS,CAAC,KAAK,EAAE,CAAC;QAExB,OAAO,QAAQ,CAAC,KAAK,CAAC;IACxB,CAAC;IAED;;;;;;;OAOG;IACK,KAAK,CAAC,qCAAqC,CAAC,YAAoB,EAAE,SAAiB;QACzF,oCAAoC;QACpC,iBAAO,CAAC,iBAAiB,CAAC,SAAS,CAAC,CAAC;QAErC,MAAM,cAAc,GAAG,iBAAO,CAAC,iCAAiC,CAAC,YAAY,CAAC,CAAC;QAE/E,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,GAAG,CAC9B,cAAc,EACd;gBACE,OAAO,EAAE;oBACP,eAAe,EAAE,SAAS,CAAC,CAAC,CAAC,UAAU,SAAS,EAAE,CAAC,CAAC,CAAC,SAAS;iBAC/D;gBACD,OAAO,EAAE,KAAK,CAAC,qBAAqB;aACrC,CACF,CAAC;YAEF,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;QAC/B,CAAC;QAAC,OAAO,GAAY,EAAE,CAAC;YACtB,MAAM,KAAK,GAAG,GAAgC,CAAC;YAC/C,MAAM,IAAI,KAAK,CAAC,6CAA6C,KAAK,CAAC,IAAI,IAAI,SAAS,IAAI,KAAK,CAAC,OAAO,IAAI,eAAe,EAAE,CAAC,CAAC;QAC9H,CAAC;IACH,CAAC;IAED;;;;;;;;;;;;;;;;;;;;OAoBG;IACK,KAAK,CAAC,+BAA+B;QAC3C,IAAI,YAAY,GAAG,cAAI,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,sBAAsB,CAAC,CAAC;QACpE,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;YACjC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,qCAAqC,YAAY,8BAA8B,CAAC,CAAC;YAClG,YAAY,GAAG,cAAI,CAAC,IAAI,CAAC,cAAI,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,EAAE,sBAAsB,CAAC,CAAC;QACxF,CAAC;QAED,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,YAAY,CAAC,EAAE,CAAC;YACjC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,qCAAqC,YAAY,EAAE,CAAC,CAAC;YACtE,OAAO,EAAE,CAAC;QACZ,CAAC;QAED,IAAI,CAAC;YACH,MAAM,WAAW,GAAG,YAAE,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,CAAC,CAAC;YAC3D,MAAM,YAAY,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;YAC7C,MAAM,UAAU,GAAG,YAAY,CAAC,UAAU,IAAI,EAAE,CAAC;YAEjD,OAAO,UAAU,CAAC,GAAG,CAAC,CAAC,CAAkB,EAAE,EAAE;gBAC3C,OAAO;oBACL,aAAa,EAAE,CAAC,CAAC,aAAa;oBAC9B,GAAG,EAAE,iBAAO,CAAC,iBAAiB,CAAC,CAAC,CAAC,aAAa,CAAC;iBAChD,CAAC;YACJ,CAAC,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,GAAY,EAAE,CAAC;YACtB,MAAM,KAAK,GAAG,GAAY,CAAC;YAC3B,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,kDAAkD,KAAK,CAAC,OAAO,IAAI,eAAe,EAAE,CAAC,CAAC;YACxG,OAAO,EAAE,CAAC;QACZ,CAAC;IACH,CAAC;IAED;;;;OAIG;IACK,aAAa;QACnB,MAAM,WAAW,GAAG,OAAO,CAAC,GAAG,CAAC,QAAQ,IAAI,aAAa,CAAC;QAC1D,OAAO,WAAW,CAAC,WAAW,EAAE,KAAK,aAAa,CAAC;IACrD,CAAC;CACF;AAlJD,8EAkJC"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
export declare enum ToolsMode {
|
|
2
|
+
MockMCPServer = "MockMCPServer",
|
|
3
|
+
MCPPlatform = "MCPPlatform"
|
|
4
|
+
}
|
|
5
|
+
export declare class Utility {
|
|
6
|
+
/**
|
|
7
|
+
* Validates a JWT authentication token.
|
|
8
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
9
|
+
*
|
|
10
|
+
* @param authToken - The JWT token to validate.
|
|
11
|
+
* @throws Error if the token is invalid or expired.
|
|
12
|
+
*/
|
|
13
|
+
static ValidateAuthToken(authToken: string | undefined): void;
|
|
14
|
+
/**
|
|
15
|
+
* Private helper to validate a JWT authentication token.
|
|
16
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
17
|
+
*
|
|
18
|
+
* @param authToken - The JWT token to validate.
|
|
19
|
+
* @throws Error if the token is invalid or expired.
|
|
20
|
+
*/
|
|
21
|
+
private static validateAuthToken;
|
|
22
|
+
/**
|
|
23
|
+
* Construct the tooling gateway URL for a given agent identity.
|
|
24
|
+
* This endpoint is used to discover MCP servers associated with the specified agent identity.
|
|
25
|
+
*
|
|
26
|
+
* Example:
|
|
27
|
+
* Utility.GetToolingGatewayForDigitalWorker(agenticAppId)
|
|
28
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/{agenticAppId}/mcpServers"
|
|
29
|
+
*
|
|
30
|
+
* @param agenticAppId - The unique identifier for the agent identity.
|
|
31
|
+
* @returns A fully-qualified URL pointing at the tooling gateway for the agent.
|
|
32
|
+
*/
|
|
33
|
+
static GetToolingGatewayForDigitalWorker(agenticAppId: string): string;
|
|
34
|
+
/**
|
|
35
|
+
* Get the base URL used to query MCP environments.
|
|
36
|
+
*
|
|
37
|
+
* @returns The base MCP environments URL.
|
|
38
|
+
*/
|
|
39
|
+
static GetMcpBaseUrl(): string;
|
|
40
|
+
/**
|
|
41
|
+
* Build the full URL for accessing a specific MCP server.
|
|
42
|
+
*
|
|
43
|
+
* Example:
|
|
44
|
+
* Utility.BuildMcpServerUrl('MyServer')
|
|
45
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/servers/MyServer/"
|
|
46
|
+
*
|
|
47
|
+
* @param serverName - The MCP server resource name.
|
|
48
|
+
* @returns The fully-qualified MCP server URL including trailing slash.
|
|
49
|
+
*/
|
|
50
|
+
static BuildMcpServerUrl(serverName: string): string;
|
|
51
|
+
static GetToolsMode(): ToolsMode;
|
|
52
|
+
/**
|
|
53
|
+
* Reads the current environment name from process.env.
|
|
54
|
+
* Checks ASPNETCORE_ENVIRONMENT, DOTNET_ENVIRONMENT, and NODE_ENV in that order.
|
|
55
|
+
* If none are set this returns the string 'Development'.
|
|
56
|
+
*
|
|
57
|
+
* @returns The current environment identifier as a string.
|
|
58
|
+
*/
|
|
59
|
+
private static getCurrentEnvironment;
|
|
60
|
+
/**
|
|
61
|
+
* Gets the base URL for MCP platform, defaults to production URL if not set.
|
|
62
|
+
*
|
|
63
|
+
* @returns The base URL for MCP platform.
|
|
64
|
+
*/
|
|
65
|
+
private static getMcpPlatformBaseUrl;
|
|
66
|
+
}
|
|
67
|
+
//# sourceMappingURL=Utility.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Utility.d.ts","sourceRoot":"","sources":["../../src/Utility.ts"],"names":[],"mappings":"AAGA,oBAAY,SAAS;IACnB,aAAa,kBAAkB;IAC/B,WAAW,gBAAgB;CAC5B;AAKD,qBAAa,OAAO;IAClB;;;;;;OAMG;WACW,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,GAAG,IAAI;IAIpE;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,iBAAiB;IAqChC;;;;;;;;;;OAUG;WACW,iCAAiC,CAAC,YAAY,EAAE,MAAM,GAAG,MAAM;IAK7E;;;;OAIG;WACW,aAAa,IAAI,MAAM;IAarC;;;;;;;;;MASE;WACY,iBAAiB,CAAC,UAAU,EAAE,MAAM,GAAI,MAAM;WAK9C,YAAY,IAAI,SAAS;IAUvC;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,qBAAqB;IAOpC;;;;OAIG;IACH,OAAO,CAAC,MAAM,CAAC,qBAAqB;CAOrC"}
|
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Copyright (c) Microsoft Corporation.
|
|
3
|
+
// Licensed under the MIT License.
|
|
4
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
5
|
+
exports.Utility = exports.ToolsMode = void 0;
|
|
6
|
+
var ToolsMode;
|
|
7
|
+
(function (ToolsMode) {
|
|
8
|
+
ToolsMode["MockMCPServer"] = "MockMCPServer";
|
|
9
|
+
ToolsMode["MCPPlatform"] = "MCPPlatform";
|
|
10
|
+
})(ToolsMode || (exports.ToolsMode = ToolsMode = {}));
|
|
11
|
+
// Constant for MCP Platform base URL in production
|
|
12
|
+
const MCP_PLATFORM_PROD_BASE_URL = 'https://agent365.svc.cloud.microsoft';
|
|
13
|
+
class Utility {
|
|
14
|
+
/**
|
|
15
|
+
* Validates a JWT authentication token.
|
|
16
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
17
|
+
*
|
|
18
|
+
* @param authToken - The JWT token to validate.
|
|
19
|
+
* @throws Error if the token is invalid or expired.
|
|
20
|
+
*/
|
|
21
|
+
static ValidateAuthToken(authToken) {
|
|
22
|
+
return Utility.validateAuthToken(authToken);
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Private helper to validate a JWT authentication token.
|
|
26
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
27
|
+
*
|
|
28
|
+
* @param authToken - The JWT token to validate.
|
|
29
|
+
* @throws Error if the token is invalid or expired.
|
|
30
|
+
*/
|
|
31
|
+
static validateAuthToken(authToken) {
|
|
32
|
+
if (!authToken) {
|
|
33
|
+
throw new Error('Authentication token is required');
|
|
34
|
+
}
|
|
35
|
+
// Parse JWT token (format: header.payload.signature)
|
|
36
|
+
const parts = authToken.split('.');
|
|
37
|
+
if (parts.length !== 3) {
|
|
38
|
+
throw new Error('Invalid JWT token format');
|
|
39
|
+
}
|
|
40
|
+
let payload;
|
|
41
|
+
try {
|
|
42
|
+
// Decode the payload (second part of the JWT)
|
|
43
|
+
const payloadBase64 = parts[1];
|
|
44
|
+
// Handle URL-safe base64
|
|
45
|
+
const paddedBase64 = payloadBase64.padEnd(payloadBase64.length + (4 - payloadBase64.length % 4) % 4, '=');
|
|
46
|
+
const payloadJson = Buffer.from(paddedBase64.replace(/-/g, '+').replace(/_/g, '/'), 'base64').toString('utf-8');
|
|
47
|
+
payload = JSON.parse(payloadJson);
|
|
48
|
+
}
|
|
49
|
+
catch (error) {
|
|
50
|
+
throw new Error('Failed to decode JWT token payload');
|
|
51
|
+
}
|
|
52
|
+
// Check expiration
|
|
53
|
+
if (payload.exp) {
|
|
54
|
+
const currentTimestamp = Math.floor(Date.now() / 1000);
|
|
55
|
+
if (payload.exp < currentTimestamp) {
|
|
56
|
+
throw new Error('Authentication token has expired');
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
else {
|
|
60
|
+
throw new Error('Authentication token does not contain expiration claim');
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Construct the tooling gateway URL for a given agent identity.
|
|
65
|
+
* This endpoint is used to discover MCP servers associated with the specified agent identity.
|
|
66
|
+
*
|
|
67
|
+
* Example:
|
|
68
|
+
* Utility.GetToolingGatewayForDigitalWorker(agenticAppId)
|
|
69
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/{agenticAppId}/mcpServers"
|
|
70
|
+
*
|
|
71
|
+
* @param agenticAppId - The unique identifier for the agent identity.
|
|
72
|
+
* @returns A fully-qualified URL pointing at the tooling gateway for the agent.
|
|
73
|
+
*/
|
|
74
|
+
static GetToolingGatewayForDigitalWorker(agenticAppId) {
|
|
75
|
+
// The endpoint needs to be updated based on the environment (prod, dev, etc.)
|
|
76
|
+
return `${this.getMcpPlatformBaseUrl()}/agents/${agenticAppId}/mcpServers`;
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Get the base URL used to query MCP environments.
|
|
80
|
+
*
|
|
81
|
+
* @returns The base MCP environments URL.
|
|
82
|
+
*/
|
|
83
|
+
static GetMcpBaseUrl() {
|
|
84
|
+
const environment = this.getCurrentEnvironment().toLowerCase();
|
|
85
|
+
if (environment === 'development') {
|
|
86
|
+
const toolsMode = this.GetToolsMode();
|
|
87
|
+
if (toolsMode === ToolsMode.MockMCPServer) {
|
|
88
|
+
return process.env.MOCK_MCP_SERVER_URL || 'http://localhost:5309/mcp-mock/agents/servers';
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
return `${this.getMcpPlatformBaseUrl()}/agents/servers`;
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* Build the full URL for accessing a specific MCP server.
|
|
95
|
+
*
|
|
96
|
+
* Example:
|
|
97
|
+
* Utility.BuildMcpServerUrl('MyServer')
|
|
98
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/servers/MyServer/"
|
|
99
|
+
*
|
|
100
|
+
* @param serverName - The MCP server resource name.
|
|
101
|
+
* @returns The fully-qualified MCP server URL including trailing slash.
|
|
102
|
+
*/
|
|
103
|
+
static BuildMcpServerUrl(serverName) {
|
|
104
|
+
const baseUrl = this.GetMcpBaseUrl();
|
|
105
|
+
return `${baseUrl}/${serverName}`;
|
|
106
|
+
}
|
|
107
|
+
static GetToolsMode() {
|
|
108
|
+
const toolsMode = process.env.TOOLS_MODE || 'MCPPlatform';
|
|
109
|
+
switch (toolsMode.toLowerCase()) {
|
|
110
|
+
case 'mockmcpserver':
|
|
111
|
+
return ToolsMode.MockMCPServer;
|
|
112
|
+
default:
|
|
113
|
+
return ToolsMode.MCPPlatform;
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
/**
|
|
117
|
+
* Reads the current environment name from process.env.
|
|
118
|
+
* Checks ASPNETCORE_ENVIRONMENT, DOTNET_ENVIRONMENT, and NODE_ENV in that order.
|
|
119
|
+
* If none are set this returns the string 'Development'.
|
|
120
|
+
*
|
|
121
|
+
* @returns The current environment identifier as a string.
|
|
122
|
+
*/
|
|
123
|
+
static getCurrentEnvironment() {
|
|
124
|
+
return process.env.ASPNETCORE_ENVIRONMENT ||
|
|
125
|
+
process.env.DOTNET_ENVIRONMENT ||
|
|
126
|
+
process.env.NODE_ENV ||
|
|
127
|
+
'Development';
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Gets the base URL for MCP platform, defaults to production URL if not set.
|
|
131
|
+
*
|
|
132
|
+
* @returns The base URL for MCP platform.
|
|
133
|
+
*/
|
|
134
|
+
static getMcpPlatformBaseUrl() {
|
|
135
|
+
if (process.env.MCP_PLATFORM_ENDPOINT) {
|
|
136
|
+
return process.env.MCP_PLATFORM_ENDPOINT;
|
|
137
|
+
}
|
|
138
|
+
return MCP_PLATFORM_PROD_BASE_URL;
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
exports.Utility = Utility;
|
|
142
|
+
//# sourceMappingURL=Utility.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Utility.js","sourceRoot":"","sources":["../../src/Utility.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export interface MCPServerConfig {
|
|
2
|
+
mcpServerName: string;
|
|
3
|
+
url: string;
|
|
4
|
+
headers?: Record<string, string>;
|
|
5
|
+
}
|
|
6
|
+
export interface McpClientTool {
|
|
7
|
+
name: string;
|
|
8
|
+
description: string;
|
|
9
|
+
inputSchema: InputSchema;
|
|
10
|
+
}
|
|
11
|
+
export interface InputSchema {
|
|
12
|
+
type: string;
|
|
13
|
+
properties: Record<string, {
|
|
14
|
+
type: string;
|
|
15
|
+
description?: string;
|
|
16
|
+
enum?: string[];
|
|
17
|
+
}>;
|
|
18
|
+
required?: string[];
|
|
19
|
+
additionalProperties?: boolean;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=contracts.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contracts.d.ts","sourceRoot":"","sources":["../../src/contracts.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,eAAe;IAC9B,aAAa,EAAE,MAAM,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAClC;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,WAAW,CAAC;CAC1B;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,WAAW,CAAC,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,EAAE,CAAA;KAAE,CAAC,CAAC;IACpF,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,oBAAoB,CAAC,EAAE,OAAO,CAAC;CAChC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contracts.js","sourceRoot":"","sources":["../../src/contracts.ts"],"names":[],"mappings":";AAAA,uCAAuC;AACvC,kCAAkC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC;AAC1B,cAAc,qCAAqC,CAAC;AACpD,cAAc,aAAa,CAAC"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
14
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
|
+
};
|
|
16
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
__exportStar(require("./Utility"), exports);
|
|
18
|
+
__exportStar(require("./McpToolServerConfigurationService"), exports);
|
|
19
|
+
__exportStar(require("./contracts"), exports);
|
|
20
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,4CAA0B;AAC1B,sEAAoD;AACpD,8CAA4B"}
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { MCPServerConfig, McpClientTool } from './contracts';
|
|
2
|
+
/**
|
|
3
|
+
* Service responsible for discovering and normalizing MCP (Model Context Protocol)
|
|
4
|
+
* tool servers and producing configuration objects consumable by the Claude SDK.
|
|
5
|
+
*/
|
|
6
|
+
export declare class McpToolServerConfigurationService {
|
|
7
|
+
private readonly logger;
|
|
8
|
+
/**
|
|
9
|
+
* Construct a McpToolServerConfigurationService.
|
|
10
|
+
*/
|
|
11
|
+
constructor();
|
|
12
|
+
/**
|
|
13
|
+
* Return MCP server definitions for the given agent. In development (NODE_ENV=Development) this reads the local ToolingManifest.json; otherwise it queries the remote tooling gateway.
|
|
14
|
+
*
|
|
15
|
+
* @param agenticAppId The agentic app id for which to discover servers.
|
|
16
|
+
* @param authToken Optional bearer token used when querying the remote tooling gateway.
|
|
17
|
+
* @returns A promise resolving to an array of normalized MCP server configuration objects.
|
|
18
|
+
*/
|
|
19
|
+
listToolServers(agenticAppId: string, authToken: string): Promise<MCPServerConfig[]>;
|
|
20
|
+
/**
|
|
21
|
+
* Connect to the MCP server and return tools with names prefixed by the server name.
|
|
22
|
+
* Throws if the server URL is missing or the client fails to list tools.
|
|
23
|
+
*/
|
|
24
|
+
getMcpClientTools(mcpServerName: string, mcpServerConfig: MCPServerConfig): Promise<McpClientTool[]>;
|
|
25
|
+
/**
|
|
26
|
+
* Query the tooling gateway for MCP servers for the specified agent and normalize each entry's mcpServerUniqueName into a full URL using Utility.BuildMcpServerUrl.
|
|
27
|
+
* Throws an error if the gateway call fails.
|
|
28
|
+
*
|
|
29
|
+
* @param agenticAppId The agentic app id used by the tooling gateway to scope results.
|
|
30
|
+
* @param authToken Optional Bearer token to include in the Authorization header when calling the gateway.
|
|
31
|
+
* @throws Error when the gateway call fails or returns an unexpected payload.
|
|
32
|
+
*/
|
|
33
|
+
private getMCPServerConfigsFromToolingGateway;
|
|
34
|
+
/**
|
|
35
|
+
* Read MCP servers from a local ToolingManifest.json file (development only).
|
|
36
|
+
* Searches process.cwd() and process.argv[1] for the manifest file.
|
|
37
|
+
*
|
|
38
|
+
* Reads MCP server configurations from ToolingManifest.json in the application's content root.
|
|
39
|
+
* The file should be located at: [ProjectRoot]/ToolingManifest.json
|
|
40
|
+
*
|
|
41
|
+
* Example ToolingManifest.json:
|
|
42
|
+
* {
|
|
43
|
+
* "mcpServers": [
|
|
44
|
+
* {
|
|
45
|
+
* "mcpServerName": "mailMCPServerConfig",
|
|
46
|
+
* "mcpServerUniqueName": "mcp_MailTools"
|
|
47
|
+
* },
|
|
48
|
+
* {
|
|
49
|
+
* "mcpServerName": "sharePointMCPServerConfig",
|
|
50
|
+
* "mcpServerUniqueName": "mcp_SharePointTools"
|
|
51
|
+
* }
|
|
52
|
+
* ]
|
|
53
|
+
* }
|
|
54
|
+
*/
|
|
55
|
+
private getMCPServerConfigsFromManifest;
|
|
56
|
+
/**
|
|
57
|
+
* Detect if the process is running in a development scenario based on environment variables.
|
|
58
|
+
*
|
|
59
|
+
* @returns {boolean} True when running in a development environment.
|
|
60
|
+
*/
|
|
61
|
+
private isDevScenario;
|
|
62
|
+
}
|
|
63
|
+
//# sourceMappingURL=McpToolServerConfigurationService.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"McpToolServerConfigurationService.d.ts","sourceRoot":"","sources":["../../src/McpToolServerConfigurationService.ts"],"names":[],"mappings":"AAMA,OAAO,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAM7D;;;GAGG;AACH,qBAAa,iCAAiC;IAC5C,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAW;IAElC;;OAEG;;IAIH;;;;;;OAMG;IACG,eAAe,CAAC,YAAY,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,EAAE,CAAC;IAI1F;;;OAGG;IACG,iBAAiB,CAAC,aAAa,EAAE,MAAM,EAAE,eAAe,EAAE,eAAe,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC;IA8B1G;;;;;;;OAOG;YACW,qCAAqC;IAwBnD;;;;;;;;;;;;;;;;;;;;OAoBG;YACW,+BAA+B;IA8B7C;;;;OAIG;IACH,OAAO,CAAC,aAAa;CAItB"}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
// Copyright (c) Microsoft Corporation.
|
|
2
|
+
// Licensed under the MIT License.
|
|
3
|
+
import fs from 'fs';
|
|
4
|
+
import path from 'path';
|
|
5
|
+
import axios from 'axios';
|
|
6
|
+
import { Utility } from './Utility';
|
|
7
|
+
import { StreamableHTTPClientTransport } from '@modelcontextprotocol/sdk/client/streamableHttp.js';
|
|
8
|
+
import { Client } from '@modelcontextprotocol/sdk/client/index.js';
|
|
9
|
+
/**
|
|
10
|
+
* Service responsible for discovering and normalizing MCP (Model Context Protocol)
|
|
11
|
+
* tool servers and producing configuration objects consumable by the Claude SDK.
|
|
12
|
+
*/
|
|
13
|
+
export class McpToolServerConfigurationService {
|
|
14
|
+
/**
|
|
15
|
+
* Construct a McpToolServerConfigurationService.
|
|
16
|
+
*/
|
|
17
|
+
constructor() {
|
|
18
|
+
this.logger = console;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Return MCP server definitions for the given agent. In development (NODE_ENV=Development) this reads the local ToolingManifest.json; otherwise it queries the remote tooling gateway.
|
|
22
|
+
*
|
|
23
|
+
* @param agenticAppId The agentic app id for which to discover servers.
|
|
24
|
+
* @param authToken Optional bearer token used when querying the remote tooling gateway.
|
|
25
|
+
* @returns A promise resolving to an array of normalized MCP server configuration objects.
|
|
26
|
+
*/
|
|
27
|
+
async listToolServers(agenticAppId, authToken) {
|
|
28
|
+
return await (this.isDevScenario() ? this.getMCPServerConfigsFromManifest() : this.getMCPServerConfigsFromToolingGateway(agenticAppId, authToken));
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Connect to the MCP server and return tools with names prefixed by the server name.
|
|
32
|
+
* Throws if the server URL is missing or the client fails to list tools.
|
|
33
|
+
*/
|
|
34
|
+
async getMcpClientTools(mcpServerName, mcpServerConfig) {
|
|
35
|
+
if (!mcpServerConfig) {
|
|
36
|
+
throw new Error('Invalid MCP Server Configuration');
|
|
37
|
+
}
|
|
38
|
+
if (!mcpServerConfig.url) {
|
|
39
|
+
throw new Error('MCP Server URL cannot be null or empty');
|
|
40
|
+
}
|
|
41
|
+
const transport = new StreamableHTTPClientTransport(new URL(mcpServerConfig.url), {
|
|
42
|
+
requestInit: {
|
|
43
|
+
headers: mcpServerConfig.headers
|
|
44
|
+
}
|
|
45
|
+
});
|
|
46
|
+
const mcpClient = new Client({
|
|
47
|
+
name: mcpServerName + ' Client',
|
|
48
|
+
version: '1.0',
|
|
49
|
+
});
|
|
50
|
+
await mcpClient.connect(transport);
|
|
51
|
+
const toolsObj = await mcpClient.listTools();
|
|
52
|
+
await mcpClient.close();
|
|
53
|
+
return toolsObj.tools;
|
|
54
|
+
}
|
|
55
|
+
/**
|
|
56
|
+
* Query the tooling gateway for MCP servers for the specified agent and normalize each entry's mcpServerUniqueName into a full URL using Utility.BuildMcpServerUrl.
|
|
57
|
+
* Throws an error if the gateway call fails.
|
|
58
|
+
*
|
|
59
|
+
* @param agenticAppId The agentic app id used by the tooling gateway to scope results.
|
|
60
|
+
* @param authToken Optional Bearer token to include in the Authorization header when calling the gateway.
|
|
61
|
+
* @throws Error when the gateway call fails or returns an unexpected payload.
|
|
62
|
+
*/
|
|
63
|
+
async getMCPServerConfigsFromToolingGateway(agenticAppId, authToken) {
|
|
64
|
+
// Validate the authentication token
|
|
65
|
+
Utility.ValidateAuthToken(authToken);
|
|
66
|
+
const configEndpoint = Utility.GetToolingGatewayForDigitalWorker(agenticAppId);
|
|
67
|
+
try {
|
|
68
|
+
const response = await axios.get(configEndpoint, {
|
|
69
|
+
headers: {
|
|
70
|
+
'Authorization': authToken ? `Bearer ${authToken}` : undefined,
|
|
71
|
+
},
|
|
72
|
+
timeout: 10000 // 10 seconds timeout
|
|
73
|
+
});
|
|
74
|
+
return (response.data) || [];
|
|
75
|
+
}
|
|
76
|
+
catch (err) {
|
|
77
|
+
const error = err;
|
|
78
|
+
throw new Error(`Failed to read MCP servers from endpoint: ${error.code || 'UNKNOWN'} ${error.message || 'Unknown error'}`);
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Read MCP servers from a local ToolingManifest.json file (development only).
|
|
83
|
+
* Searches process.cwd() and process.argv[1] for the manifest file.
|
|
84
|
+
*
|
|
85
|
+
* Reads MCP server configurations from ToolingManifest.json in the application's content root.
|
|
86
|
+
* The file should be located at: [ProjectRoot]/ToolingManifest.json
|
|
87
|
+
*
|
|
88
|
+
* Example ToolingManifest.json:
|
|
89
|
+
* {
|
|
90
|
+
* "mcpServers": [
|
|
91
|
+
* {
|
|
92
|
+
* "mcpServerName": "mailMCPServerConfig",
|
|
93
|
+
* "mcpServerUniqueName": "mcp_MailTools"
|
|
94
|
+
* },
|
|
95
|
+
* {
|
|
96
|
+
* "mcpServerName": "sharePointMCPServerConfig",
|
|
97
|
+
* "mcpServerUniqueName": "mcp_SharePointTools"
|
|
98
|
+
* }
|
|
99
|
+
* ]
|
|
100
|
+
* }
|
|
101
|
+
*/
|
|
102
|
+
async getMCPServerConfigsFromManifest() {
|
|
103
|
+
let manifestPath = path.join(process.cwd(), 'ToolingManifest.json');
|
|
104
|
+
if (!fs.existsSync(manifestPath)) {
|
|
105
|
+
this.logger.warn(`ToolingManifest.json not found at ${manifestPath}, checking argv[1] location.`);
|
|
106
|
+
manifestPath = path.join(path.dirname(process.argv[1] || ''), 'ToolingManifest.json');
|
|
107
|
+
}
|
|
108
|
+
if (!fs.existsSync(manifestPath)) {
|
|
109
|
+
this.logger.warn(`ToolingManifest.json not found at ${manifestPath}`);
|
|
110
|
+
return [];
|
|
111
|
+
}
|
|
112
|
+
try {
|
|
113
|
+
const jsonContent = fs.readFileSync(manifestPath, 'utf-8');
|
|
114
|
+
const manifestData = JSON.parse(jsonContent);
|
|
115
|
+
const mcpServers = manifestData.mcpServers || [];
|
|
116
|
+
return mcpServers.map((s) => {
|
|
117
|
+
return {
|
|
118
|
+
mcpServerName: s.mcpServerName,
|
|
119
|
+
url: Utility.BuildMcpServerUrl(s.mcpServerName)
|
|
120
|
+
};
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
catch (err) {
|
|
124
|
+
const error = err;
|
|
125
|
+
this.logger.error(`Error reading or parsing ToolingManifest.json: ${error.message || 'Unknown error'}`);
|
|
126
|
+
return [];
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Detect if the process is running in a development scenario based on environment variables.
|
|
131
|
+
*
|
|
132
|
+
* @returns {boolean} True when running in a development environment.
|
|
133
|
+
*/
|
|
134
|
+
isDevScenario() {
|
|
135
|
+
const environment = process.env.NODE_ENV || 'Development';
|
|
136
|
+
return environment.toLowerCase() === 'development';
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
//# sourceMappingURL=McpToolServerConfigurationService.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"McpToolServerConfigurationService.js","sourceRoot":"","sources":["../../src/McpToolServerConfigurationService.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
export declare enum ToolsMode {
|
|
2
|
+
MockMCPServer = "MockMCPServer",
|
|
3
|
+
MCPPlatform = "MCPPlatform"
|
|
4
|
+
}
|
|
5
|
+
export declare class Utility {
|
|
6
|
+
/**
|
|
7
|
+
* Validates a JWT authentication token.
|
|
8
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
9
|
+
*
|
|
10
|
+
* @param authToken - The JWT token to validate.
|
|
11
|
+
* @throws Error if the token is invalid or expired.
|
|
12
|
+
*/
|
|
13
|
+
static ValidateAuthToken(authToken: string | undefined): void;
|
|
14
|
+
/**
|
|
15
|
+
* Private helper to validate a JWT authentication token.
|
|
16
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
17
|
+
*
|
|
18
|
+
* @param authToken - The JWT token to validate.
|
|
19
|
+
* @throws Error if the token is invalid or expired.
|
|
20
|
+
*/
|
|
21
|
+
private static validateAuthToken;
|
|
22
|
+
/**
|
|
23
|
+
* Construct the tooling gateway URL for a given agent identity.
|
|
24
|
+
* This endpoint is used to discover MCP servers associated with the specified agent identity.
|
|
25
|
+
*
|
|
26
|
+
* Example:
|
|
27
|
+
* Utility.GetToolingGatewayForDigitalWorker(agenticAppId)
|
|
28
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/{agenticAppId}/mcpServers"
|
|
29
|
+
*
|
|
30
|
+
* @param agenticAppId - The unique identifier for the agent identity.
|
|
31
|
+
* @returns A fully-qualified URL pointing at the tooling gateway for the agent.
|
|
32
|
+
*/
|
|
33
|
+
static GetToolingGatewayForDigitalWorker(agenticAppId: string): string;
|
|
34
|
+
/**
|
|
35
|
+
* Get the base URL used to query MCP environments.
|
|
36
|
+
*
|
|
37
|
+
* @returns The base MCP environments URL.
|
|
38
|
+
*/
|
|
39
|
+
static GetMcpBaseUrl(): string;
|
|
40
|
+
/**
|
|
41
|
+
* Build the full URL for accessing a specific MCP server.
|
|
42
|
+
*
|
|
43
|
+
* Example:
|
|
44
|
+
* Utility.BuildMcpServerUrl('MyServer')
|
|
45
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/servers/MyServer/"
|
|
46
|
+
*
|
|
47
|
+
* @param serverName - The MCP server resource name.
|
|
48
|
+
* @returns The fully-qualified MCP server URL including trailing slash.
|
|
49
|
+
*/
|
|
50
|
+
static BuildMcpServerUrl(serverName: string): string;
|
|
51
|
+
static GetToolsMode(): ToolsMode;
|
|
52
|
+
/**
|
|
53
|
+
* Reads the current environment name from process.env.
|
|
54
|
+
* Checks ASPNETCORE_ENVIRONMENT, DOTNET_ENVIRONMENT, and NODE_ENV in that order.
|
|
55
|
+
* If none are set this returns the string 'Development'.
|
|
56
|
+
*
|
|
57
|
+
* @returns The current environment identifier as a string.
|
|
58
|
+
*/
|
|
59
|
+
private static getCurrentEnvironment;
|
|
60
|
+
/**
|
|
61
|
+
* Gets the base URL for MCP platform, defaults to production URL if not set.
|
|
62
|
+
*
|
|
63
|
+
* @returns The base URL for MCP platform.
|
|
64
|
+
*/
|
|
65
|
+
private static getMcpPlatformBaseUrl;
|
|
66
|
+
}
|
|
67
|
+
//# sourceMappingURL=Utility.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Utility.d.ts","sourceRoot":"","sources":["../../src/Utility.ts"],"names":[],"mappings":"AAGA,oBAAY,SAAS;IACnB,aAAa,kBAAkB;IAC/B,WAAW,gBAAgB;CAC5B;AAKD,qBAAa,OAAO;IAClB;;;;;;OAMG;WACW,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,SAAS,GAAG,IAAI;IAIpE;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,iBAAiB;IAqChC;;;;;;;;;;OAUG;WACW,iCAAiC,CAAC,YAAY,EAAE,MAAM,GAAG,MAAM;IAK7E;;;;OAIG;WACW,aAAa,IAAI,MAAM;IAarC;;;;;;;;;MASE;WACY,iBAAiB,CAAC,UAAU,EAAE,MAAM,GAAI,MAAM;WAK9C,YAAY,IAAI,SAAS;IAUvC;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,qBAAqB;IAOpC;;;;OAIG;IACH,OAAO,CAAC,MAAM,CAAC,qBAAqB;CAOrC"}
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
// Copyright (c) Microsoft Corporation.
|
|
2
|
+
// Licensed under the MIT License.
|
|
3
|
+
export var ToolsMode;
|
|
4
|
+
(function (ToolsMode) {
|
|
5
|
+
ToolsMode["MockMCPServer"] = "MockMCPServer";
|
|
6
|
+
ToolsMode["MCPPlatform"] = "MCPPlatform";
|
|
7
|
+
})(ToolsMode || (ToolsMode = {}));
|
|
8
|
+
// Constant for MCP Platform base URL in production
|
|
9
|
+
const MCP_PLATFORM_PROD_BASE_URL = 'https://agent365.svc.cloud.microsoft';
|
|
10
|
+
export class Utility {
|
|
11
|
+
/**
|
|
12
|
+
* Validates a JWT authentication token.
|
|
13
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
14
|
+
*
|
|
15
|
+
* @param authToken - The JWT token to validate.
|
|
16
|
+
* @throws Error if the token is invalid or expired.
|
|
17
|
+
*/
|
|
18
|
+
static ValidateAuthToken(authToken) {
|
|
19
|
+
return Utility.validateAuthToken(authToken);
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Private helper to validate a JWT authentication token.
|
|
23
|
+
* Checks that the token is a valid JWT and is not expired.
|
|
24
|
+
*
|
|
25
|
+
* @param authToken - The JWT token to validate.
|
|
26
|
+
* @throws Error if the token is invalid or expired.
|
|
27
|
+
*/
|
|
28
|
+
static validateAuthToken(authToken) {
|
|
29
|
+
if (!authToken) {
|
|
30
|
+
throw new Error('Authentication token is required');
|
|
31
|
+
}
|
|
32
|
+
// Parse JWT token (format: header.payload.signature)
|
|
33
|
+
const parts = authToken.split('.');
|
|
34
|
+
if (parts.length !== 3) {
|
|
35
|
+
throw new Error('Invalid JWT token format');
|
|
36
|
+
}
|
|
37
|
+
let payload;
|
|
38
|
+
try {
|
|
39
|
+
// Decode the payload (second part of the JWT)
|
|
40
|
+
const payloadBase64 = parts[1];
|
|
41
|
+
// Handle URL-safe base64
|
|
42
|
+
const paddedBase64 = payloadBase64.padEnd(payloadBase64.length + (4 - payloadBase64.length % 4) % 4, '=');
|
|
43
|
+
const payloadJson = Buffer.from(paddedBase64.replace(/-/g, '+').replace(/_/g, '/'), 'base64').toString('utf-8');
|
|
44
|
+
payload = JSON.parse(payloadJson);
|
|
45
|
+
}
|
|
46
|
+
catch (error) {
|
|
47
|
+
throw new Error('Failed to decode JWT token payload');
|
|
48
|
+
}
|
|
49
|
+
// Check expiration
|
|
50
|
+
if (payload.exp) {
|
|
51
|
+
const currentTimestamp = Math.floor(Date.now() / 1000);
|
|
52
|
+
if (payload.exp < currentTimestamp) {
|
|
53
|
+
throw new Error('Authentication token has expired');
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
else {
|
|
57
|
+
throw new Error('Authentication token does not contain expiration claim');
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Construct the tooling gateway URL for a given agent identity.
|
|
62
|
+
* This endpoint is used to discover MCP servers associated with the specified agent identity.
|
|
63
|
+
*
|
|
64
|
+
* Example:
|
|
65
|
+
* Utility.GetToolingGatewayForDigitalWorker(agenticAppId)
|
|
66
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/{agenticAppId}/mcpServers"
|
|
67
|
+
*
|
|
68
|
+
* @param agenticAppId - The unique identifier for the agent identity.
|
|
69
|
+
* @returns A fully-qualified URL pointing at the tooling gateway for the agent.
|
|
70
|
+
*/
|
|
71
|
+
static GetToolingGatewayForDigitalWorker(agenticAppId) {
|
|
72
|
+
// The endpoint needs to be updated based on the environment (prod, dev, etc.)
|
|
73
|
+
return `${this.getMcpPlatformBaseUrl()}/agents/${agenticAppId}/mcpServers`;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Get the base URL used to query MCP environments.
|
|
77
|
+
*
|
|
78
|
+
* @returns The base MCP environments URL.
|
|
79
|
+
*/
|
|
80
|
+
static GetMcpBaseUrl() {
|
|
81
|
+
const environment = this.getCurrentEnvironment().toLowerCase();
|
|
82
|
+
if (environment === 'development') {
|
|
83
|
+
const toolsMode = this.GetToolsMode();
|
|
84
|
+
if (toolsMode === ToolsMode.MockMCPServer) {
|
|
85
|
+
return process.env.MOCK_MCP_SERVER_URL || 'http://localhost:5309/mcp-mock/agents/servers';
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
return `${this.getMcpPlatformBaseUrl()}/agents/servers`;
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* Build the full URL for accessing a specific MCP server.
|
|
92
|
+
*
|
|
93
|
+
* Example:
|
|
94
|
+
* Utility.BuildMcpServerUrl('MyServer')
|
|
95
|
+
* // => "https://agent365.svc.cloud.microsoft/agents/servers/MyServer/"
|
|
96
|
+
*
|
|
97
|
+
* @param serverName - The MCP server resource name.
|
|
98
|
+
* @returns The fully-qualified MCP server URL including trailing slash.
|
|
99
|
+
*/
|
|
100
|
+
static BuildMcpServerUrl(serverName) {
|
|
101
|
+
const baseUrl = this.GetMcpBaseUrl();
|
|
102
|
+
return `${baseUrl}/${serverName}`;
|
|
103
|
+
}
|
|
104
|
+
static GetToolsMode() {
|
|
105
|
+
const toolsMode = process.env.TOOLS_MODE || 'MCPPlatform';
|
|
106
|
+
switch (toolsMode.toLowerCase()) {
|
|
107
|
+
case 'mockmcpserver':
|
|
108
|
+
return ToolsMode.MockMCPServer;
|
|
109
|
+
default:
|
|
110
|
+
return ToolsMode.MCPPlatform;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* Reads the current environment name from process.env.
|
|
115
|
+
* Checks ASPNETCORE_ENVIRONMENT, DOTNET_ENVIRONMENT, and NODE_ENV in that order.
|
|
116
|
+
* If none are set this returns the string 'Development'.
|
|
117
|
+
*
|
|
118
|
+
* @returns The current environment identifier as a string.
|
|
119
|
+
*/
|
|
120
|
+
static getCurrentEnvironment() {
|
|
121
|
+
return process.env.ASPNETCORE_ENVIRONMENT ||
|
|
122
|
+
process.env.DOTNET_ENVIRONMENT ||
|
|
123
|
+
process.env.NODE_ENV ||
|
|
124
|
+
'Development';
|
|
125
|
+
}
|
|
126
|
+
/**
|
|
127
|
+
* Gets the base URL for MCP platform, defaults to production URL if not set.
|
|
128
|
+
*
|
|
129
|
+
* @returns The base URL for MCP platform.
|
|
130
|
+
*/
|
|
131
|
+
static getMcpPlatformBaseUrl() {
|
|
132
|
+
if (process.env.MCP_PLATFORM_ENDPOINT) {
|
|
133
|
+
return process.env.MCP_PLATFORM_ENDPOINT;
|
|
134
|
+
}
|
|
135
|
+
return MCP_PLATFORM_PROD_BASE_URL;
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
//# sourceMappingURL=Utility.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Utility.js","sourceRoot":"","sources":["../../src/Utility.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export interface MCPServerConfig {
|
|
2
|
+
mcpServerName: string;
|
|
3
|
+
url: string;
|
|
4
|
+
headers?: Record<string, string>;
|
|
5
|
+
}
|
|
6
|
+
export interface McpClientTool {
|
|
7
|
+
name: string;
|
|
8
|
+
description: string;
|
|
9
|
+
inputSchema: InputSchema;
|
|
10
|
+
}
|
|
11
|
+
export interface InputSchema {
|
|
12
|
+
type: string;
|
|
13
|
+
properties: Record<string, {
|
|
14
|
+
type: string;
|
|
15
|
+
description?: string;
|
|
16
|
+
enum?: string[];
|
|
17
|
+
}>;
|
|
18
|
+
required?: string[];
|
|
19
|
+
additionalProperties?: boolean;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=contracts.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contracts.d.ts","sourceRoot":"","sources":["../../src/contracts.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,eAAe;IAC9B,aAAa,EAAE,MAAM,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAClC;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,WAAW,CAAC;CAC1B;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,WAAW,CAAC,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,EAAE,CAAA;KAAE,CAAC,CAAC;IACpF,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,oBAAoB,CAAC,EAAE,OAAO,CAAC;CAChC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contracts.js","sourceRoot":"","sources":["../../src/contracts.ts"],"names":[],"mappings":"AAAA,uCAAuC;AACvC,kCAAkC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC;AAC1B,cAAc,qCAAqC,CAAC;AACpD,cAAc,aAAa,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,cAAc,WAAW,CAAC;AAC1B,cAAc,qCAAqC,CAAC;AACpD,cAAc,aAAa,CAAC"}
|
package/package.json
ADDED
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@microsoft/agents-a365-tooling",
|
|
3
|
+
"version": "0.1.0-preview.30",
|
|
4
|
+
"description": "Agent 365 Tooling SDK for AI agents built with TypeScript/Node.js",
|
|
5
|
+
"main": "dist/cjs/index.js",
|
|
6
|
+
"module": "dist/esm/index.js",
|
|
7
|
+
"types": "dist/esm/index.d.ts",
|
|
8
|
+
"scripts": {
|
|
9
|
+
"build:cjs": "npx tsc --project tsconfig.cjs.json",
|
|
10
|
+
"build:esm": "npx tsc --project tsconfig.esm.json",
|
|
11
|
+
"build": "npm run build:cjs && npm run build:esm",
|
|
12
|
+
"build:watch": "npx tsc --watch",
|
|
13
|
+
"clean": "npx rimraf dist",
|
|
14
|
+
"test": "jest --passWithNoTests",
|
|
15
|
+
"test:watch": "jest --watch",
|
|
16
|
+
"lint": "eslint src/**/*.ts",
|
|
17
|
+
"lint:fix": "eslint src/**/*.ts --fix",
|
|
18
|
+
"prepublishOnly": "npm run clean && npm run build",
|
|
19
|
+
"ci": "npm ci",
|
|
20
|
+
"pack": "npm pack --pack-destination=../"
|
|
21
|
+
},
|
|
22
|
+
"keywords": [
|
|
23
|
+
"ai",
|
|
24
|
+
"agents",
|
|
25
|
+
"azure",
|
|
26
|
+
"typescript"
|
|
27
|
+
],
|
|
28
|
+
"author": "Microsoft Corporation",
|
|
29
|
+
"license": "See license file",
|
|
30
|
+
"repository": {
|
|
31
|
+
"type": "git",
|
|
32
|
+
"url": "https://github.com/microsoft/Agent365-nodejs.git",
|
|
33
|
+
"directory": "packages/agents-a365-tooling"
|
|
34
|
+
},
|
|
35
|
+
"dependencies": {
|
|
36
|
+
"@microsoft/agents-a365-runtime": "0.1.0-preview.30",
|
|
37
|
+
"@microsoft/agents-hosting": "*",
|
|
38
|
+
"@modelcontextprotocol/sdk": "*",
|
|
39
|
+
"express": "*"
|
|
40
|
+
},
|
|
41
|
+
"devDependencies": {
|
|
42
|
+
"@types/jest": "^29.5.14",
|
|
43
|
+
"@types/node": "^20.0.0",
|
|
44
|
+
"@typescript-eslint/eslint-plugin": "^6.0.0",
|
|
45
|
+
"@typescript-eslint/parser": "^6.0.0",
|
|
46
|
+
"eslint": "^8.0.0",
|
|
47
|
+
"jest": "^29.0.0",
|
|
48
|
+
"rimraf": "^5.0.0",
|
|
49
|
+
"ts-jest": "^29.0.0",
|
|
50
|
+
"typescript": "^5.0.0"
|
|
51
|
+
},
|
|
52
|
+
"engines": {
|
|
53
|
+
"node": ">=18.0.0"
|
|
54
|
+
},
|
|
55
|
+
"files": [
|
|
56
|
+
"dist/**/*",
|
|
57
|
+
"README.md",
|
|
58
|
+
"CHANGELOG.md"
|
|
59
|
+
]
|
|
60
|
+
}
|