@kya-os/mcp-i 1.5.2 → 1.5.3-canary.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/compiler/config/injection.d.ts +5 -1
- package/dist/compiler/config/injection.js +25 -0
- package/dist/compiler/get-webpack-config/get-injected-variables.js +2 -0
- package/dist/runtime/adapter-express.js +1 -1
- package/dist/runtime/adapter-nextjs.js +1 -1
- package/dist/runtime/http.js +1 -1
- package/dist/runtime/index.d.ts +2 -0
- package/dist/runtime/index.js +13 -1
- package/dist/runtime/mcpi-runtime.d.ts +39 -0
- package/dist/runtime/mcpi-runtime.js +58 -0
- package/dist/runtime/proof-batch-queue.d.ts +3 -0
- package/dist/runtime/proof-batch-queue.js +21 -4
- package/dist/runtime/proof.d.ts +8 -6
- package/dist/runtime/proof.js +35 -16
- package/dist/runtime/request-context.d.ts +37 -0
- package/dist/runtime/request-context.js +56 -0
- package/dist/runtime/session.js +1 -0
- package/dist/runtime/stdio.js +1 -1
- package/dist/runtime/tool-protection-registry.d.ts +94 -0
- package/dist/runtime/tool-protection-registry.js +140 -0
- package/dist/runtime/tool-protection.d.ts +120 -0
- package/dist/runtime/tool-protection.js +192 -0
- package/dist/runtime/transports/http/index.js +2 -1
- package/dist/runtime/utils/tools.js +293 -76
- package/package.json +1 -1
package/dist/runtime/index.d.ts
CHANGED
|
@@ -19,6 +19,8 @@ export { type ProofDestination, type ProofBatchQueueConfig, ProofBatchQueue, KTA
|
|
|
19
19
|
export { CloudflareKVDelegationVerifier, } from "./delegation-verifier-kv";
|
|
20
20
|
export { AgentShieldAPIDelegationVerifier, } from "./delegation-verifier-agentshield";
|
|
21
21
|
export { MemoryDelegationVerifier, } from "./delegation-verifier-memory";
|
|
22
|
+
export { type ToolProtectionConfig, type ToolProtectionMap, type ToolProtectionConfigSource, ToolProtectionResolver, createToolProtectionResolver, InlineToolProtectionSource, FileToolProtectionSource, AgentShieldToolProtectionSource, } from "./tool-protection";
|
|
23
|
+
export { toolProtectionRegistry, isToolProtected, getToolProtection, } from "./tool-protection-registry";
|
|
22
24
|
export type { HandshakeRequest, SessionContext, NonceCache, NonceCacheEntry, NonceCacheConfig, } from "@kya-os/contracts/handshake";
|
|
23
25
|
export type { ProofMeta, DetachedProof, CanonicalHashes, AuditRecord, } from "@kya-os/contracts/proof";
|
|
24
26
|
export type { DelegationRecord, DelegationStatus, DelegationChain, DelegationConstraints, } from "@kya-os/contracts/delegation";
|
package/dist/runtime/index.js
CHANGED
|
@@ -6,7 +6,8 @@
|
|
|
6
6
|
* audit logging, and well-known endpoints.
|
|
7
7
|
*/
|
|
8
8
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
-
exports.MemoryDelegationVerifier = exports.AgentShieldAPIDelegationVerifier = exports.CloudflareKVDelegationVerifier = exports.createProofBatchQueue = exports.AgentShieldProofDestination = exports.KTAProofDestination = exports.ProofBatchQueue = exports.MemoryResumeTokenStore = exports.hasSensitiveScopes = exports.verifyOrHints = exports.extractScopes = exports.validateDelegation = exports.checkScopes = exports.createDelegationVerifier = exports.formatVerifyLink = exports.DemoConsole = exports.createDemoManager = exports.DemoManager = exports.createDebugEndpoint = exports.DebugManager = exports.extractDIDFromPath = exports.validateAgentDocument = exports.validateDIDDocument = exports.createWellKnownHandler = exports.WellKnownManager = exports.validateAuditRecord = exports.parseAuditLine = exports.logKeyRotationAudit = exports.defaultAuditLogger = exports.AuditLogger = exports.extractCanonicalData = exports.createProofResponse = exports.ProofGenerator = exports.validateHandshakeFormat = exports.createHandshakeRequest = exports.defaultSessionManager = exports.SessionManager = exports.IDENTITY_ERRORS = exports.ensureIdentity = exports.defaultIdentityManager = exports.IdentityManager = exports.RUNTIME_ERRORS = exports.RuntimeFactory = exports.createMCPIRuntime = exports.MCPIRuntime = void 0;
|
|
9
|
+
exports.AgentShieldToolProtectionSource = exports.FileToolProtectionSource = exports.InlineToolProtectionSource = exports.createToolProtectionResolver = exports.ToolProtectionResolver = exports.MemoryDelegationVerifier = exports.AgentShieldAPIDelegationVerifier = exports.CloudflareKVDelegationVerifier = exports.createProofBatchQueue = exports.AgentShieldProofDestination = exports.KTAProofDestination = exports.ProofBatchQueue = exports.MemoryResumeTokenStore = exports.hasSensitiveScopes = exports.verifyOrHints = exports.extractScopes = exports.validateDelegation = exports.checkScopes = exports.createDelegationVerifier = exports.formatVerifyLink = exports.DemoConsole = exports.createDemoManager = exports.DemoManager = exports.createDebugEndpoint = exports.DebugManager = exports.extractDIDFromPath = exports.validateAgentDocument = exports.validateDIDDocument = exports.createWellKnownHandler = exports.WellKnownManager = exports.validateAuditRecord = exports.parseAuditLine = exports.logKeyRotationAudit = exports.defaultAuditLogger = exports.AuditLogger = exports.extractCanonicalData = exports.createProofResponse = exports.ProofGenerator = exports.validateHandshakeFormat = exports.createHandshakeRequest = exports.defaultSessionManager = exports.SessionManager = exports.IDENTITY_ERRORS = exports.ensureIdentity = exports.defaultIdentityManager = exports.IdentityManager = exports.RUNTIME_ERRORS = exports.RuntimeFactory = exports.createMCPIRuntime = exports.MCPIRuntime = void 0;
|
|
10
|
+
exports.getToolProtection = exports.isToolProtected = exports.toolProtectionRegistry = void 0;
|
|
10
11
|
// Main runtime - now using core with Node.js providers
|
|
11
12
|
var mcpi_runtime_wrapper_1 = require("./mcpi-runtime-wrapper");
|
|
12
13
|
Object.defineProperty(exports, "MCPIRuntime", { enumerable: true, get: function () { return mcpi_runtime_wrapper_1.MCPIRuntimeWrapper; } });
|
|
@@ -79,3 +80,14 @@ var delegation_verifier_agentshield_1 = require("./delegation-verifier-agentshie
|
|
|
79
80
|
Object.defineProperty(exports, "AgentShieldAPIDelegationVerifier", { enumerable: true, get: function () { return delegation_verifier_agentshield_1.AgentShieldAPIDelegationVerifier; } });
|
|
80
81
|
var delegation_verifier_memory_1 = require("./delegation-verifier-memory");
|
|
81
82
|
Object.defineProperty(exports, "MemoryDelegationVerifier", { enumerable: true, get: function () { return delegation_verifier_memory_1.MemoryDelegationVerifier; } });
|
|
83
|
+
// Tool protection (NEW - Phase 1.5)
|
|
84
|
+
var tool_protection_1 = require("./tool-protection");
|
|
85
|
+
Object.defineProperty(exports, "ToolProtectionResolver", { enumerable: true, get: function () { return tool_protection_1.ToolProtectionResolver; } });
|
|
86
|
+
Object.defineProperty(exports, "createToolProtectionResolver", { enumerable: true, get: function () { return tool_protection_1.createToolProtectionResolver; } });
|
|
87
|
+
Object.defineProperty(exports, "InlineToolProtectionSource", { enumerable: true, get: function () { return tool_protection_1.InlineToolProtectionSource; } });
|
|
88
|
+
Object.defineProperty(exports, "FileToolProtectionSource", { enumerable: true, get: function () { return tool_protection_1.FileToolProtectionSource; } });
|
|
89
|
+
Object.defineProperty(exports, "AgentShieldToolProtectionSource", { enumerable: true, get: function () { return tool_protection_1.AgentShieldToolProtectionSource; } });
|
|
90
|
+
var tool_protection_registry_1 = require("./tool-protection-registry");
|
|
91
|
+
Object.defineProperty(exports, "toolProtectionRegistry", { enumerable: true, get: function () { return tool_protection_registry_1.toolProtectionRegistry; } });
|
|
92
|
+
Object.defineProperty(exports, "isToolProtected", { enumerable: true, get: function () { return tool_protection_registry_1.isToolProtected; } });
|
|
93
|
+
Object.defineProperty(exports, "getToolProtection", { enumerable: true, get: function () { return tool_protection_registry_1.getToolProtection; } });
|
|
@@ -10,6 +10,7 @@ import { WellKnownConfig } from "./well-known";
|
|
|
10
10
|
import { DemoManager } from "./demo";
|
|
11
11
|
import { DelegationVerifierConfig } from "./delegation-verifier";
|
|
12
12
|
import { NeedsAuthorizationError } from "@kya-os/contracts/runtime";
|
|
13
|
+
import { ToolProtectionMap, ToolProtectionResolver } from "./tool-protection";
|
|
13
14
|
/**
|
|
14
15
|
* Runtime environment check
|
|
15
16
|
*/
|
|
@@ -40,6 +41,30 @@ export interface MCPIRuntimeConfig {
|
|
|
40
41
|
logFunction?: (record: string) => void;
|
|
41
42
|
includePayloads?: boolean;
|
|
42
43
|
};
|
|
44
|
+
proofing?: {
|
|
45
|
+
/** Enable proof generation and submission */
|
|
46
|
+
enabled?: boolean;
|
|
47
|
+
/** Proof batch queue configuration */
|
|
48
|
+
batchQueue?: {
|
|
49
|
+
/** Proof submission destinations (AgentShield, KTA, etc.) */
|
|
50
|
+
destinations?: Array<{
|
|
51
|
+
/** Destination type */
|
|
52
|
+
type: "agentshield" | "kta";
|
|
53
|
+
/** API base URL */
|
|
54
|
+
apiUrl: string;
|
|
55
|
+
/** API key for authentication */
|
|
56
|
+
apiKey?: string;
|
|
57
|
+
}>;
|
|
58
|
+
/** Maximum batch size before auto-flush (default: 10) */
|
|
59
|
+
maxBatchSize?: number;
|
|
60
|
+
/** Flush interval in milliseconds (default: 5000) */
|
|
61
|
+
flushIntervalMs?: number;
|
|
62
|
+
/** Maximum retries per batch (default: 3) */
|
|
63
|
+
maxRetries?: number;
|
|
64
|
+
/** Enable debug logging */
|
|
65
|
+
debug?: boolean;
|
|
66
|
+
};
|
|
67
|
+
};
|
|
43
68
|
wellKnown?: WellKnownConfig;
|
|
44
69
|
delegation?: {
|
|
45
70
|
/** Enable delegation checks (default: false for backward compatibility) */
|
|
@@ -62,6 +87,15 @@ export interface MCPIRuntimeConfig {
|
|
|
62
87
|
/** Require authorization for unknown agents */
|
|
63
88
|
requireAuthForUnknown?: boolean;
|
|
64
89
|
};
|
|
90
|
+
/** Tool protection configuration (NEW - Phase 1.5) */
|
|
91
|
+
toolProtections?: ToolProtectionMap;
|
|
92
|
+
/** Local tool protection file path (default: tool-protections.json) */
|
|
93
|
+
toolProtectionsFile?: string | false;
|
|
94
|
+
/** AgentShield API configuration for fetching tool protections */
|
|
95
|
+
agentShield?: {
|
|
96
|
+
apiUrl: string;
|
|
97
|
+
apiKey?: string;
|
|
98
|
+
};
|
|
65
99
|
};
|
|
66
100
|
runtime?: {
|
|
67
101
|
showVerifyLink?: boolean;
|
|
@@ -83,6 +117,7 @@ export declare class MCPIRuntime {
|
|
|
83
117
|
private demoManager?;
|
|
84
118
|
private delegationVerifier?;
|
|
85
119
|
private resumeTokenStore;
|
|
120
|
+
private toolProtectionResolver?;
|
|
86
121
|
private config;
|
|
87
122
|
private cachedIdentity?;
|
|
88
123
|
constructor(config?: MCPIRuntimeConfig);
|
|
@@ -118,6 +153,10 @@ export declare class MCPIRuntime {
|
|
|
118
153
|
* Get demo manager
|
|
119
154
|
*/
|
|
120
155
|
getDemoManager(): DemoManager | undefined;
|
|
156
|
+
/**
|
|
157
|
+
* Get tool protection resolver (NEW - Phase 1.5)
|
|
158
|
+
*/
|
|
159
|
+
getToolProtectionResolver(): ToolProtectionResolver | undefined;
|
|
121
160
|
/**
|
|
122
161
|
* Get runtime statistics
|
|
123
162
|
*/
|
|
@@ -17,6 +17,8 @@ const debug_1 = require("./debug");
|
|
|
17
17
|
const demo_1 = require("./demo");
|
|
18
18
|
const delegation_verifier_1 = require("./delegation-verifier");
|
|
19
19
|
const auth_handshake_1 = require("./auth-handshake");
|
|
20
|
+
const tool_protection_1 = require("./tool-protection");
|
|
21
|
+
const tool_protection_registry_1 = require("./tool-protection-registry");
|
|
20
22
|
/**
|
|
21
23
|
* XMCP-I Runtime class
|
|
22
24
|
*/
|
|
@@ -29,6 +31,7 @@ class MCPIRuntime {
|
|
|
29
31
|
demoManager;
|
|
30
32
|
delegationVerifier; // NEW - Phase 1
|
|
31
33
|
resumeTokenStore; // NEW - Phase 1
|
|
34
|
+
toolProtectionResolver; // NEW - Phase 1.5
|
|
32
35
|
config;
|
|
33
36
|
cachedIdentity;
|
|
34
37
|
constructor(config = {}) {
|
|
@@ -49,6 +52,8 @@ class MCPIRuntime {
|
|
|
49
52
|
if (config.delegation?.enabled && config.delegation?.verifier) {
|
|
50
53
|
this.delegationVerifier = (0, delegation_verifier_1.createDelegationVerifier)(config.delegation.verifier);
|
|
51
54
|
}
|
|
55
|
+
// NOTE: Tool protection resolver is created in initialize()
|
|
56
|
+
// after identity is loaded, because AgentShield API needs the agent DID
|
|
52
57
|
}
|
|
53
58
|
/**
|
|
54
59
|
* Initialize the runtime (async setup)
|
|
@@ -58,6 +63,21 @@ class MCPIRuntime {
|
|
|
58
63
|
this.checkRuntimeEnvironment();
|
|
59
64
|
// Ensure identity is loaded
|
|
60
65
|
this.cachedIdentity = await this.identityManager.ensureIdentity();
|
|
66
|
+
// Create tool protection resolver NOW that we have the agent DID (NEW - Phase 1.5)
|
|
67
|
+
if (this.config.delegation?.enabled) {
|
|
68
|
+
this.toolProtectionResolver = (0, tool_protection_1.createToolProtectionResolver)({
|
|
69
|
+
inline: this.config.delegation.toolProtections,
|
|
70
|
+
localFile: this.config.delegation.toolProtectionsFile,
|
|
71
|
+
agentShield: this.config.delegation.agentShield
|
|
72
|
+
? {
|
|
73
|
+
apiUrl: this.config.delegation.agentShield.apiUrl,
|
|
74
|
+
agentDid: this.cachedIdentity.did, // ← FIX: Use actual DID!
|
|
75
|
+
apiKey: this.config.delegation.agentShield.apiKey,
|
|
76
|
+
}
|
|
77
|
+
: undefined,
|
|
78
|
+
debug: this.config.identity?.environment === 'development',
|
|
79
|
+
});
|
|
80
|
+
}
|
|
61
81
|
// Initialize well-known manager if configured
|
|
62
82
|
if (this.config.wellKnown) {
|
|
63
83
|
this.wellKnownManager = new well_known_1.WellKnownManager(this.cachedIdentity, this.config.wellKnown);
|
|
@@ -81,6 +101,38 @@ class MCPIRuntime {
|
|
|
81
101
|
if (this.demoManager?.isIdentityBadgeEnabled()) {
|
|
82
102
|
demo_1.DemoConsole.printDemoWarning();
|
|
83
103
|
}
|
|
104
|
+
// Resolve tool protection configuration (NEW - Phase 1.5)
|
|
105
|
+
if (this.toolProtectionResolver) {
|
|
106
|
+
const toolProtections = await this.toolProtectionResolver.resolve();
|
|
107
|
+
// Populate global registry so compiled code can access it
|
|
108
|
+
tool_protection_registry_1.toolProtectionRegistry.registerAll(toolProtections);
|
|
109
|
+
tool_protection_registry_1.toolProtectionRegistry.setDelegationVerifier(this.delegationVerifier);
|
|
110
|
+
tool_protection_registry_1.toolProtectionRegistry.setDebug(this.config.identity?.environment === 'development');
|
|
111
|
+
// Build auth config for the registry
|
|
112
|
+
if (this.delegationVerifier) {
|
|
113
|
+
const authConfig = {
|
|
114
|
+
delegationVerifier: this.delegationVerifier,
|
|
115
|
+
resumeTokenStore: this.resumeTokenStore,
|
|
116
|
+
kta: this.config.delegation?.authorization?.kta,
|
|
117
|
+
bouncer: {
|
|
118
|
+
authorizationUrl: this.config.delegation?.authorization?.authorizationUrl ||
|
|
119
|
+
"https://agentshield.example.com/consent",
|
|
120
|
+
resumeTokenTtl: this.config.delegation?.authorization?.resumeTokenTtl,
|
|
121
|
+
minReputationScore: this.config.delegation?.authorization?.minReputationScore,
|
|
122
|
+
requireAuthForUnknown: this.config.delegation?.authorization?.requireAuthForUnknown,
|
|
123
|
+
},
|
|
124
|
+
debug: this.config.identity?.environment === "development",
|
|
125
|
+
};
|
|
126
|
+
tool_protection_registry_1.toolProtectionRegistry.setAuthConfig(authConfig);
|
|
127
|
+
}
|
|
128
|
+
if (this.config.identity?.environment === 'development') {
|
|
129
|
+
const protectedTools = tool_protection_registry_1.toolProtectionRegistry.getProtectedTools();
|
|
130
|
+
console.error('✅ Tool protection configuration loaded');
|
|
131
|
+
if (protectedTools.length > 0) {
|
|
132
|
+
console.error(` Protected tools: ${protectedTools.join(', ')}`);
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
}
|
|
84
136
|
}
|
|
85
137
|
/**
|
|
86
138
|
* Validate handshake and create session
|
|
@@ -216,6 +268,12 @@ class MCPIRuntime {
|
|
|
216
268
|
getDemoManager() {
|
|
217
269
|
return this.demoManager;
|
|
218
270
|
}
|
|
271
|
+
/**
|
|
272
|
+
* Get tool protection resolver (NEW - Phase 1.5)
|
|
273
|
+
*/
|
|
274
|
+
getToolProtectionResolver() {
|
|
275
|
+
return this.toolProtectionResolver;
|
|
276
|
+
}
|
|
219
277
|
/**
|
|
220
278
|
* Get runtime statistics
|
|
221
279
|
*/
|
|
@@ -38,6 +38,9 @@ export declare class KTAProofDestination implements ProofDestination {
|
|
|
38
38
|
}
|
|
39
39
|
/**
|
|
40
40
|
* AgentShield proof submission destination
|
|
41
|
+
*
|
|
42
|
+
* Submits proofs to AgentShield's /api/v1/bouncer/proofs endpoint
|
|
43
|
+
* with proper authentication and session grouping.
|
|
41
44
|
*/
|
|
42
45
|
export declare class AgentShieldProofDestination implements ProofDestination {
|
|
43
46
|
name: string;
|
|
@@ -51,6 +51,9 @@ class KTAProofDestination {
|
|
|
51
51
|
exports.KTAProofDestination = KTAProofDestination;
|
|
52
52
|
/**
|
|
53
53
|
* AgentShield proof submission destination
|
|
54
|
+
*
|
|
55
|
+
* Submits proofs to AgentShield's /api/v1/bouncer/proofs endpoint
|
|
56
|
+
* with proper authentication and session grouping.
|
|
54
57
|
*/
|
|
55
58
|
class AgentShieldProofDestination {
|
|
56
59
|
name = 'AgentShield';
|
|
@@ -61,16 +64,30 @@ class AgentShieldProofDestination {
|
|
|
61
64
|
this.apiKey = apiKey;
|
|
62
65
|
}
|
|
63
66
|
async submit(proofs) {
|
|
64
|
-
|
|
67
|
+
if (proofs.length === 0) {
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
// Extract session_id from first proof for AgentShield session grouping
|
|
71
|
+
// AgentShield uses this for analytics and detection monitoring
|
|
72
|
+
const sessionId = proofs[0]?.meta?.sessionId || 'unknown';
|
|
73
|
+
// AgentShield API format requires delegation_id and session_id wrapper
|
|
74
|
+
const requestBody = {
|
|
75
|
+
delegation_id: null, // null for proofs without delegation context
|
|
76
|
+
session_id: sessionId, // AgentShield session grouping (same as meta.sessionId)
|
|
77
|
+
proofs: proofs
|
|
78
|
+
};
|
|
79
|
+
const response = await fetch(`${this.apiUrl}/api/v1/bouncer/proofs`, {
|
|
65
80
|
method: 'POST',
|
|
66
81
|
headers: {
|
|
67
82
|
'Content-Type': 'application/json',
|
|
68
|
-
'
|
|
83
|
+
'Authorization': `Bearer ${this.apiKey}`, // Bearer token format
|
|
69
84
|
},
|
|
70
|
-
body: JSON.stringify(
|
|
85
|
+
body: JSON.stringify(requestBody),
|
|
71
86
|
});
|
|
72
87
|
if (!response.ok) {
|
|
73
|
-
|
|
88
|
+
// Include response body in error for debugging
|
|
89
|
+
const errorBody = await response.text().catch(() => 'Unable to read error body');
|
|
90
|
+
throw new Error(`AgentShield proof submission failed: ${response.status} ${response.statusText}\n${errorBody}`);
|
|
74
91
|
}
|
|
75
92
|
}
|
|
76
93
|
}
|
package/dist/runtime/proof.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* Proof Generation for XMCP-I Runtime
|
|
3
3
|
*
|
|
4
|
-
* Handles JCS canonicalization, SHA-256 digest generation, and Ed25519
|
|
4
|
+
* Handles JCS canonicalization, SHA-256 digest generation, and Ed25519 JWS signing (compact format)
|
|
5
5
|
* according to requirements 5.1, 5.2, 5.3, 5.6.
|
|
6
6
|
*/
|
|
7
7
|
import { DetachedProof } from "@kya-os/contracts/proof";
|
|
@@ -38,7 +38,7 @@ export declare class ProofGenerator {
|
|
|
38
38
|
private identity;
|
|
39
39
|
constructor(identity: AgentIdentity);
|
|
40
40
|
/**
|
|
41
|
-
* Generate
|
|
41
|
+
* Generate proof for tool request/response
|
|
42
42
|
* Requirements: 5.1, 5.2, 5.3, 5.6
|
|
43
43
|
*/
|
|
44
44
|
generateProof(request: ToolRequest, response: ToolResponse, session: SessionContext, options?: ProofOptions): Promise<DetachedProof>;
|
|
@@ -57,16 +57,18 @@ export declare class ProofGenerator {
|
|
|
57
57
|
*/
|
|
58
58
|
private canonicalizeJSON;
|
|
59
59
|
/**
|
|
60
|
-
* Generate Ed25519
|
|
60
|
+
* Generate Ed25519 JWS in compact format (header.payload.signature)
|
|
61
61
|
* Requirement: 5.3
|
|
62
|
+
*
|
|
63
|
+
* Uses standard JWT claims (aud, sub, iss) in addition to custom claims
|
|
62
64
|
*/
|
|
63
|
-
private
|
|
65
|
+
private generateJWS;
|
|
64
66
|
/**
|
|
65
67
|
* Format base64 private key as PKCS#8 PEM for JOSE library
|
|
66
68
|
*/
|
|
67
69
|
private formatPrivateKeyAsPEM;
|
|
68
70
|
/**
|
|
69
|
-
* Verify a
|
|
71
|
+
* Verify a proof (for testing/validation)
|
|
70
72
|
*/
|
|
71
73
|
verifyProof(proof: DetachedProof, request: ToolRequest, response: ToolResponse): Promise<boolean>;
|
|
72
74
|
}
|
package/dist/runtime/proof.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
/**
|
|
3
|
-
*
|
|
3
|
+
* Proof Generation for XMCP-I Runtime
|
|
4
4
|
*
|
|
5
|
-
* Handles JCS canonicalization, SHA-256 digest generation, and Ed25519
|
|
5
|
+
* Handles JCS canonicalization, SHA-256 digest generation, and Ed25519 JWS signing (compact format)
|
|
6
6
|
* according to requirements 5.1, 5.2, 5.3, 5.6.
|
|
7
7
|
*/
|
|
8
8
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
@@ -21,7 +21,7 @@ class ProofGenerator {
|
|
|
21
21
|
this.identity = identity;
|
|
22
22
|
}
|
|
23
23
|
/**
|
|
24
|
-
* Generate
|
|
24
|
+
* Generate proof for tool request/response
|
|
25
25
|
* Requirements: 5.1, 5.2, 5.3, 5.6
|
|
26
26
|
*/
|
|
27
27
|
async generateProof(request, response, session, options = {}) {
|
|
@@ -39,8 +39,8 @@ class ProofGenerator {
|
|
|
39
39
|
responseHash: hashes.responseHash,
|
|
40
40
|
...options, // Include scopeId and delegationRef if provided
|
|
41
41
|
};
|
|
42
|
-
// Generate
|
|
43
|
-
const jws = await this.
|
|
42
|
+
// Generate JWS (compact format)
|
|
43
|
+
const jws = await this.generateJWS(meta);
|
|
44
44
|
return {
|
|
45
45
|
jws,
|
|
46
46
|
meta,
|
|
@@ -86,27 +86,46 @@ class ProofGenerator {
|
|
|
86
86
|
return (0, json_canonicalize_1.canonicalize)(obj);
|
|
87
87
|
}
|
|
88
88
|
/**
|
|
89
|
-
* Generate Ed25519
|
|
89
|
+
* Generate Ed25519 JWS in compact format (header.payload.signature)
|
|
90
90
|
* Requirement: 5.3
|
|
91
|
+
*
|
|
92
|
+
* Uses standard JWT claims (aud, sub, iss) in addition to custom claims
|
|
91
93
|
*/
|
|
92
|
-
async
|
|
94
|
+
async generateJWS(meta) {
|
|
93
95
|
try {
|
|
94
96
|
// Import the private key
|
|
95
97
|
const privateKeyPem = this.formatPrivateKeyAsPEM(this.identity.privateKey);
|
|
96
98
|
const privateKey = await (0, jose_1.importPKCS8)(privateKeyPem, "EdDSA");
|
|
97
|
-
// Create JWT with
|
|
98
|
-
|
|
99
|
+
// Create JWT payload with standard claims + custom proof data
|
|
100
|
+
// Standard JWT claims: aud (audience), sub (subject), iss (issuer)
|
|
101
|
+
// Custom claims: requestHash, responseHash, nonce, sessionId, etc.
|
|
102
|
+
const payload = {
|
|
103
|
+
// Standard JWT claims (RFC 7519)
|
|
104
|
+
aud: meta.audience, // Audience (who the token is for)
|
|
105
|
+
sub: meta.did, // Subject (agent DID)
|
|
106
|
+
iss: meta.did, // Issuer (agent DID - self-issued)
|
|
107
|
+
// Custom MCP-I proof claims
|
|
108
|
+
requestHash: meta.requestHash,
|
|
109
|
+
responseHash: meta.responseHash,
|
|
110
|
+
ts: meta.ts,
|
|
111
|
+
nonce: meta.nonce,
|
|
112
|
+
sessionId: meta.sessionId,
|
|
113
|
+
// Optional claims
|
|
114
|
+
...(meta.scopeId && { scopeId: meta.scopeId }),
|
|
115
|
+
...(meta.delegationRef && { delegationRef: meta.delegationRef }),
|
|
116
|
+
};
|
|
117
|
+
// Create and sign JWT (compact format: header.payload.signature)
|
|
118
|
+
const jwt = await new jose_1.SignJWT(payload)
|
|
99
119
|
.setProtectedHeader({
|
|
100
120
|
alg: "EdDSA",
|
|
101
121
|
kid: this.identity.keyId,
|
|
102
122
|
})
|
|
103
123
|
.sign(privateKey);
|
|
104
|
-
//
|
|
105
|
-
|
|
106
|
-
return `${header}..${signature}`;
|
|
124
|
+
// Return full compact JWS (NOT detached)
|
|
125
|
+
return jwt;
|
|
107
126
|
}
|
|
108
127
|
catch (error) {
|
|
109
|
-
throw new Error(`Failed to generate
|
|
128
|
+
throw new Error(`Failed to generate JWS: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
110
129
|
}
|
|
111
130
|
}
|
|
112
131
|
/**
|
|
@@ -143,7 +162,7 @@ class ProofGenerator {
|
|
|
143
162
|
return header + formattedKey + footer;
|
|
144
163
|
}
|
|
145
164
|
/**
|
|
146
|
-
* Verify a
|
|
165
|
+
* Verify a proof (for testing/validation)
|
|
147
166
|
*/
|
|
148
167
|
async verifyProof(proof, request, response) {
|
|
149
168
|
try {
|
|
@@ -155,9 +174,9 @@ class ProofGenerator {
|
|
|
155
174
|
return false;
|
|
156
175
|
}
|
|
157
176
|
// TODO: Verify JWS signature (requires public key)
|
|
158
|
-
// For now, just validate the structure
|
|
177
|
+
// For now, just validate the structure (compact JWS: header.payload.signature)
|
|
159
178
|
const jwsParts = proof.jws.split(".");
|
|
160
|
-
return jwsParts.length === 3 && jwsParts[1]
|
|
179
|
+
return jwsParts.length === 3 && jwsParts[0] !== "" && jwsParts[1] !== "" && jwsParts[2] !== "";
|
|
161
180
|
}
|
|
162
181
|
catch {
|
|
163
182
|
return false;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Request Context Management
|
|
3
|
+
*
|
|
4
|
+
* Uses AsyncLocalStorage to track request-scoped data like session information
|
|
5
|
+
* across async operations without needing to pass it through every function.
|
|
6
|
+
*
|
|
7
|
+
* This enables the compiler path to access session data (like agentDid) that
|
|
8
|
+
* was set during handshake processing.
|
|
9
|
+
*/
|
|
10
|
+
import type { SessionContext } from '@kya-os/contracts/handshake';
|
|
11
|
+
export interface RequestContext {
|
|
12
|
+
session?: SessionContext;
|
|
13
|
+
requestId?: string;
|
|
14
|
+
startTime?: number;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Run a function with request context
|
|
18
|
+
*/
|
|
19
|
+
export declare function runWithContext<T>(context: RequestContext, fn: () => T | Promise<T>): T | Promise<T>;
|
|
20
|
+
/**
|
|
21
|
+
* Get the current request context
|
|
22
|
+
*/
|
|
23
|
+
export declare function getContext(): RequestContext | undefined;
|
|
24
|
+
/**
|
|
25
|
+
* Get the current session from context
|
|
26
|
+
*/
|
|
27
|
+
export declare function getCurrentSession(): SessionContext | undefined;
|
|
28
|
+
/**
|
|
29
|
+
* Get the current agent DID from session
|
|
30
|
+
*/
|
|
31
|
+
export declare function getCurrentAgentDid(): string | undefined;
|
|
32
|
+
/**
|
|
33
|
+
* Set session in current context
|
|
34
|
+
*
|
|
35
|
+
* NOTE: This only works if called within a runWithContext block
|
|
36
|
+
*/
|
|
37
|
+
export declare function setSession(session: SessionContext): void;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Request Context Management
|
|
4
|
+
*
|
|
5
|
+
* Uses AsyncLocalStorage to track request-scoped data like session information
|
|
6
|
+
* across async operations without needing to pass it through every function.
|
|
7
|
+
*
|
|
8
|
+
* This enables the compiler path to access session data (like agentDid) that
|
|
9
|
+
* was set during handshake processing.
|
|
10
|
+
*/
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.runWithContext = runWithContext;
|
|
13
|
+
exports.getContext = getContext;
|
|
14
|
+
exports.getCurrentSession = getCurrentSession;
|
|
15
|
+
exports.getCurrentAgentDid = getCurrentAgentDid;
|
|
16
|
+
exports.setSession = setSession;
|
|
17
|
+
const async_hooks_1 = require("async_hooks");
|
|
18
|
+
const asyncLocalStorage = new async_hooks_1.AsyncLocalStorage();
|
|
19
|
+
/**
|
|
20
|
+
* Run a function with request context
|
|
21
|
+
*/
|
|
22
|
+
function runWithContext(context, fn) {
|
|
23
|
+
return asyncLocalStorage.run(context, fn);
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Get the current request context
|
|
27
|
+
*/
|
|
28
|
+
function getContext() {
|
|
29
|
+
return asyncLocalStorage.getStore();
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Get the current session from context
|
|
33
|
+
*/
|
|
34
|
+
function getCurrentSession() {
|
|
35
|
+
return getContext()?.session;
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Get the current agent DID from session
|
|
39
|
+
*/
|
|
40
|
+
function getCurrentAgentDid() {
|
|
41
|
+
return getCurrentSession()?.agentDid;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Set session in current context
|
|
45
|
+
*
|
|
46
|
+
* NOTE: This only works if called within a runWithContext block
|
|
47
|
+
*/
|
|
48
|
+
function setSession(session) {
|
|
49
|
+
const context = getContext();
|
|
50
|
+
if (context) {
|
|
51
|
+
context.session = session;
|
|
52
|
+
}
|
|
53
|
+
else {
|
|
54
|
+
console.warn('[RequestContext] Attempted to set session outside of request context');
|
|
55
|
+
}
|
|
56
|
+
}
|
package/dist/runtime/session.js
CHANGED
|
@@ -78,6 +78,7 @@ class SessionManager {
|
|
|
78
78
|
createdAt: now,
|
|
79
79
|
lastActivity: now,
|
|
80
80
|
ttlMinutes: this.config.sessionTtlMinutes,
|
|
81
|
+
agentDid: request.agentDid, // Pass through agent DID for delegation verification
|
|
81
82
|
};
|
|
82
83
|
// Store session
|
|
83
84
|
this.sessions.set(sessionId, session);
|