@agentvalet/register 0.1.9 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +42 -27
- package/dist/mcp-server-AM5ZYWTB.js +133 -0
- package/package.json +55 -53
package/dist/index.js
CHANGED
|
@@ -383,33 +383,6 @@ function ensureHook() {
|
|
|
383
383
|
const newEntry = { matcher: "", hooks: [{ type: "command", command: HOOK_COMMAND }] };
|
|
384
384
|
settings.hooks = { ...hooks, UserPromptSubmit: [...ups, newEntry] };
|
|
385
385
|
}
|
|
386
|
-
const mcpServers = settings.mcpServers ?? {};
|
|
387
|
-
if (!mcpServers["agent-authority"]) {
|
|
388
|
-
const envPath = resolve2(".env.agentvalet");
|
|
389
|
-
if (existsSync(envPath)) {
|
|
390
|
-
try {
|
|
391
|
-
const envVars = parseEnvFile(readFileSync(envPath, "utf-8"));
|
|
392
|
-
const agentId = envVars["AGENTVALET_AGENT_ID"];
|
|
393
|
-
const ownerId = envVars["AGENTVALET_OWNER_ID"];
|
|
394
|
-
const apiUrl = envVars["AGENTVALET_API_URL"] ?? "https://api.agentvalet.ai";
|
|
395
|
-
const keyPath = envVars["AGENTVALET_PRIVATE_KEY_PATH"];
|
|
396
|
-
if (agentId && ownerId && keyPath) {
|
|
397
|
-
mcpServers["agent-authority"] = {
|
|
398
|
-
command: "npx",
|
|
399
|
-
args: ["-y", "@agentvalet/mcp-server"],
|
|
400
|
-
env: {
|
|
401
|
-
AGENT_ID: agentId,
|
|
402
|
-
OWNER_ID: ownerId,
|
|
403
|
-
PROXY_URL: apiUrl,
|
|
404
|
-
AGENT_PRIVATE_KEY_PATH: keyPath
|
|
405
|
-
}
|
|
406
|
-
};
|
|
407
|
-
settings.mcpServers = mcpServers;
|
|
408
|
-
}
|
|
409
|
-
} catch {
|
|
410
|
-
}
|
|
411
|
-
}
|
|
412
|
-
}
|
|
413
386
|
const perms = settings.permissions ?? {};
|
|
414
387
|
const allow = perms.allow ?? [];
|
|
415
388
|
const mcpAllows = ["mcp__agent-authority__list_platforms", "mcp__agent-authority__use_platform"];
|
|
@@ -420,6 +393,45 @@ function ensureHook() {
|
|
|
420
393
|
}
|
|
421
394
|
mkdirSync(dirname2(settingsPath), { recursive: true });
|
|
422
395
|
writeFileSync(settingsPath, JSON.stringify(settings, null, 2) + "\n", "utf-8");
|
|
396
|
+
ensureMcpJson();
|
|
397
|
+
}
|
|
398
|
+
function ensureMcpJson() {
|
|
399
|
+
const mcpJsonPath = resolve2(".mcp.json");
|
|
400
|
+
let mcpConfig = {};
|
|
401
|
+
if (existsSync(mcpJsonPath)) {
|
|
402
|
+
try {
|
|
403
|
+
mcpConfig = JSON.parse(readFileSync(mcpJsonPath, "utf-8"));
|
|
404
|
+
} catch {
|
|
405
|
+
return;
|
|
406
|
+
}
|
|
407
|
+
}
|
|
408
|
+
const servers = mcpConfig.mcpServers ?? {};
|
|
409
|
+
if (servers["agent-authority"]) return;
|
|
410
|
+
const envPath = resolve2(".env.agentvalet");
|
|
411
|
+
if (!existsSync(envPath)) return;
|
|
412
|
+
let envVars;
|
|
413
|
+
try {
|
|
414
|
+
envVars = parseEnvFile(readFileSync(envPath, "utf-8"));
|
|
415
|
+
} catch {
|
|
416
|
+
return;
|
|
417
|
+
}
|
|
418
|
+
const agentId = envVars["AGENTVALET_AGENT_ID"];
|
|
419
|
+
const ownerId = envVars["AGENTVALET_OWNER_ID"];
|
|
420
|
+
const apiUrl = envVars["AGENTVALET_API_URL"] ?? "https://api.agentvalet.ai";
|
|
421
|
+
const keyPath = envVars["AGENTVALET_PRIVATE_KEY_PATH"];
|
|
422
|
+
if (!agentId || !ownerId || !keyPath) return;
|
|
423
|
+
servers["agent-authority"] = {
|
|
424
|
+
command: "npx",
|
|
425
|
+
args: ["-y", "@agentvalet/register", "mcp-server"],
|
|
426
|
+
env: {
|
|
427
|
+
AGENT_ID: agentId,
|
|
428
|
+
OWNER_ID: ownerId,
|
|
429
|
+
PROXY_URL: apiUrl,
|
|
430
|
+
AGENT_PRIVATE_KEY_PATH: keyPath
|
|
431
|
+
}
|
|
432
|
+
};
|
|
433
|
+
mcpConfig.mcpServers = servers;
|
|
434
|
+
writeFileSync(mcpJsonPath, JSON.stringify(mcpConfig, null, 2) + "\n", "utf-8");
|
|
423
435
|
}
|
|
424
436
|
|
|
425
437
|
// src/index.ts
|
|
@@ -590,6 +602,9 @@ program.command("refresh").description("Refresh approved permissions and update
|
|
|
590
602
|
process.exit(3);
|
|
591
603
|
}
|
|
592
604
|
});
|
|
605
|
+
program.command("mcp-server").description("Start the AgentValet MCP server (stdio transport)").action(async () => {
|
|
606
|
+
await import("./mcp-server-AM5ZYWTB.js");
|
|
607
|
+
});
|
|
593
608
|
program.parseAsync().catch((err) => {
|
|
594
609
|
console.error(err);
|
|
595
610
|
process.exit(3);
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
// src/commands/mcp-server.ts
|
|
2
|
+
import { readFileSync } from "fs";
|
|
3
|
+
import { Server } from "@modelcontextprotocol/sdk/server/index.js";
|
|
4
|
+
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
|
|
5
|
+
import { CallToolRequestSchema, ListToolsRequestSchema } from "@modelcontextprotocol/sdk/types.js";
|
|
6
|
+
import { SignJWT, importPKCS8 } from "jose";
|
|
7
|
+
if (!process.env.AGENT_PRIVATE_KEY && process.env.AGENT_PRIVATE_KEY_PATH) {
|
|
8
|
+
try {
|
|
9
|
+
process.env.AGENT_PRIVATE_KEY = readFileSync(process.env.AGENT_PRIVATE_KEY_PATH, "utf-8").trim();
|
|
10
|
+
} catch (err2) {
|
|
11
|
+
process.stderr.write(`[agent-authority] Cannot read AGENT_PRIVATE_KEY_PATH: ${err2 instanceof Error ? err2.message : err2}
|
|
12
|
+
`);
|
|
13
|
+
process.exit(1);
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
var REQUIRED = ["AGENT_PRIVATE_KEY", "AGENT_ID", "OWNER_ID", "PROXY_URL"];
|
|
17
|
+
for (const key of REQUIRED) {
|
|
18
|
+
if (!process.env[key]) {
|
|
19
|
+
process.stderr.write(`[agent-authority] Missing env var: ${key}
|
|
20
|
+
`);
|
|
21
|
+
process.exit(1);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
var AGENT_PRIVATE_KEY_RAW = process.env.AGENT_PRIVATE_KEY;
|
|
25
|
+
var AGENT_ID = process.env.AGENT_ID;
|
|
26
|
+
var OWNER_ID = process.env.OWNER_ID;
|
|
27
|
+
var PROXY_URL = process.env.PROXY_URL.replace(/\/$/, "");
|
|
28
|
+
var privateKey = null;
|
|
29
|
+
if (AGENT_PRIVATE_KEY_RAW !== "PENDING_FIRST_CALL") {
|
|
30
|
+
const raw = AGENT_PRIVATE_KEY_RAW.trim();
|
|
31
|
+
const pem = raw.startsWith("-----") ? raw.replace(/\\n/g, "\n") : `-----BEGIN PRIVATE KEY-----
|
|
32
|
+
${raw}
|
|
33
|
+
-----END PRIVATE KEY-----`;
|
|
34
|
+
try {
|
|
35
|
+
privateKey = await importPKCS8(pem, "RS256");
|
|
36
|
+
} catch (err2) {
|
|
37
|
+
process.stderr.write(`[agent-authority] Invalid private key: ${err2 instanceof Error ? err2.message : err2}
|
|
38
|
+
`);
|
|
39
|
+
process.exit(1);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
async function signJWT() {
|
|
43
|
+
if (!privateKey) throw new Error("Private key not loaded");
|
|
44
|
+
return new SignJWT({ agent_id: AGENT_ID, owner_id: OWNER_ID }).setProtectedHeader({ alg: "RS256" }).setIssuedAt().setExpirationTime("60s").sign(privateKey);
|
|
45
|
+
}
|
|
46
|
+
function fetchWithTimeout(url, init, ms = 15e3) {
|
|
47
|
+
const ac = new AbortController();
|
|
48
|
+
const t = setTimeout(() => ac.abort(), ms);
|
|
49
|
+
return fetch(url, { ...init, signal: ac.signal }).finally(() => clearTimeout(t));
|
|
50
|
+
}
|
|
51
|
+
async function bearerFetch(url, init) {
|
|
52
|
+
const token = await signJWT();
|
|
53
|
+
return fetchWithTimeout(url, {
|
|
54
|
+
...init,
|
|
55
|
+
headers: { Authorization: `Bearer ${token}`, "Content-Type": "application/json", ...init.headers }
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
function err(msg) {
|
|
59
|
+
return { content: [{ type: "text", text: msg }], isError: true };
|
|
60
|
+
}
|
|
61
|
+
function pendingResponse() {
|
|
62
|
+
return err("Agent not yet activated \u2014 owner confirmation pending. Retry in 60 seconds.");
|
|
63
|
+
}
|
|
64
|
+
var ALLOWED_METHODS = ["GET", "POST", "PUT", "PATCH", "DELETE"];
|
|
65
|
+
var server = new Server(
|
|
66
|
+
{ name: "agent-authority", version: "1.0.0" },
|
|
67
|
+
{ capabilities: { tools: {} } }
|
|
68
|
+
);
|
|
69
|
+
server.setRequestHandler(ListToolsRequestSchema, async () => ({
|
|
70
|
+
tools: [
|
|
71
|
+
{
|
|
72
|
+
name: "list_platforms",
|
|
73
|
+
description: "List the platforms and permission scopes this agent has access to.",
|
|
74
|
+
inputSchema: { type: "object", properties: {} }
|
|
75
|
+
},
|
|
76
|
+
{
|
|
77
|
+
name: "use_platform",
|
|
78
|
+
description: "Call an external platform API through the AgentValet proxy.",
|
|
79
|
+
inputSchema: {
|
|
80
|
+
type: "object",
|
|
81
|
+
properties: {
|
|
82
|
+
platform: { type: "string", description: "Platform ID (e.g. slack, github)" },
|
|
83
|
+
endpoint: { type: "string", description: "API path on the target platform" },
|
|
84
|
+
method: { type: "string", enum: ["GET", "POST", "PUT", "PATCH", "DELETE"] },
|
|
85
|
+
scope: { type: "string", description: "Permission scope required" },
|
|
86
|
+
data: { type: "object", description: "Optional request body" }
|
|
87
|
+
},
|
|
88
|
+
required: ["platform", "endpoint", "method", "scope"]
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
]
|
|
92
|
+
}));
|
|
93
|
+
server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
94
|
+
const { name, arguments: args } = request.params;
|
|
95
|
+
if (name === "list_platforms") {
|
|
96
|
+
if (AGENT_PRIVATE_KEY_RAW === "PENDING_FIRST_CALL") return pendingResponse();
|
|
97
|
+
try {
|
|
98
|
+
const res = await bearerFetch(`${PROXY_URL}/v1/agent/permissions`, { method: "GET", headers: {} });
|
|
99
|
+
const body = await res.text();
|
|
100
|
+
if (!res.ok) return err(`Proxy error ${res.status}: ${body}`);
|
|
101
|
+
return { content: [{ type: "text", text: body }] };
|
|
102
|
+
} catch (e) {
|
|
103
|
+
return err(`Network error: ${e instanceof Error ? e.message : e}`);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
if (name === "use_platform") {
|
|
107
|
+
if (AGENT_PRIVATE_KEY_RAW === "PENDING_FIRST_CALL") return pendingResponse();
|
|
108
|
+
if (!args || typeof args.platform !== "string" || typeof args.endpoint !== "string" || typeof args.method !== "string" || typeof args.scope !== "string") {
|
|
109
|
+
return err("Missing required args: platform, endpoint, method, scope");
|
|
110
|
+
}
|
|
111
|
+
if (!ALLOWED_METHODS.includes(args.method)) return err(`Invalid method: ${args.method}`);
|
|
112
|
+
try {
|
|
113
|
+
const res = await bearerFetch(`${PROXY_URL}/v1/actions`, {
|
|
114
|
+
method: "POST",
|
|
115
|
+
body: JSON.stringify({
|
|
116
|
+
platform: args.platform,
|
|
117
|
+
endpoint: args.endpoint,
|
|
118
|
+
method: args.method,
|
|
119
|
+
scope: args.scope,
|
|
120
|
+
...args.data !== void 0 && { data: args.data }
|
|
121
|
+
})
|
|
122
|
+
});
|
|
123
|
+
const body = await res.text();
|
|
124
|
+
if (!res.ok) return err(`Proxy error ${res.status}: ${body}`);
|
|
125
|
+
return { content: [{ type: "text", text: body }] };
|
|
126
|
+
} catch (e) {
|
|
127
|
+
return err(`Network error: ${e instanceof Error ? e.message : e}`);
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
return err(`Unknown tool: ${name}`);
|
|
131
|
+
});
|
|
132
|
+
var transport = new StdioServerTransport();
|
|
133
|
+
await server.connect(transport);
|
package/package.json
CHANGED
|
@@ -1,53 +1,55 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@agentvalet/register",
|
|
3
|
-
"version": "0.1
|
|
4
|
-
"description": "Self-register AI agents with AgentValet",
|
|
5
|
-
"type": "module",
|
|
6
|
-
"bin": {
|
|
7
|
-
"agentvalet-register": "dist/index.js"
|
|
8
|
-
},
|
|
9
|
-
"files": [
|
|
10
|
-
"dist",
|
|
11
|
-
"README.md"
|
|
12
|
-
],
|
|
13
|
-
"scripts": {
|
|
14
|
-
"build": "tsup src/index.ts --format esm --dts --clean",
|
|
15
|
-
"dev": "tsx src/index.ts",
|
|
16
|
-
"test": "vitest run",
|
|
17
|
-
"typecheck": "tsc --noEmit",
|
|
18
|
-
"prepublishOnly": "pnpm build"
|
|
19
|
-
},
|
|
20
|
-
"dependencies": {
|
|
21
|
-
"
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
"
|
|
31
|
-
"
|
|
32
|
-
"
|
|
33
|
-
"
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
"
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
"
|
|
47
|
-
"
|
|
48
|
-
"
|
|
49
|
-
"
|
|
50
|
-
"
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
1
|
+
{
|
|
2
|
+
"name": "@agentvalet/register",
|
|
3
|
+
"version": "0.2.1",
|
|
4
|
+
"description": "Self-register AI agents with AgentValet",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"bin": {
|
|
7
|
+
"agentvalet-register": "dist/index.js"
|
|
8
|
+
},
|
|
9
|
+
"files": [
|
|
10
|
+
"dist",
|
|
11
|
+
"README.md"
|
|
12
|
+
],
|
|
13
|
+
"scripts": {
|
|
14
|
+
"build": "tsup src/index.ts --format esm --dts --clean",
|
|
15
|
+
"dev": "tsx src/index.ts",
|
|
16
|
+
"test": "vitest run",
|
|
17
|
+
"typecheck": "tsc --noEmit",
|
|
18
|
+
"prepublishOnly": "pnpm build"
|
|
19
|
+
},
|
|
20
|
+
"dependencies": {
|
|
21
|
+
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
22
|
+
"chalk": "^5.3.0",
|
|
23
|
+
"commander": "^12.0.0",
|
|
24
|
+
"jose": "^6.2.2",
|
|
25
|
+
"ora": "^8.0.1",
|
|
26
|
+
"prompts": "^2.4.2",
|
|
27
|
+
"undici": "^6.0.0"
|
|
28
|
+
},
|
|
29
|
+
"devDependencies": {
|
|
30
|
+
"@types/node": "^20.0.0",
|
|
31
|
+
"@types/prompts": "^2.4.0",
|
|
32
|
+
"tsup": "^8.0.0",
|
|
33
|
+
"tsx": "^4.0.0",
|
|
34
|
+
"typescript": "^5.0.0",
|
|
35
|
+
"vitest": "^1.5.0"
|
|
36
|
+
},
|
|
37
|
+
"engines": {
|
|
38
|
+
"node": ">=18"
|
|
39
|
+
},
|
|
40
|
+
"repository": {
|
|
41
|
+
"type": "git",
|
|
42
|
+
"url": "git+https://github.com/MCSEdwin/agentvalet.git",
|
|
43
|
+
"directory": "apps/cli"
|
|
44
|
+
},
|
|
45
|
+
"keywords": [
|
|
46
|
+
"ai",
|
|
47
|
+
"agents",
|
|
48
|
+
"auth",
|
|
49
|
+
"credentials",
|
|
50
|
+
"mcp",
|
|
51
|
+
"valet",
|
|
52
|
+
"agentvalet"
|
|
53
|
+
],
|
|
54
|
+
"license": "MIT"
|
|
55
|
+
}
|