@sanctuary-framework/mcp-server 0.3.0 → 0.3.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/cli.cjs +1044 -86
- package/dist/cli.cjs.map +1 -1
- package/dist/cli.js +1045 -87
- package/dist/cli.js.map +1 -1
- package/dist/index.cjs +1044 -86
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +58 -15
- package/dist/index.d.ts +58 -15
- package/dist/index.js +1045 -87
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.cts
CHANGED
|
@@ -255,9 +255,11 @@ declare class StateStore {
|
|
|
255
255
|
/**
|
|
256
256
|
* Import a previously exported state bundle.
|
|
257
257
|
*/
|
|
258
|
-
import(bundleBase64: string, conflictResolution
|
|
258
|
+
import(bundleBase64: string, conflictResolution: "skip" | "overwrite" | "version" | undefined, publicKeyResolver: (kid: string) => Uint8Array | null): Promise<{
|
|
259
259
|
imported_keys: number;
|
|
260
260
|
skipped_keys: number;
|
|
261
|
+
skipped_invalid_sig: number;
|
|
262
|
+
skipped_unknown_kid: number;
|
|
261
263
|
conflicts: number;
|
|
262
264
|
namespaces: string[];
|
|
263
265
|
imported_at: string;
|
|
@@ -1187,7 +1189,13 @@ interface Tier2Config {
|
|
|
1187
1189
|
interface ApprovalChannelConfig {
|
|
1188
1190
|
type: "stderr" | "webhook" | "callback";
|
|
1189
1191
|
timeout_seconds: number;
|
|
1190
|
-
|
|
1192
|
+
/**
|
|
1193
|
+
* SEC-002: auto_deny is hardcoded to true and not configurable.
|
|
1194
|
+
* Timeout on any approval channel ALWAYS results in denial.
|
|
1195
|
+
* This field is retained for backward compatibility with existing
|
|
1196
|
+
* policy files but is ignored — timeout always denies.
|
|
1197
|
+
*/
|
|
1198
|
+
auto_deny?: boolean;
|
|
1191
1199
|
webhook_url?: string;
|
|
1192
1200
|
webhook_secret?: string;
|
|
1193
1201
|
}
|
|
@@ -1215,7 +1223,7 @@ interface ApprovalRequest {
|
|
|
1215
1223
|
interface ApprovalResponse {
|
|
1216
1224
|
decision: "approve" | "deny";
|
|
1217
1225
|
decided_at: string;
|
|
1218
|
-
decided_by: "human" | "timeout" | "auto";
|
|
1226
|
+
decided_by: "human" | "timeout" | "auto" | "stderr:non-interactive";
|
|
1219
1227
|
}
|
|
1220
1228
|
/** Result of the approval gate evaluation */
|
|
1221
1229
|
interface GateResult {
|
|
@@ -1258,22 +1266,25 @@ interface ApprovalChannel {
|
|
|
1258
1266
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1259
1267
|
}
|
|
1260
1268
|
/**
|
|
1261
|
-
* Stderr approval channel —
|
|
1269
|
+
* Stderr approval channel — non-interactive informational channel.
|
|
1262
1270
|
*
|
|
1263
1271
|
* In the MCP stdio model:
|
|
1264
1272
|
* - stdin/stdout carry the MCP protocol (JSON-RPC)
|
|
1265
1273
|
* - stderr is available for out-of-band human communication
|
|
1266
1274
|
*
|
|
1267
|
-
*
|
|
1268
|
-
*
|
|
1269
|
-
*
|
|
1275
|
+
* Because stdin is consumed by the MCP JSON-RPC transport, this channel
|
|
1276
|
+
* CANNOT read interactive human input. It is strictly informational:
|
|
1277
|
+
* the prompt is displayed so the human sees what is happening, and the
|
|
1278
|
+
* operation is denied immediately.
|
|
1270
1279
|
*
|
|
1271
|
-
*
|
|
1272
|
-
*
|
|
1280
|
+
* SEC-002 + SEC-016 invariants:
|
|
1281
|
+
* - This channel ALWAYS denies. No configuration can change this.
|
|
1282
|
+
* - There is no timeout or async delay — denial is synchronous.
|
|
1283
|
+
* - The `auto_deny` config field is ignored (SEC-002).
|
|
1284
|
+
* - For interactive approval, use the dashboard or webhook channel.
|
|
1273
1285
|
*/
|
|
1274
1286
|
declare class StderrApprovalChannel implements ApprovalChannel {
|
|
1275
|
-
|
|
1276
|
-
constructor(config: ApprovalChannelConfig);
|
|
1287
|
+
constructor(_config: ApprovalChannelConfig);
|
|
1277
1288
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1278
1289
|
private formatPrompt;
|
|
1279
1290
|
}
|
|
@@ -1458,7 +1469,8 @@ interface DashboardConfig {
|
|
|
1458
1469
|
port: number;
|
|
1459
1470
|
host: string;
|
|
1460
1471
|
timeout_seconds: number;
|
|
1461
|
-
|
|
1472
|
+
/** SEC-002: auto_deny is always true. Field retained for interface compat but ignored. */
|
|
1473
|
+
auto_deny?: boolean;
|
|
1462
1474
|
/** Bearer token for API authentication. If omitted, auth is disabled. */
|
|
1463
1475
|
auth_token?: string;
|
|
1464
1476
|
/** TLS configuration for HTTPS. If omitted, plain HTTP is used. */
|
|
@@ -1478,6 +1490,9 @@ declare class DashboardApprovalChannel implements ApprovalChannel {
|
|
|
1478
1490
|
private dashboardHTML;
|
|
1479
1491
|
private authToken;
|
|
1480
1492
|
private useTLS;
|
|
1493
|
+
/** SEC-012: Short-lived session store. Sessions replace URL query tokens. */
|
|
1494
|
+
private sessions;
|
|
1495
|
+
private sessionCleanupTimer;
|
|
1481
1496
|
constructor(config: DashboardConfig);
|
|
1482
1497
|
/**
|
|
1483
1498
|
* Inject dependencies after construction.
|
|
@@ -1503,11 +1518,39 @@ declare class DashboardApprovalChannel implements ApprovalChannel {
|
|
|
1503
1518
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1504
1519
|
/**
|
|
1505
1520
|
* Verify bearer token authentication.
|
|
1506
|
-
*
|
|
1521
|
+
*
|
|
1522
|
+
* SEC-012: The long-lived auth token is ONLY accepted via the Authorization
|
|
1523
|
+
* header — never in URL query strings. For SSE and page loads that cannot
|
|
1524
|
+
* set headers, a short-lived session token (obtained via POST /auth/session)
|
|
1525
|
+
* is accepted via ?session= query parameter.
|
|
1526
|
+
*
|
|
1507
1527
|
* Returns true if auth passes, false if blocked (response already sent).
|
|
1508
1528
|
*/
|
|
1509
1529
|
private checkAuth;
|
|
1530
|
+
/**
|
|
1531
|
+
* Create a short-lived session by exchanging the long-lived auth token
|
|
1532
|
+
* (provided in the Authorization header) for a session ID.
|
|
1533
|
+
*/
|
|
1534
|
+
private createSession;
|
|
1535
|
+
/**
|
|
1536
|
+
* Validate a session ID — must exist and not be expired.
|
|
1537
|
+
*/
|
|
1538
|
+
private validateSession;
|
|
1539
|
+
/**
|
|
1540
|
+
* Remove all expired sessions.
|
|
1541
|
+
*/
|
|
1542
|
+
private cleanupSessions;
|
|
1510
1543
|
private handleRequest;
|
|
1544
|
+
/**
|
|
1545
|
+
* SEC-012: Exchange a long-lived auth token (in Authorization header)
|
|
1546
|
+
* for a short-lived session ID. The session ID can be used in URL
|
|
1547
|
+
* query parameters without exposing the long-lived credential.
|
|
1548
|
+
*
|
|
1549
|
+
* This endpoint performs its OWN auth check (header-only) because it
|
|
1550
|
+
* must reject query-parameter tokens and is called before the
|
|
1551
|
+
* normal checkAuth flow.
|
|
1552
|
+
*/
|
|
1553
|
+
private handleSessionExchange;
|
|
1511
1554
|
private serveDashboard;
|
|
1512
1555
|
private handleSSE;
|
|
1513
1556
|
private handleStatus;
|
|
@@ -1568,8 +1611,8 @@ interface WebhookConfig {
|
|
|
1568
1611
|
callback_host: string;
|
|
1569
1612
|
/** Seconds to wait for a callback before timeout */
|
|
1570
1613
|
timeout_seconds: number;
|
|
1571
|
-
/**
|
|
1572
|
-
auto_deny
|
|
1614
|
+
/** SEC-002: auto_deny is always true. Field retained for interface compat but ignored. */
|
|
1615
|
+
auto_deny?: boolean;
|
|
1573
1616
|
}
|
|
1574
1617
|
/** Outbound webhook payload */
|
|
1575
1618
|
interface WebhookPayload {
|
package/dist/index.d.ts
CHANGED
|
@@ -255,9 +255,11 @@ declare class StateStore {
|
|
|
255
255
|
/**
|
|
256
256
|
* Import a previously exported state bundle.
|
|
257
257
|
*/
|
|
258
|
-
import(bundleBase64: string, conflictResolution
|
|
258
|
+
import(bundleBase64: string, conflictResolution: "skip" | "overwrite" | "version" | undefined, publicKeyResolver: (kid: string) => Uint8Array | null): Promise<{
|
|
259
259
|
imported_keys: number;
|
|
260
260
|
skipped_keys: number;
|
|
261
|
+
skipped_invalid_sig: number;
|
|
262
|
+
skipped_unknown_kid: number;
|
|
261
263
|
conflicts: number;
|
|
262
264
|
namespaces: string[];
|
|
263
265
|
imported_at: string;
|
|
@@ -1187,7 +1189,13 @@ interface Tier2Config {
|
|
|
1187
1189
|
interface ApprovalChannelConfig {
|
|
1188
1190
|
type: "stderr" | "webhook" | "callback";
|
|
1189
1191
|
timeout_seconds: number;
|
|
1190
|
-
|
|
1192
|
+
/**
|
|
1193
|
+
* SEC-002: auto_deny is hardcoded to true and not configurable.
|
|
1194
|
+
* Timeout on any approval channel ALWAYS results in denial.
|
|
1195
|
+
* This field is retained for backward compatibility with existing
|
|
1196
|
+
* policy files but is ignored — timeout always denies.
|
|
1197
|
+
*/
|
|
1198
|
+
auto_deny?: boolean;
|
|
1191
1199
|
webhook_url?: string;
|
|
1192
1200
|
webhook_secret?: string;
|
|
1193
1201
|
}
|
|
@@ -1215,7 +1223,7 @@ interface ApprovalRequest {
|
|
|
1215
1223
|
interface ApprovalResponse {
|
|
1216
1224
|
decision: "approve" | "deny";
|
|
1217
1225
|
decided_at: string;
|
|
1218
|
-
decided_by: "human" | "timeout" | "auto";
|
|
1226
|
+
decided_by: "human" | "timeout" | "auto" | "stderr:non-interactive";
|
|
1219
1227
|
}
|
|
1220
1228
|
/** Result of the approval gate evaluation */
|
|
1221
1229
|
interface GateResult {
|
|
@@ -1258,22 +1266,25 @@ interface ApprovalChannel {
|
|
|
1258
1266
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1259
1267
|
}
|
|
1260
1268
|
/**
|
|
1261
|
-
* Stderr approval channel —
|
|
1269
|
+
* Stderr approval channel — non-interactive informational channel.
|
|
1262
1270
|
*
|
|
1263
1271
|
* In the MCP stdio model:
|
|
1264
1272
|
* - stdin/stdout carry the MCP protocol (JSON-RPC)
|
|
1265
1273
|
* - stderr is available for out-of-band human communication
|
|
1266
1274
|
*
|
|
1267
|
-
*
|
|
1268
|
-
*
|
|
1269
|
-
*
|
|
1275
|
+
* Because stdin is consumed by the MCP JSON-RPC transport, this channel
|
|
1276
|
+
* CANNOT read interactive human input. It is strictly informational:
|
|
1277
|
+
* the prompt is displayed so the human sees what is happening, and the
|
|
1278
|
+
* operation is denied immediately.
|
|
1270
1279
|
*
|
|
1271
|
-
*
|
|
1272
|
-
*
|
|
1280
|
+
* SEC-002 + SEC-016 invariants:
|
|
1281
|
+
* - This channel ALWAYS denies. No configuration can change this.
|
|
1282
|
+
* - There is no timeout or async delay — denial is synchronous.
|
|
1283
|
+
* - The `auto_deny` config field is ignored (SEC-002).
|
|
1284
|
+
* - For interactive approval, use the dashboard or webhook channel.
|
|
1273
1285
|
*/
|
|
1274
1286
|
declare class StderrApprovalChannel implements ApprovalChannel {
|
|
1275
|
-
|
|
1276
|
-
constructor(config: ApprovalChannelConfig);
|
|
1287
|
+
constructor(_config: ApprovalChannelConfig);
|
|
1277
1288
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1278
1289
|
private formatPrompt;
|
|
1279
1290
|
}
|
|
@@ -1458,7 +1469,8 @@ interface DashboardConfig {
|
|
|
1458
1469
|
port: number;
|
|
1459
1470
|
host: string;
|
|
1460
1471
|
timeout_seconds: number;
|
|
1461
|
-
|
|
1472
|
+
/** SEC-002: auto_deny is always true. Field retained for interface compat but ignored. */
|
|
1473
|
+
auto_deny?: boolean;
|
|
1462
1474
|
/** Bearer token for API authentication. If omitted, auth is disabled. */
|
|
1463
1475
|
auth_token?: string;
|
|
1464
1476
|
/** TLS configuration for HTTPS. If omitted, plain HTTP is used. */
|
|
@@ -1478,6 +1490,9 @@ declare class DashboardApprovalChannel implements ApprovalChannel {
|
|
|
1478
1490
|
private dashboardHTML;
|
|
1479
1491
|
private authToken;
|
|
1480
1492
|
private useTLS;
|
|
1493
|
+
/** SEC-012: Short-lived session store. Sessions replace URL query tokens. */
|
|
1494
|
+
private sessions;
|
|
1495
|
+
private sessionCleanupTimer;
|
|
1481
1496
|
constructor(config: DashboardConfig);
|
|
1482
1497
|
/**
|
|
1483
1498
|
* Inject dependencies after construction.
|
|
@@ -1503,11 +1518,39 @@ declare class DashboardApprovalChannel implements ApprovalChannel {
|
|
|
1503
1518
|
requestApproval(request: ApprovalRequest): Promise<ApprovalResponse>;
|
|
1504
1519
|
/**
|
|
1505
1520
|
* Verify bearer token authentication.
|
|
1506
|
-
*
|
|
1521
|
+
*
|
|
1522
|
+
* SEC-012: The long-lived auth token is ONLY accepted via the Authorization
|
|
1523
|
+
* header — never in URL query strings. For SSE and page loads that cannot
|
|
1524
|
+
* set headers, a short-lived session token (obtained via POST /auth/session)
|
|
1525
|
+
* is accepted via ?session= query parameter.
|
|
1526
|
+
*
|
|
1507
1527
|
* Returns true if auth passes, false if blocked (response already sent).
|
|
1508
1528
|
*/
|
|
1509
1529
|
private checkAuth;
|
|
1530
|
+
/**
|
|
1531
|
+
* Create a short-lived session by exchanging the long-lived auth token
|
|
1532
|
+
* (provided in the Authorization header) for a session ID.
|
|
1533
|
+
*/
|
|
1534
|
+
private createSession;
|
|
1535
|
+
/**
|
|
1536
|
+
* Validate a session ID — must exist and not be expired.
|
|
1537
|
+
*/
|
|
1538
|
+
private validateSession;
|
|
1539
|
+
/**
|
|
1540
|
+
* Remove all expired sessions.
|
|
1541
|
+
*/
|
|
1542
|
+
private cleanupSessions;
|
|
1510
1543
|
private handleRequest;
|
|
1544
|
+
/**
|
|
1545
|
+
* SEC-012: Exchange a long-lived auth token (in Authorization header)
|
|
1546
|
+
* for a short-lived session ID. The session ID can be used in URL
|
|
1547
|
+
* query parameters without exposing the long-lived credential.
|
|
1548
|
+
*
|
|
1549
|
+
* This endpoint performs its OWN auth check (header-only) because it
|
|
1550
|
+
* must reject query-parameter tokens and is called before the
|
|
1551
|
+
* normal checkAuth flow.
|
|
1552
|
+
*/
|
|
1553
|
+
private handleSessionExchange;
|
|
1511
1554
|
private serveDashboard;
|
|
1512
1555
|
private handleSSE;
|
|
1513
1556
|
private handleStatus;
|
|
@@ -1568,8 +1611,8 @@ interface WebhookConfig {
|
|
|
1568
1611
|
callback_host: string;
|
|
1569
1612
|
/** Seconds to wait for a callback before timeout */
|
|
1570
1613
|
timeout_seconds: number;
|
|
1571
|
-
/**
|
|
1572
|
-
auto_deny
|
|
1614
|
+
/** SEC-002: auto_deny is always true. Field retained for interface compat but ignored. */
|
|
1615
|
+
auto_deny?: boolean;
|
|
1573
1616
|
}
|
|
1574
1617
|
/** Outbound webhook payload */
|
|
1575
1618
|
interface WebhookPayload {
|