@vinkius-core/mcp-fusion 2.6.0 → 2.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (140) hide show
  1. package/dist/cli/fusion.d.ts +101 -0
  2. package/dist/cli/fusion.d.ts.map +1 -0
  3. package/dist/cli/fusion.js +333 -0
  4. package/dist/cli/fusion.js.map +1 -0
  5. package/dist/client/FusionClient.d.ts +122 -1
  6. package/dist/client/FusionClient.d.ts.map +1 -1
  7. package/dist/client/FusionClient.js +173 -11
  8. package/dist/client/FusionClient.js.map +1 -1
  9. package/dist/client/index.d.ts +2 -2
  10. package/dist/client/index.d.ts.map +1 -1
  11. package/dist/client/index.js +1 -1
  12. package/dist/client/index.js.map +1 -1
  13. package/dist/core/StandardSchema.d.ts +178 -0
  14. package/dist/core/StandardSchema.d.ts.map +1 -0
  15. package/dist/core/StandardSchema.js +166 -0
  16. package/dist/core/StandardSchema.js.map +1 -0
  17. package/dist/core/createGroup.d.ts +140 -0
  18. package/dist/core/createGroup.d.ts.map +1 -0
  19. package/dist/core/createGroup.js +133 -0
  20. package/dist/core/createGroup.js.map +1 -0
  21. package/dist/core/execution/ExecutionPipeline.d.ts.map +1 -1
  22. package/dist/core/execution/ExecutionPipeline.js +6 -2
  23. package/dist/core/execution/ExecutionPipeline.js.map +1 -1
  24. package/dist/core/index.d.ts +7 -1
  25. package/dist/core/index.d.ts.map +1 -1
  26. package/dist/core/index.js +6 -0
  27. package/dist/core/index.js.map +1 -1
  28. package/dist/core/initFusion.d.ts +201 -0
  29. package/dist/core/initFusion.d.ts.map +1 -0
  30. package/dist/core/initFusion.js +134 -0
  31. package/dist/core/initFusion.js.map +1 -0
  32. package/dist/core/response.d.ts +49 -2
  33. package/dist/core/response.d.ts.map +1 -1
  34. package/dist/core/response.js +27 -5
  35. package/dist/core/response.js.map +1 -1
  36. package/dist/index.d.ts +57 -9
  37. package/dist/index.d.ts.map +1 -1
  38. package/dist/index.js +30 -4
  39. package/dist/index.js.map +1 -1
  40. package/dist/introspection/BehaviorDigest.d.ts +112 -0
  41. package/dist/introspection/BehaviorDigest.d.ts.map +1 -0
  42. package/dist/introspection/BehaviorDigest.js +146 -0
  43. package/dist/introspection/BehaviorDigest.js.map +1 -0
  44. package/dist/introspection/CapabilityLockfile.d.ts +259 -0
  45. package/dist/introspection/CapabilityLockfile.d.ts.map +1 -0
  46. package/dist/introspection/CapabilityLockfile.js +391 -0
  47. package/dist/introspection/CapabilityLockfile.js.map +1 -0
  48. package/dist/introspection/ContractAwareSelfHealing.d.ts +90 -0
  49. package/dist/introspection/ContractAwareSelfHealing.d.ts.map +1 -0
  50. package/dist/introspection/ContractAwareSelfHealing.js +132 -0
  51. package/dist/introspection/ContractAwareSelfHealing.js.map +1 -0
  52. package/dist/introspection/ContractDiff.d.ts +91 -0
  53. package/dist/introspection/ContractDiff.d.ts.map +1 -0
  54. package/dist/introspection/ContractDiff.js +466 -0
  55. package/dist/introspection/ContractDiff.js.map +1 -0
  56. package/dist/introspection/CryptoAttestation.d.ts +143 -0
  57. package/dist/introspection/CryptoAttestation.d.ts.map +1 -0
  58. package/dist/introspection/CryptoAttestation.js +194 -0
  59. package/dist/introspection/CryptoAttestation.js.map +1 -0
  60. package/dist/introspection/EntitlementScanner.d.ts +124 -0
  61. package/dist/introspection/EntitlementScanner.d.ts.map +1 -0
  62. package/dist/introspection/EntitlementScanner.js +244 -0
  63. package/dist/introspection/EntitlementScanner.js.map +1 -0
  64. package/dist/introspection/GovernanceObserver.d.ts +88 -0
  65. package/dist/introspection/GovernanceObserver.d.ts.map +1 -0
  66. package/dist/introspection/GovernanceObserver.js +132 -0
  67. package/dist/introspection/GovernanceObserver.js.map +1 -0
  68. package/dist/introspection/SemanticProbe.d.ts +207 -0
  69. package/dist/introspection/SemanticProbe.d.ts.map +1 -0
  70. package/dist/introspection/SemanticProbe.js +255 -0
  71. package/dist/introspection/SemanticProbe.js.map +1 -0
  72. package/dist/introspection/TokenEconomics.d.ts +210 -0
  73. package/dist/introspection/TokenEconomics.d.ts.map +1 -0
  74. package/dist/introspection/TokenEconomics.js +286 -0
  75. package/dist/introspection/TokenEconomics.js.map +1 -0
  76. package/dist/introspection/ToolContract.d.ts +159 -0
  77. package/dist/introspection/ToolContract.d.ts.map +1 -0
  78. package/dist/introspection/ToolContract.js +191 -0
  79. package/dist/introspection/ToolContract.js.map +1 -0
  80. package/dist/introspection/canonicalize.d.ts +20 -0
  81. package/dist/introspection/canonicalize.d.ts.map +1 -0
  82. package/dist/introspection/canonicalize.js +51 -0
  83. package/dist/introspection/canonicalize.js.map +1 -0
  84. package/dist/introspection/index.d.ts +20 -0
  85. package/dist/introspection/index.d.ts.map +1 -1
  86. package/dist/introspection/index.js +20 -0
  87. package/dist/introspection/index.js.map +1 -1
  88. package/dist/observability/DebugObserver.d.ts +26 -1
  89. package/dist/observability/DebugObserver.d.ts.map +1 -1
  90. package/dist/observability/DebugObserver.js +8 -1
  91. package/dist/observability/DebugObserver.js.map +1 -1
  92. package/dist/observability/index.d.ts +1 -1
  93. package/dist/observability/index.d.ts.map +1 -1
  94. package/dist/observability/index.js.map +1 -1
  95. package/dist/presenter/ZodDescriptionExtractor.d.ts +54 -0
  96. package/dist/presenter/ZodDescriptionExtractor.d.ts.map +1 -0
  97. package/dist/presenter/ZodDescriptionExtractor.js +131 -0
  98. package/dist/presenter/ZodDescriptionExtractor.js.map +1 -0
  99. package/dist/presenter/definePresenter.d.ts +172 -0
  100. package/dist/presenter/definePresenter.d.ts.map +1 -0
  101. package/dist/presenter/definePresenter.js +96 -0
  102. package/dist/presenter/definePresenter.js.map +1 -0
  103. package/dist/presenter/index.d.ts +3 -0
  104. package/dist/presenter/index.d.ts.map +1 -1
  105. package/dist/presenter/index.js +4 -0
  106. package/dist/presenter/index.js.map +1 -1
  107. package/dist/server/DevServer.d.ts +96 -0
  108. package/dist/server/DevServer.d.ts.map +1 -0
  109. package/dist/server/DevServer.js +187 -0
  110. package/dist/server/DevServer.js.map +1 -0
  111. package/dist/server/ServerAttachment.d.ts +41 -0
  112. package/dist/server/ServerAttachment.d.ts.map +1 -1
  113. package/dist/server/ServerAttachment.js +25 -1
  114. package/dist/server/ServerAttachment.js.map +1 -1
  115. package/dist/server/autoDiscover.d.ts +63 -0
  116. package/dist/server/autoDiscover.d.ts.map +1 -0
  117. package/dist/server/autoDiscover.js +157 -0
  118. package/dist/server/autoDiscover.js.map +1 -0
  119. package/dist/server/index.d.ts +4 -0
  120. package/dist/server/index.d.ts.map +1 -1
  121. package/dist/server/index.js +4 -0
  122. package/dist/server/index.js.map +1 -1
  123. package/dist/state-sync/PolicyValidator.d.ts +36 -0
  124. package/dist/state-sync/PolicyValidator.d.ts.map +1 -1
  125. package/dist/state-sync/PolicyValidator.js +35 -0
  126. package/dist/state-sync/PolicyValidator.js.map +1 -1
  127. package/dist/state-sync/ResponseDecorator.d.ts.map +1 -1
  128. package/dist/state-sync/ResponseDecorator.js +2 -1
  129. package/dist/state-sync/ResponseDecorator.js.map +1 -1
  130. package/dist/state-sync/StateSyncLayer.d.ts +5 -4
  131. package/dist/state-sync/StateSyncLayer.d.ts.map +1 -1
  132. package/dist/state-sync/StateSyncLayer.js +35 -4
  133. package/dist/state-sync/StateSyncLayer.js.map +1 -1
  134. package/dist/state-sync/index.d.ts +3 -1
  135. package/dist/state-sync/index.d.ts.map +1 -1
  136. package/dist/state-sync/index.js +1 -0
  137. package/dist/state-sync/index.js.map +1 -1
  138. package/dist/state-sync/types.d.ts +62 -0
  139. package/dist/state-sync/types.d.ts.map +1 -1
  140. package/package.json +45 -1
@@ -0,0 +1,143 @@
1
+ import type { ServerDigest } from './BehaviorDigest.js';
2
+ /**
3
+ * Configuration for zero-trust attestation.
4
+ *
5
+ * Passed to `AttachOptions.zeroTrust` in ServerAttachment.
6
+ */
7
+ export interface ZeroTrustConfig {
8
+ /**
9
+ * The signing strategy to use.
10
+ * - `'hmac'` — HMAC-SHA256 with a shared secret (built-in)
11
+ * - A custom `AttestationSigner` for external KMS integration
12
+ */
13
+ readonly signer: 'hmac' | AttestationSigner;
14
+ /**
15
+ * For `'hmac'` mode: the shared secret.
16
+ * Read from environment in production (never hardcode).
17
+ */
18
+ readonly secret?: string;
19
+ /**
20
+ * Expected server digest hash from a known-good build.
21
+ * When set, runtime verification will fail-fast if the
22
+ * re-computed digest doesn't match.
23
+ */
24
+ readonly expectedDigest?: string;
25
+ /**
26
+ * Whether to fail-fast on attestation failure.
27
+ * Default: `true` in production, `false` in development.
28
+ */
29
+ readonly failOnMismatch?: boolean;
30
+ /**
31
+ * Whether to expose the attestation in MCP capabilities.
32
+ * Default: `true`.
33
+ */
34
+ readonly exposeCapability?: boolean;
35
+ }
36
+ /**
37
+ * Pluggable signer interface for external KMS integration.
38
+ *
39
+ * Implementations should be stateless and async-safe.
40
+ * The `sign()` method receives the canonical digest string
41
+ * and returns a signature (hex-encoded or base64).
42
+ */
43
+ export interface AttestationSigner {
44
+ /** Human-readable name (e.g., 'sigstore', 'aws-kms') */
45
+ readonly name: string;
46
+ /** Sign a digest string */
47
+ sign(digest: string): Promise<string>;
48
+ /** Verify a digest against a signature */
49
+ verify(digest: string, signature: string): Promise<boolean>;
50
+ }
51
+ /**
52
+ * Result of an attestation operation.
53
+ */
54
+ export interface AttestationResult {
55
+ /** Whether the attestation was successful */
56
+ readonly valid: boolean;
57
+ /** The computed digest */
58
+ readonly computedDigest: string;
59
+ /** The expected digest (if configured) */
60
+ readonly expectedDigest: string | null;
61
+ /** The signature (if signing was performed) */
62
+ readonly signature: string | null;
63
+ /** Signer identity */
64
+ readonly signerName: string;
65
+ /** ISO-8601 timestamp of attestation */
66
+ readonly attestedAt: string;
67
+ /** Human-readable error message, if invalid */
68
+ readonly error: string | null;
69
+ }
70
+ /**
71
+ * Capability structure exposed via MCP `server.capabilities`.
72
+ *
73
+ * Clients can inspect this to verify the server's behavioral
74
+ * identity before trusting tool responses.
75
+ */
76
+ export interface FusionTrustCapability {
77
+ /** Current server behavioral digest */
78
+ readonly serverDigest: string;
79
+ /** Attestation signature (if signed) */
80
+ readonly signature: string | null;
81
+ /** Signer identity */
82
+ readonly signerName: string;
83
+ /** ISO-8601 timestamp of last attestation */
84
+ readonly attestedAt: string;
85
+ /** Number of tools covered by the attestation */
86
+ readonly toolCount: number;
87
+ /** Whether the attestation passed verification */
88
+ readonly verified: boolean;
89
+ }
90
+ /**
91
+ * Create an HMAC-SHA256 signer from a shared secret.
92
+ *
93
+ * @param secret - The shared secret (should be ≥32 bytes)
94
+ * @returns An `AttestationSigner` using HMAC-SHA256
95
+ */
96
+ export declare function createHmacSigner(secret: string): AttestationSigner;
97
+ /**
98
+ * Sign a server digest and produce an attestation result.
99
+ *
100
+ * @param serverDigest - The server's behavioral digest
101
+ * @param config - Zero-trust configuration
102
+ * @returns Attestation result with signature
103
+ */
104
+ export declare function attestServerDigest(serverDigest: ServerDigest, config: ZeroTrustConfig): Promise<AttestationResult>;
105
+ /**
106
+ * Verify a previously signed attestation.
107
+ *
108
+ * @param serverDigest - The current server digest
109
+ * @param signature - The signature to verify
110
+ * @param config - Zero-trust configuration
111
+ * @returns Attestation result with verification status
112
+ */
113
+ export declare function verifyAttestation(serverDigest: ServerDigest, signature: string, config: ZeroTrustConfig): Promise<AttestationResult>;
114
+ /**
115
+ * Runtime capability pinning — check that the current digest
116
+ * matches what was attested at build time.
117
+ *
118
+ * Designed to be called once at server startup in the `attach()` flow.
119
+ *
120
+ * @param currentDigest - Re-computed server digest
121
+ * @param config - Zero-trust configuration
122
+ * @returns Attestation result
123
+ * @throws If `failOnMismatch` is true and the digest doesn't match
124
+ */
125
+ export declare function verifyCapabilityPin(currentDigest: ServerDigest, config: ZeroTrustConfig): Promise<AttestationResult>;
126
+ /**
127
+ * Build the `fusionTrust` capability object for MCP exposure.
128
+ *
129
+ * @param attestation - A completed attestation result
130
+ * @param toolCount - Number of tools in the registry
131
+ * @returns Capability structure for `server.capabilities`
132
+ */
133
+ export declare function buildTrustCapability(attestation: AttestationResult, toolCount: number): FusionTrustCapability;
134
+ /**
135
+ * Error thrown when zero-trust attestation fails with failOnMismatch.
136
+ *
137
+ * Carries the full `AttestationResult` for programmatic inspection.
138
+ */
139
+ export declare class AttestationError extends Error {
140
+ readonly attestation: AttestationResult;
141
+ constructor(message: string, attestation: AttestationResult);
142
+ }
143
+ //# sourceMappingURL=CryptoAttestation.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CryptoAttestation.d.ts","sourceRoot":"","sources":["../../src/introspection/CryptoAttestation.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,194 @@
1
+ /**
2
+ * CryptoAttestation — Zero-Trust Runtime Verification
3
+ *
4
+ * **Evolution 1: Zero-Trust Runtime**
5
+ *
6
+ * Provides cryptographic attestation and capability pinning
7
+ * for MCP Fusion tool contracts. This module enables:
8
+ *
9
+ * 1. **Digital Signing**: Sign a `ToolContract` or `ServerDigest`
10
+ * using HMAC-SHA256 (built-in) or pluggable external signers
11
+ * (Sigstore, AWS KMS, Azure Key Vault).
12
+ *
13
+ * 2. **Runtime Verification**: At server startup, re-compute the
14
+ * behavioral digest and compare it against the expected
15
+ * (signed) digest. If they differ, fail fast with a clear
16
+ * attestation error.
17
+ *
18
+ * 3. **Capability Pinning**: Expose a `fusionTrust` capability
19
+ * in the MCP `server.capabilities` that clients can inspect
20
+ * to verify the server's behavioral identity.
21
+ *
22
+ * **Zero-overhead principle**: When attestation is not configured,
23
+ * no cryptographic operations execute — the attach flow is
24
+ * identical to the default path.
25
+ *
26
+ * @module
27
+ */
28
+ import { createHmac, timingSafeEqual } from 'node:crypto';
29
+ // ============================================================================
30
+ // HMAC Signer (Built-in)
31
+ // ============================================================================
32
+ /**
33
+ * Create an HMAC-SHA256 signer from a shared secret.
34
+ *
35
+ * @param secret - The shared secret (should be ≥32 bytes)
36
+ * @returns An `AttestationSigner` using HMAC-SHA256
37
+ */
38
+ export function createHmacSigner(secret) {
39
+ return {
40
+ name: 'hmac-sha256',
41
+ async sign(digest) {
42
+ return hmacSign(digest, secret);
43
+ },
44
+ async verify(digest, signature) {
45
+ const expected = hmacSign(digest, secret);
46
+ return timingSafeCompare(expected, signature);
47
+ },
48
+ };
49
+ }
50
+ // ============================================================================
51
+ // Attestation Operations
52
+ // ============================================================================
53
+ /**
54
+ * Sign a server digest and produce an attestation result.
55
+ *
56
+ * @param serverDigest - The server's behavioral digest
57
+ * @param config - Zero-trust configuration
58
+ * @returns Attestation result with signature
59
+ */
60
+ export async function attestServerDigest(serverDigest, config) {
61
+ const signer = resolveSigner(config);
62
+ const signature = await signer.sign(serverDigest.digest);
63
+ const attestedAt = new Date().toISOString();
64
+ // Verify against expected digest if configured
65
+ if (config.expectedDigest) {
66
+ const matches = serverDigest.digest === config.expectedDigest;
67
+ return {
68
+ valid: matches,
69
+ computedDigest: serverDigest.digest,
70
+ expectedDigest: config.expectedDigest,
71
+ signature,
72
+ signerName: signer.name,
73
+ attestedAt,
74
+ error: matches ? null : `Attestation failed: computed digest ${serverDigest.digest} does not match expected ${config.expectedDigest}`,
75
+ };
76
+ }
77
+ return {
78
+ valid: true,
79
+ computedDigest: serverDigest.digest,
80
+ expectedDigest: null,
81
+ signature,
82
+ signerName: signer.name,
83
+ attestedAt,
84
+ error: null,
85
+ };
86
+ }
87
+ /**
88
+ * Verify a previously signed attestation.
89
+ *
90
+ * @param serverDigest - The current server digest
91
+ * @param signature - The signature to verify
92
+ * @param config - Zero-trust configuration
93
+ * @returns Attestation result with verification status
94
+ */
95
+ export async function verifyAttestation(serverDigest, signature, config) {
96
+ const signer = resolveSigner(config);
97
+ const verified = await signer.verify(serverDigest.digest, signature);
98
+ const attestedAt = new Date().toISOString();
99
+ return {
100
+ valid: verified,
101
+ computedDigest: serverDigest.digest,
102
+ expectedDigest: config.expectedDigest ?? null,
103
+ signature,
104
+ signerName: signer.name,
105
+ attestedAt,
106
+ error: verified ? null : `Signature verification failed for digest ${serverDigest.digest}`,
107
+ };
108
+ }
109
+ /**
110
+ * Runtime capability pinning — check that the current digest
111
+ * matches what was attested at build time.
112
+ *
113
+ * Designed to be called once at server startup in the `attach()` flow.
114
+ *
115
+ * @param currentDigest - Re-computed server digest
116
+ * @param config - Zero-trust configuration
117
+ * @returns Attestation result
118
+ * @throws If `failOnMismatch` is true and the digest doesn't match
119
+ */
120
+ export async function verifyCapabilityPin(currentDigest, config) {
121
+ const result = await attestServerDigest(currentDigest, config);
122
+ if (!result.valid && (config.failOnMismatch ?? true)) {
123
+ throw new AttestationError(`[MCP Fusion] Zero-Trust attestation failed: ${result.error}`, result);
124
+ }
125
+ return result;
126
+ }
127
+ /**
128
+ * Build the `fusionTrust` capability object for MCP exposure.
129
+ *
130
+ * @param attestation - A completed attestation result
131
+ * @param toolCount - Number of tools in the registry
132
+ * @returns Capability structure for `server.capabilities`
133
+ */
134
+ export function buildTrustCapability(attestation, toolCount) {
135
+ return {
136
+ serverDigest: attestation.computedDigest,
137
+ signature: attestation.signature,
138
+ signerName: attestation.signerName,
139
+ attestedAt: attestation.attestedAt,
140
+ toolCount,
141
+ verified: attestation.valid,
142
+ };
143
+ }
144
+ // ============================================================================
145
+ // Attestation Error
146
+ // ============================================================================
147
+ /**
148
+ * Error thrown when zero-trust attestation fails with failOnMismatch.
149
+ *
150
+ * Carries the full `AttestationResult` for programmatic inspection.
151
+ */
152
+ export class AttestationError extends Error {
153
+ attestation;
154
+ constructor(message, attestation) {
155
+ super(message);
156
+ this.name = 'AttestationError';
157
+ this.attestation = attestation;
158
+ }
159
+ }
160
+ // ============================================================================
161
+ // Internals
162
+ // ============================================================================
163
+ /**
164
+ * Resolve the signer from config.
165
+ * @internal
166
+ */
167
+ function resolveSigner(config) {
168
+ if (config.signer === 'hmac') {
169
+ if (!config.secret) {
170
+ throw new Error('[MCP Fusion] HMAC signer requires a secret. Set zeroTrust.secret or use a custom signer.');
171
+ }
172
+ return createHmacSigner(config.secret);
173
+ }
174
+ return config.signer;
175
+ }
176
+ /**
177
+ * HMAC-SHA256 sign.
178
+ * @internal
179
+ */
180
+ function hmacSign(data, secret) {
181
+ return createHmac('sha256', secret).update(data, 'utf8').digest('hex');
182
+ }
183
+ /**
184
+ * Timing-safe string comparison to prevent timing attacks.
185
+ * @internal
186
+ */
187
+ function timingSafeCompare(a, b) {
188
+ if (a.length !== b.length)
189
+ return false;
190
+ const bufA = Buffer.from(a, 'utf8');
191
+ const bufB = Buffer.from(b, 'utf8');
192
+ return timingSafeEqual(bufA, bufB);
193
+ }
194
+ //# sourceMappingURL=CryptoAttestation.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CryptoAttestation.js","sourceRoot":"","sources":["../../src/introspection/CryptoAttestation.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,124 @@
1
+ /**
2
+ * EntitlementScanner — AST-Based Blast Radius Analysis
3
+ *
4
+ * **Evolution 5: Blast Radius**
5
+ *
6
+ * Performs static analysis of handler source files to detect
7
+ * I/O capabilities (filesystem, network, subprocess, crypto)
8
+ * that expand the tool's blast radius beyond what its
9
+ * declarative contract suggests.
10
+ *
11
+ * **Key insight**: A tool declared as `readOnly: true` that
12
+ * imports `child_process` has a mismatch between its declared
13
+ * contract and its actual capabilities. This scanner detects
14
+ * such mismatches and reports them as entitlement violations.
15
+ *
16
+ * **Implementation approach**: Instead of a full TypeScript AST
17
+ * parser (which would require `typescript` as a dependency),
18
+ * this module uses regex-based pattern matching on source text.
19
+ * This is deliberately conservative — it may over-report but
20
+ * never under-report.
21
+ *
22
+ * **Contract integration**: The entitlement report is embedded
23
+ * in the `ToolContract.entitlements` field, making entitlement
24
+ * changes trackable via `ContractDiff`.
25
+ *
26
+ * Pure-function module: no state, no side effects.
27
+ *
28
+ * @module
29
+ */
30
+ import type { HandlerEntitlements } from './ToolContract.js';
31
+ /**
32
+ * Complete entitlement report for a handler.
33
+ */
34
+ export interface EntitlementReport {
35
+ /** Resolved entitlements */
36
+ readonly entitlements: HandlerEntitlements;
37
+ /** All detected entitlement matches */
38
+ readonly matches: readonly EntitlementMatch[];
39
+ /** Entitlement violations (declared vs detected mismatches) */
40
+ readonly violations: readonly EntitlementViolation[];
41
+ /** Whether the handler is considered safe */
42
+ readonly safe: boolean;
43
+ /** Human-readable summary */
44
+ readonly summary: string;
45
+ }
46
+ /**
47
+ * A single entitlement match detected in source code.
48
+ */
49
+ export interface EntitlementMatch {
50
+ /** Which entitlement category */
51
+ readonly category: EntitlementCategory;
52
+ /** The specific API/import detected */
53
+ readonly identifier: string;
54
+ /** Pattern that matched */
55
+ readonly pattern: string;
56
+ /** Source text (context around the match) */
57
+ readonly context: string;
58
+ /** Line number in the source (1-based) */
59
+ readonly line: number;
60
+ }
61
+ /**
62
+ * An entitlement violation — mismatch between declaration and detection.
63
+ */
64
+ export interface EntitlementViolation {
65
+ /** Which entitlement is violated */
66
+ readonly category: EntitlementCategory;
67
+ /** What was declared (e.g., readOnly: true) */
68
+ readonly declared: string;
69
+ /** What was detected */
70
+ readonly detected: string;
71
+ /** Severity */
72
+ readonly severity: 'warning' | 'error';
73
+ /** Human-readable description */
74
+ readonly description: string;
75
+ }
76
+ /** Entitlement categories */
77
+ export type EntitlementCategory = 'filesystem' | 'network' | 'subprocess' | 'crypto';
78
+ /**
79
+ * Declaration claims for validation against detected entitlements.
80
+ */
81
+ export interface EntitlementClaims {
82
+ /** Whether the action is declared as readOnly */
83
+ readonly readOnly?: boolean;
84
+ /** Whether the action is declared as destructive */
85
+ readonly destructive?: boolean;
86
+ /** Explicitly allowed entitlements (bypasses violation detection) */
87
+ readonly allowed?: readonly EntitlementCategory[];
88
+ }
89
+ /**
90
+ * Scan source text for entitlement patterns.
91
+ *
92
+ * @param source - The source code text to scan
93
+ * @param fileName - File name for reporting (optional)
94
+ * @returns All entitlement matches found
95
+ */
96
+ export declare function scanSource(source: string, fileName?: string): readonly EntitlementMatch[];
97
+ /**
98
+ * Build `HandlerEntitlements` from detected matches.
99
+ *
100
+ * @param matches - Detected entitlement matches
101
+ * @returns Aggregated entitlements
102
+ */
103
+ export declare function buildEntitlements(matches: readonly EntitlementMatch[]): HandlerEntitlements;
104
+ /**
105
+ * Validate detected entitlements against declared claims.
106
+ *
107
+ * Uses a rule table instead of imperative branching.
108
+ * Each rule encodes a policy check as pure data.
109
+ *
110
+ * @param matches - Detected matches
111
+ * @param claims - Declared claims from action metadata
112
+ * @returns Violations found
113
+ */
114
+ export declare function validateClaims(matches: readonly EntitlementMatch[], claims: EntitlementClaims): readonly EntitlementViolation[];
115
+ /**
116
+ * Perform a complete entitlement scan and validation.
117
+ *
118
+ * @param source - Handler source code
119
+ * @param claims - Declared claims for validation
120
+ * @param fileName - Optional file name for reporting
121
+ * @returns Complete entitlement report
122
+ */
123
+ export declare function scanAndValidate(source: string, claims?: EntitlementClaims, fileName?: string): EntitlementReport;
124
+ //# sourceMappingURL=EntitlementScanner.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"EntitlementScanner.d.ts","sourceRoot":"","sources":["../../src/introspection/EntitlementScanner.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAC;AAM7D;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B,4BAA4B;IAC5B,QAAQ,CAAC,YAAY,EAAE,mBAAmB,CAAC;IAC3C,uCAAuC;IACvC,QAAQ,CAAC,OAAO,EAAE,SAAS,gBAAgB,EAAE,CAAC;IAC9C,+DAA+D;IAC/D,QAAQ,CAAC,UAAU,EAAE,SAAS,oBAAoB,EAAE,CAAC;IACrD,6CAA6C;IAC7C,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC;IACvB,6BAA6B;IAC7B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;CAC5B;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC7B,iCAAiC;IACjC,QAAQ,CAAC,QAAQ,EAAE,mBAAmB,CAAC;IACvC,uCAAuC;IACvC,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,2BAA2B;IAC3B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,6CAA6C;IAC7C,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,0CAA0C;IAC1C,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;CACzB;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACjC,oCAAoC;IACpC,QAAQ,CAAC,QAAQ,EAAE,mBAAmB,CAAC;IACvC,+CAA+C;IAC/C,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,wBAAwB;IACxB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,eAAe;IACf,QAAQ,CAAC,QAAQ,EAAE,SAAS,GAAG,OAAO,CAAC;IACvC,iCAAiC;IACjC,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;CAChC;AAED,6BAA6B;AAC7B,MAAM,MAAM,mBAAmB,GAAG,YAAY,GAAG,SAAS,GAAG,YAAY,GAAG,QAAQ,CAAC;AAErF;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B,iDAAiD;IACjD,QAAQ,CAAC,QAAQ,CAAC,EAAE,OAAO,CAAC;IAC5B,oDAAoD;IACpD,QAAQ,CAAC,WAAW,CAAC,EAAE,OAAO,CAAC;IAC/B,qEAAqE;IACrE,QAAQ,CAAC,OAAO,CAAC,EAAE,SAAS,mBAAmB,EAAE,CAAC;CACrD;AAsED;;;;;;GAMG;AACH,wBAAgB,UAAU,CACtB,MAAM,EAAE,MAAM,EACd,QAAQ,CAAC,EAAE,MAAM,GAClB,SAAS,gBAAgB,EAAE,CAyB7B;AAED;;;;;GAKG;AACH,wBAAgB,iBAAiB,CAC7B,OAAO,EAAE,SAAS,gBAAgB,EAAE,GACrC,mBAAmB,CAWrB;AA4ED;;;;;;;;;GASG;AACH,wBAAgB,cAAc,CAC1B,OAAO,EAAE,SAAS,gBAAgB,EAAE,EACpC,MAAM,EAAE,iBAAiB,GAC1B,SAAS,oBAAoB,EAAE,CAOjC;AAED;;;;;;;GAOG;AACH,wBAAgB,eAAe,CAC3B,MAAM,EAAE,MAAM,EACd,MAAM,GAAE,iBAAsB,EAC9B,QAAQ,CAAC,EAAE,MAAM,GAClB,iBAAiB,CAgBnB"}