@nylorun/runtime 0.19.1-beta → 0.21.0-beta
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/CHANGELOG.md +90 -0
- package/README.md +22 -13
- package/dist/adapters/streams/s2.js +5 -11
- package/dist/api/components.d.ts +326 -205
- package/dist/api/components.js +3 -3
- package/dist/api/http/app.js +2 -0
- package/dist/api/http/define.d.ts +3 -2
- package/dist/api/http/define.js +10 -11
- package/dist/api/http/routes/mcp.d.ts +9 -0
- package/dist/api/http/routes/mcp.js +32 -0
- package/dist/api/http/routes/vaults.d.ts +1 -9
- package/dist/api/http/routes/vaults.js +3 -103
- package/dist/api/openapi.js +37 -6
- package/dist/artifacts/media-types.d.ts +2 -0
- package/dist/artifacts/media-types.js +5 -0
- package/dist/execution/types.d.ts +1 -1
- package/dist/gates/http-tool.d.ts +7 -0
- package/dist/gates/http-tool.js +34 -3
- package/dist/gates/mcp-handler.d.ts +4 -1
- package/dist/gates/mcp-handler.js +64 -8
- package/dist/gates/tenant-vaults.d.ts +9 -15
- package/dist/gates/tenant-vaults.js +9 -17
- package/dist/gates/tool-client.js +36 -17
- package/dist/gates/tool-contract.d.ts +19 -3
- package/dist/gates/tool-contract.js +9 -3
- package/dist/gates/tool-gate.d.ts +2 -2
- package/dist/harness/calls.d.ts +2 -0
- package/dist/harness/calls.js +13 -3
- package/dist/harness-api/record.d.ts +7 -6
- package/dist/harness-api/record.js +99 -17
- package/dist/harness-api/server.js +35 -27
- package/dist/harness-api/start.js +2 -1
- package/dist/host/app.d.ts +3 -0
- package/dist/host/app.js +33 -4
- package/dist/host/config-for.d.ts +0 -2
- package/dist/host/config-for.js +0 -1
- package/dist/host/create-host.d.ts +6 -0
- package/dist/host/create-host.js +1 -0
- package/dist/host/gates.js +0 -1
- package/dist/host/main.js +24 -7
- package/dist/host/stack-config.d.ts +5 -8
- package/dist/host/stack-config.js +9 -20
- package/dist/index.d.ts +0 -1
- package/dist/infra/index.d.ts +2 -1
- package/dist/infra/index.js +0 -1
- package/dist/infra/readiness.d.ts +6 -6
- package/dist/infra/readiness.js +2 -5
- package/dist/keys/client.js +1 -9
- package/dist/keys/keys.d.ts +11 -13
- package/dist/keys/keys.js +5 -7
- package/dist/management-openapi.json +671 -378
- package/dist/mcp/connect.d.ts +159 -13
- package/dist/mcp/connect.js +538 -55
- package/dist/mcp/pool.d.ts +11 -2
- package/dist/mcp/pool.js +74 -27
- package/dist/mcp/preview.d.ts +35 -0
- package/dist/mcp/preview.js +215 -0
- package/dist/mcp/snapshot.d.ts +79 -5
- package/dist/mcp/snapshot.js +145 -27
- package/dist/model/catalog.d.ts +14 -0
- package/dist/model/catalog.js +14 -1
- package/dist/model/pi-model.js +36 -2
- package/dist/openapi.json +644 -266
- package/dist/redact.d.ts +19 -1
- package/dist/redact.js +42 -13
- package/dist/sandbox/session-sandbox.d.ts +7 -0
- package/dist/sandbox/session-sandbox.js +89 -28
- package/dist/store/postgres/connect.d.ts +10 -0
- package/dist/store/postgres/connect.js +30 -3
- package/dist/store/postgres/control.d.ts +14 -0
- package/dist/store/postgres/control.js +187 -0
- package/dist/store/postgres/drizzle/0015_control_signals.sql +11 -0
- package/dist/store/postgres/drizzle/0016_mcp_oauth_removed.sql +5 -0
- package/dist/store/postgres/drizzle/meta/_journal.json +14 -0
- package/dist/store/postgres/schema.d.ts +122 -261
- package/dist/store/postgres/schema.js +22 -36
- package/dist/store/postgres/store.js +16 -18
- package/dist/store/postgres/tenant.d.ts +14 -0
- package/dist/store/postgres/tenant.js +22 -2
- package/dist/store/types.d.ts +42 -8
- package/dist/streams/types.d.ts +6 -29
- package/dist/streams/types.js +5 -4
- package/dist/tenant/artifact-tool.d.ts +9 -1
- package/dist/tenant/artifact-tool.js +113 -9
- package/dist/tenant/auth.d.ts +16 -6
- package/dist/tenant/auth.js +41 -17
- package/dist/tenant/commands.js +10 -6
- package/dist/tenant/context.d.ts +9 -6
- package/dist/tenant/control.d.ts +26 -0
- package/dist/tenant/control.js +35 -0
- package/dist/tenant/effects.d.ts +2 -2
- package/dist/tenant/effects.js +20 -5
- package/dist/tenant/ephemeral.d.ts +0 -6
- package/dist/tenant/ephemeral.js +1 -1
- package/dist/tenant/http.d.ts +4 -2
- package/dist/tenant/http.js +4 -2
- package/dist/tenant/identity-file.d.ts +16 -12
- package/dist/tenant/identity-file.js +41 -29
- package/dist/tenant/issuers.d.ts +4 -3
- package/dist/tenant/issuers.js +22 -16
- package/dist/tenant/outbound.d.ts +14 -5
- package/dist/tenant/outbound.js +21 -9
- package/dist/tenant/reset.d.ts +2 -2
- package/dist/tenant/reset.js +8 -2
- package/dist/tenant/resource-server.d.ts +56 -0
- package/dist/tenant/resource-server.js +62 -0
- package/dist/tenant/runtime.d.ts +1 -1
- package/dist/tenant/runtime.js +16 -15
- package/dist/tenant/scheduler.d.ts +1 -1
- package/dist/tenant/scheduler.js +1 -1
- package/dist/tenant/sessions.js +20 -3
- package/dist/tenant/store-pg.js +9 -0
- package/dist/tenant/streams.d.ts +16 -22
- package/dist/tenant/streams.js +7 -87
- package/dist/tenant/sweep.js +9 -1
- package/dist/tenant/tool-results.d.ts +57 -0
- package/dist/tenant/tool-results.js +298 -0
- package/dist/tenant/tool-search.d.ts +43 -0
- package/dist/tenant/tool-search.js +100 -0
- package/dist/tenant/transcript.d.ts +108 -0
- package/dist/tenant/transcript.js +13 -0
- package/dist/tenant/types.d.ts +0 -14
- package/dist/vault/crypto.d.ts +0 -7
- package/dist/vault/crypto.js +0 -16
- package/dist/vault/headers.d.ts +17 -0
- package/dist/vault/headers.js +61 -0
- package/dist/vault/service.d.ts +11 -68
- package/dist/vault/service.js +83 -438
- package/dist/vault/sources.d.ts +20 -48
- package/dist/vault/sources.js +25 -189
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +3 -3
- package/dist/streams/control.d.ts +0 -13
- package/dist/streams/control.js +0 -25
- package/dist/vault/oauth.d.ts +0 -55
- package/dist/vault/oauth.js +0 -186
|
@@ -1048,14 +1048,14 @@ export declare const vaultCredentials: import("drizzle-orm/pg-core").PgTableWith
|
|
|
1048
1048
|
tableName: "vault_credentials";
|
|
1049
1049
|
dataType: "string";
|
|
1050
1050
|
columnType: "PgText";
|
|
1051
|
-
data: "bearer" | "
|
|
1051
|
+
data: "bearer" | "headers" | "model";
|
|
1052
1052
|
driverParam: string;
|
|
1053
1053
|
notNull: true;
|
|
1054
1054
|
hasDefault: false;
|
|
1055
1055
|
isPrimaryKey: false;
|
|
1056
1056
|
isAutoincrement: false;
|
|
1057
1057
|
hasRuntimeDefault: false;
|
|
1058
|
-
enumValues: ["bearer", "
|
|
1058
|
+
enumValues: ["bearer", "headers", "model"];
|
|
1059
1059
|
baseColumn: never;
|
|
1060
1060
|
identity: undefined;
|
|
1061
1061
|
generated: undefined;
|
|
@@ -1442,264 +1442,6 @@ export declare const vaultIdempotency: import("drizzle-orm/pg-core").PgTableWith
|
|
|
1442
1442
|
};
|
|
1443
1443
|
dialect: 'pg';
|
|
1444
1444
|
}>;
|
|
1445
|
-
/**
|
|
1446
|
-
* An MCP OAuth connect between its start and its callback (F9 C2): found by the SHA-256 of its
|
|
1447
|
-
* `state`, used once, for ten minutes. The PKCE verifier and any client secret are sealed under
|
|
1448
|
-
* the vault key (`sealBytes`), which only the keys module holds.
|
|
1449
|
-
*/
|
|
1450
|
-
export declare const oauthPending: import("drizzle-orm/pg-core").PgTableWithColumns<{
|
|
1451
|
-
name: "oauth_pending";
|
|
1452
|
-
schema: "nylorun";
|
|
1453
|
-
columns: {
|
|
1454
|
-
stateHash: import("drizzle-orm/pg-core").PgColumn<{
|
|
1455
|
-
name: "stateHash";
|
|
1456
|
-
tableName: "oauth_pending";
|
|
1457
|
-
dataType: "string";
|
|
1458
|
-
columnType: "PgText";
|
|
1459
|
-
data: string;
|
|
1460
|
-
driverParam: string;
|
|
1461
|
-
notNull: true;
|
|
1462
|
-
hasDefault: false;
|
|
1463
|
-
isPrimaryKey: true;
|
|
1464
|
-
isAutoincrement: false;
|
|
1465
|
-
hasRuntimeDefault: false;
|
|
1466
|
-
enumValues: [string, ...string[]];
|
|
1467
|
-
baseColumn: never;
|
|
1468
|
-
identity: undefined;
|
|
1469
|
-
generated: undefined;
|
|
1470
|
-
}, {}, {}>;
|
|
1471
|
-
vaultId: import("drizzle-orm/pg-core").PgColumn<{
|
|
1472
|
-
name: "vaultId";
|
|
1473
|
-
tableName: "oauth_pending";
|
|
1474
|
-
dataType: "string";
|
|
1475
|
-
columnType: "PgText";
|
|
1476
|
-
data: string;
|
|
1477
|
-
driverParam: string;
|
|
1478
|
-
notNull: true;
|
|
1479
|
-
hasDefault: false;
|
|
1480
|
-
isPrimaryKey: false;
|
|
1481
|
-
isAutoincrement: false;
|
|
1482
|
-
hasRuntimeDefault: false;
|
|
1483
|
-
enumValues: [string, ...string[]];
|
|
1484
|
-
baseColumn: never;
|
|
1485
|
-
identity: undefined;
|
|
1486
|
-
generated: undefined;
|
|
1487
|
-
}, {}, {}>;
|
|
1488
|
-
server: import("drizzle-orm/pg-core").PgColumn<{
|
|
1489
|
-
name: "server";
|
|
1490
|
-
tableName: "oauth_pending";
|
|
1491
|
-
dataType: "string";
|
|
1492
|
-
columnType: "PgText";
|
|
1493
|
-
data: string;
|
|
1494
|
-
driverParam: string;
|
|
1495
|
-
notNull: true;
|
|
1496
|
-
hasDefault: false;
|
|
1497
|
-
isPrimaryKey: false;
|
|
1498
|
-
isAutoincrement: false;
|
|
1499
|
-
hasRuntimeDefault: false;
|
|
1500
|
-
enumValues: [string, ...string[]];
|
|
1501
|
-
baseColumn: never;
|
|
1502
|
-
identity: undefined;
|
|
1503
|
-
generated: undefined;
|
|
1504
|
-
}, {}, {}>;
|
|
1505
|
-
url: import("drizzle-orm/pg-core").PgColumn<{
|
|
1506
|
-
name: "url";
|
|
1507
|
-
tableName: "oauth_pending";
|
|
1508
|
-
dataType: "string";
|
|
1509
|
-
columnType: "PgText";
|
|
1510
|
-
data: string;
|
|
1511
|
-
driverParam: string;
|
|
1512
|
-
notNull: true;
|
|
1513
|
-
hasDefault: false;
|
|
1514
|
-
isPrimaryKey: false;
|
|
1515
|
-
isAutoincrement: false;
|
|
1516
|
-
hasRuntimeDefault: false;
|
|
1517
|
-
enumValues: [string, ...string[]];
|
|
1518
|
-
baseColumn: never;
|
|
1519
|
-
identity: undefined;
|
|
1520
|
-
generated: undefined;
|
|
1521
|
-
}, {}, {}>;
|
|
1522
|
-
tokenEndpoint: import("drizzle-orm/pg-core").PgColumn<{
|
|
1523
|
-
name: "tokenEndpoint";
|
|
1524
|
-
tableName: "oauth_pending";
|
|
1525
|
-
dataType: "string";
|
|
1526
|
-
columnType: "PgText";
|
|
1527
|
-
data: string;
|
|
1528
|
-
driverParam: string;
|
|
1529
|
-
notNull: true;
|
|
1530
|
-
hasDefault: false;
|
|
1531
|
-
isPrimaryKey: false;
|
|
1532
|
-
isAutoincrement: false;
|
|
1533
|
-
hasRuntimeDefault: false;
|
|
1534
|
-
enumValues: [string, ...string[]];
|
|
1535
|
-
baseColumn: never;
|
|
1536
|
-
identity: undefined;
|
|
1537
|
-
generated: undefined;
|
|
1538
|
-
}, {}, {}>;
|
|
1539
|
-
clientId: import("drizzle-orm/pg-core").PgColumn<{
|
|
1540
|
-
name: "clientId";
|
|
1541
|
-
tableName: "oauth_pending";
|
|
1542
|
-
dataType: "string";
|
|
1543
|
-
columnType: "PgText";
|
|
1544
|
-
data: string;
|
|
1545
|
-
driverParam: string;
|
|
1546
|
-
notNull: true;
|
|
1547
|
-
hasDefault: false;
|
|
1548
|
-
isPrimaryKey: false;
|
|
1549
|
-
isAutoincrement: false;
|
|
1550
|
-
hasRuntimeDefault: false;
|
|
1551
|
-
enumValues: [string, ...string[]];
|
|
1552
|
-
baseColumn: never;
|
|
1553
|
-
identity: undefined;
|
|
1554
|
-
generated: undefined;
|
|
1555
|
-
}, {}, {}>;
|
|
1556
|
-
tokenEndpointAuth: import("drizzle-orm/pg-core").PgColumn<{
|
|
1557
|
-
name: "tokenEndpointAuth";
|
|
1558
|
-
tableName: "oauth_pending";
|
|
1559
|
-
dataType: "string";
|
|
1560
|
-
columnType: "PgText";
|
|
1561
|
-
data: "client_secret_basic" | "client_secret_post" | "none";
|
|
1562
|
-
driverParam: string;
|
|
1563
|
-
notNull: true;
|
|
1564
|
-
hasDefault: false;
|
|
1565
|
-
isPrimaryKey: false;
|
|
1566
|
-
isAutoincrement: false;
|
|
1567
|
-
hasRuntimeDefault: false;
|
|
1568
|
-
enumValues: ["none", "client_secret_basic", "client_secret_post"];
|
|
1569
|
-
baseColumn: never;
|
|
1570
|
-
identity: undefined;
|
|
1571
|
-
generated: undefined;
|
|
1572
|
-
}, {}, {}>;
|
|
1573
|
-
resource: import("drizzle-orm/pg-core").PgColumn<{
|
|
1574
|
-
name: "resource";
|
|
1575
|
-
tableName: "oauth_pending";
|
|
1576
|
-
dataType: "string";
|
|
1577
|
-
columnType: "PgText";
|
|
1578
|
-
data: string;
|
|
1579
|
-
driverParam: string;
|
|
1580
|
-
notNull: false;
|
|
1581
|
-
hasDefault: false;
|
|
1582
|
-
isPrimaryKey: false;
|
|
1583
|
-
isAutoincrement: false;
|
|
1584
|
-
hasRuntimeDefault: false;
|
|
1585
|
-
enumValues: [string, ...string[]];
|
|
1586
|
-
baseColumn: never;
|
|
1587
|
-
identity: undefined;
|
|
1588
|
-
generated: undefined;
|
|
1589
|
-
}, {}, {}>;
|
|
1590
|
-
kekId: import("drizzle-orm/pg-core").PgColumn<{
|
|
1591
|
-
name: "kekId";
|
|
1592
|
-
tableName: "oauth_pending";
|
|
1593
|
-
dataType: "string";
|
|
1594
|
-
columnType: "PgText";
|
|
1595
|
-
data: string;
|
|
1596
|
-
driverParam: string;
|
|
1597
|
-
notNull: true;
|
|
1598
|
-
hasDefault: false;
|
|
1599
|
-
isPrimaryKey: false;
|
|
1600
|
-
isAutoincrement: false;
|
|
1601
|
-
hasRuntimeDefault: false;
|
|
1602
|
-
enumValues: [string, ...string[]];
|
|
1603
|
-
baseColumn: never;
|
|
1604
|
-
identity: undefined;
|
|
1605
|
-
generated: undefined;
|
|
1606
|
-
}, {}, {}>;
|
|
1607
|
-
clientSecret: import("drizzle-orm/pg-core").PgColumn<{
|
|
1608
|
-
name: "clientSecret";
|
|
1609
|
-
tableName: "oauth_pending";
|
|
1610
|
-
dataType: "custom";
|
|
1611
|
-
columnType: "PgCustomColumn";
|
|
1612
|
-
data: Uint8Array<ArrayBufferLike>;
|
|
1613
|
-
driverParam: Buffer<ArrayBufferLike>;
|
|
1614
|
-
notNull: false;
|
|
1615
|
-
hasDefault: false;
|
|
1616
|
-
isPrimaryKey: false;
|
|
1617
|
-
isAutoincrement: false;
|
|
1618
|
-
hasRuntimeDefault: false;
|
|
1619
|
-
enumValues: undefined;
|
|
1620
|
-
baseColumn: never;
|
|
1621
|
-
identity: undefined;
|
|
1622
|
-
generated: undefined;
|
|
1623
|
-
}, {}, {
|
|
1624
|
-
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
1625
|
-
}>;
|
|
1626
|
-
codeVerifier: import("drizzle-orm/pg-core").PgColumn<{
|
|
1627
|
-
name: "codeVerifier";
|
|
1628
|
-
tableName: "oauth_pending";
|
|
1629
|
-
dataType: "custom";
|
|
1630
|
-
columnType: "PgCustomColumn";
|
|
1631
|
-
data: Uint8Array<ArrayBufferLike>;
|
|
1632
|
-
driverParam: Buffer<ArrayBufferLike>;
|
|
1633
|
-
notNull: true;
|
|
1634
|
-
hasDefault: false;
|
|
1635
|
-
isPrimaryKey: false;
|
|
1636
|
-
isAutoincrement: false;
|
|
1637
|
-
hasRuntimeDefault: false;
|
|
1638
|
-
enumValues: undefined;
|
|
1639
|
-
baseColumn: never;
|
|
1640
|
-
identity: undefined;
|
|
1641
|
-
generated: undefined;
|
|
1642
|
-
}, {}, {
|
|
1643
|
-
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
1644
|
-
}>;
|
|
1645
|
-
redirectUri: import("drizzle-orm/pg-core").PgColumn<{
|
|
1646
|
-
name: "redirectUri";
|
|
1647
|
-
tableName: "oauth_pending";
|
|
1648
|
-
dataType: "string";
|
|
1649
|
-
columnType: "PgText";
|
|
1650
|
-
data: string;
|
|
1651
|
-
driverParam: string;
|
|
1652
|
-
notNull: true;
|
|
1653
|
-
hasDefault: false;
|
|
1654
|
-
isPrimaryKey: false;
|
|
1655
|
-
isAutoincrement: false;
|
|
1656
|
-
hasRuntimeDefault: false;
|
|
1657
|
-
enumValues: [string, ...string[]];
|
|
1658
|
-
baseColumn: never;
|
|
1659
|
-
identity: undefined;
|
|
1660
|
-
generated: undefined;
|
|
1661
|
-
}, {}, {}>;
|
|
1662
|
-
expiresAt: import("drizzle-orm/pg-core").PgColumn<{
|
|
1663
|
-
name: "expiresAt";
|
|
1664
|
-
tableName: "oauth_pending";
|
|
1665
|
-
dataType: "custom";
|
|
1666
|
-
columnType: "PgCustomColumn";
|
|
1667
|
-
data: string;
|
|
1668
|
-
driverParam: string;
|
|
1669
|
-
notNull: true;
|
|
1670
|
-
hasDefault: false;
|
|
1671
|
-
isPrimaryKey: false;
|
|
1672
|
-
isAutoincrement: false;
|
|
1673
|
-
hasRuntimeDefault: false;
|
|
1674
|
-
enumValues: undefined;
|
|
1675
|
-
baseColumn: never;
|
|
1676
|
-
identity: undefined;
|
|
1677
|
-
generated: undefined;
|
|
1678
|
-
}, {}, {
|
|
1679
|
-
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
1680
|
-
}>;
|
|
1681
|
-
createdAt: import("drizzle-orm/pg-core").PgColumn<{
|
|
1682
|
-
name: "createdAt";
|
|
1683
|
-
tableName: "oauth_pending";
|
|
1684
|
-
dataType: "custom";
|
|
1685
|
-
columnType: "PgCustomColumn";
|
|
1686
|
-
data: string;
|
|
1687
|
-
driverParam: string;
|
|
1688
|
-
notNull: true;
|
|
1689
|
-
hasDefault: false;
|
|
1690
|
-
isPrimaryKey: false;
|
|
1691
|
-
isAutoincrement: false;
|
|
1692
|
-
hasRuntimeDefault: false;
|
|
1693
|
-
enumValues: undefined;
|
|
1694
|
-
baseColumn: never;
|
|
1695
|
-
identity: undefined;
|
|
1696
|
-
generated: undefined;
|
|
1697
|
-
}, {}, {
|
|
1698
|
-
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
1699
|
-
}>;
|
|
1700
|
-
};
|
|
1701
|
-
dialect: 'pg';
|
|
1702
|
-
}>;
|
|
1703
1445
|
export declare const tenantSettings: import("drizzle-orm/pg-core").PgTableWithColumns<{
|
|
1704
1446
|
name: "tenant_settings";
|
|
1705
1447
|
schema: "nylorun";
|
|
@@ -3478,6 +3220,126 @@ export declare const definitionFileUses: import("drizzle-orm/pg-core").PgTableWi
|
|
|
3478
3220
|
};
|
|
3479
3221
|
dialect: 'pg';
|
|
3480
3222
|
}>;
|
|
3223
|
+
/**
|
|
3224
|
+
* The control bus (D21, D48): signals between the processes that have the Tenant open,
|
|
3225
|
+
* written in the transaction that commits what they announce and notified on
|
|
3226
|
+
* `nylorun_control` at commit (`control.ts`). A row outlives its notification so a process
|
|
3227
|
+
* whose listener was down catches up; the Tenant sweep deletes old ones. `created_at` is the
|
|
3228
|
+
* insert's own clock (`clock_timestamp()`), not its transaction's start.
|
|
3229
|
+
*/
|
|
3230
|
+
export declare const controlSignals: import("drizzle-orm/pg-core").PgTableWithColumns<{
|
|
3231
|
+
name: "control_signals";
|
|
3232
|
+
schema: "nylorun";
|
|
3233
|
+
columns: {
|
|
3234
|
+
id: import("drizzle-orm/pg-core").PgColumn<{
|
|
3235
|
+
name: "id";
|
|
3236
|
+
tableName: "control_signals";
|
|
3237
|
+
dataType: "number";
|
|
3238
|
+
columnType: "PgBigInt53";
|
|
3239
|
+
data: number;
|
|
3240
|
+
driverParam: string | number;
|
|
3241
|
+
notNull: true;
|
|
3242
|
+
hasDefault: true;
|
|
3243
|
+
isPrimaryKey: true;
|
|
3244
|
+
isAutoincrement: false;
|
|
3245
|
+
hasRuntimeDefault: false;
|
|
3246
|
+
enumValues: undefined;
|
|
3247
|
+
baseColumn: never;
|
|
3248
|
+
identity: "always";
|
|
3249
|
+
generated: undefined;
|
|
3250
|
+
}, {}, {}>;
|
|
3251
|
+
kind: import("drizzle-orm/pg-core").PgColumn<{
|
|
3252
|
+
name: "kind";
|
|
3253
|
+
tableName: "control_signals";
|
|
3254
|
+
dataType: "string";
|
|
3255
|
+
columnType: "PgText";
|
|
3256
|
+
data: string;
|
|
3257
|
+
driverParam: string;
|
|
3258
|
+
notNull: true;
|
|
3259
|
+
hasDefault: false;
|
|
3260
|
+
isPrimaryKey: false;
|
|
3261
|
+
isAutoincrement: false;
|
|
3262
|
+
hasRuntimeDefault: false;
|
|
3263
|
+
enumValues: [string, ...string[]];
|
|
3264
|
+
baseColumn: never;
|
|
3265
|
+
identity: undefined;
|
|
3266
|
+
generated: undefined;
|
|
3267
|
+
}, {}, {}>;
|
|
3268
|
+
sessionId: import("drizzle-orm/pg-core").PgColumn<{
|
|
3269
|
+
name: "sessionId";
|
|
3270
|
+
tableName: "control_signals";
|
|
3271
|
+
dataType: "custom";
|
|
3272
|
+
columnType: "PgCustomColumn";
|
|
3273
|
+
data: string;
|
|
3274
|
+
driverParam: string;
|
|
3275
|
+
notNull: false;
|
|
3276
|
+
hasDefault: false;
|
|
3277
|
+
isPrimaryKey: false;
|
|
3278
|
+
isAutoincrement: false;
|
|
3279
|
+
hasRuntimeDefault: false;
|
|
3280
|
+
enumValues: undefined;
|
|
3281
|
+
baseColumn: never;
|
|
3282
|
+
identity: undefined;
|
|
3283
|
+
generated: undefined;
|
|
3284
|
+
}, {}, {
|
|
3285
|
+
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
3286
|
+
}>;
|
|
3287
|
+
turnId: import("drizzle-orm/pg-core").PgColumn<{
|
|
3288
|
+
name: "turnId";
|
|
3289
|
+
tableName: "control_signals";
|
|
3290
|
+
dataType: "custom";
|
|
3291
|
+
columnType: "PgCustomColumn";
|
|
3292
|
+
data: string;
|
|
3293
|
+
driverParam: string;
|
|
3294
|
+
notNull: false;
|
|
3295
|
+
hasDefault: false;
|
|
3296
|
+
isPrimaryKey: false;
|
|
3297
|
+
isAutoincrement: false;
|
|
3298
|
+
hasRuntimeDefault: false;
|
|
3299
|
+
enumValues: undefined;
|
|
3300
|
+
baseColumn: never;
|
|
3301
|
+
identity: undefined;
|
|
3302
|
+
generated: undefined;
|
|
3303
|
+
}, {}, {
|
|
3304
|
+
pgColumnBuilderBrand: 'PgCustomColumnBuilderBrand';
|
|
3305
|
+
}>;
|
|
3306
|
+
generation: import("drizzle-orm/pg-core").PgColumn<{
|
|
3307
|
+
name: "generation";
|
|
3308
|
+
tableName: "control_signals";
|
|
3309
|
+
dataType: "number";
|
|
3310
|
+
columnType: "PgInteger";
|
|
3311
|
+
data: number;
|
|
3312
|
+
driverParam: string | number;
|
|
3313
|
+
notNull: false;
|
|
3314
|
+
hasDefault: false;
|
|
3315
|
+
isPrimaryKey: false;
|
|
3316
|
+
isAutoincrement: false;
|
|
3317
|
+
hasRuntimeDefault: false;
|
|
3318
|
+
enumValues: undefined;
|
|
3319
|
+
baseColumn: never;
|
|
3320
|
+
identity: undefined;
|
|
3321
|
+
generated: undefined;
|
|
3322
|
+
}, {}, {}>;
|
|
3323
|
+
createdAt: import("drizzle-orm/pg-core").PgColumn<{
|
|
3324
|
+
name: "createdAt";
|
|
3325
|
+
tableName: "control_signals";
|
|
3326
|
+
dataType: "string";
|
|
3327
|
+
columnType: "PgTimestampString";
|
|
3328
|
+
data: string;
|
|
3329
|
+
driverParam: string;
|
|
3330
|
+
notNull: true;
|
|
3331
|
+
hasDefault: true;
|
|
3332
|
+
isPrimaryKey: false;
|
|
3333
|
+
isAutoincrement: false;
|
|
3334
|
+
hasRuntimeDefault: false;
|
|
3335
|
+
enumValues: undefined;
|
|
3336
|
+
baseColumn: never;
|
|
3337
|
+
identity: undefined;
|
|
3338
|
+
generated: undefined;
|
|
3339
|
+
}, {}, {}>;
|
|
3340
|
+
};
|
|
3341
|
+
dialect: 'pg';
|
|
3342
|
+
}>;
|
|
3481
3343
|
/**
|
|
3482
3344
|
* Each sandbox's lifecycle stream (`nylorun.sandbox-event/1`), numbered from 0 per sandbox id.
|
|
3483
3345
|
* Written only by the record module; not published to the stream relay.
|
|
@@ -3804,7 +3666,6 @@ export type VaultRow = typeof vaults.$inferSelect;
|
|
|
3804
3666
|
export type VaultCredentialRow = typeof vaultCredentials.$inferSelect;
|
|
3805
3667
|
export type VaultAuditRow = Omit<typeof vaultAudit.$inferSelect, "ord">;
|
|
3806
3668
|
export type VaultIdempotencyRow = typeof vaultIdempotency.$inferSelect;
|
|
3807
|
-
export type OAuthPendingRow = typeof oauthPending.$inferSelect;
|
|
3808
3669
|
export type SigningKeyRow = typeof signingKeys.$inferSelect;
|
|
3809
3670
|
export type ModelUsageRow = typeof modelUsage.$inferSelect;
|
|
3810
3671
|
export type ModelBudgetRow = typeof modelBudgets.$inferSelect;
|
|
@@ -129,8 +129,8 @@ export const vaultCredentials = nylorun.table("vault_credentials", {
|
|
|
129
129
|
id: textC().primaryKey(),
|
|
130
130
|
vaultId: text().notNull(),
|
|
131
131
|
name: text().notNull(),
|
|
132
|
-
type: text({ enum: ["bearer", "
|
|
133
|
-
/** JSON text of the non-secret binding (
|
|
132
|
+
type: text({ enum: ["bearer", "headers", "model"] }).notNull(),
|
|
133
|
+
/** JSON text of the non-secret binding: url (and via, identity, header names), or provider and model. */
|
|
134
134
|
bindingJson: text().notNull(),
|
|
135
135
|
expiresAt: text(),
|
|
136
136
|
createdAt: textC().notNull(),
|
|
@@ -165,40 +165,6 @@ export const vaultIdempotency = nylorun.table("vault_idempotency", {
|
|
|
165
165
|
/** JSON text of the original response. */
|
|
166
166
|
response: text().notNull(),
|
|
167
167
|
});
|
|
168
|
-
/**
|
|
169
|
-
* An MCP OAuth connect between its start and its callback (F9 C2): found by the SHA-256 of its
|
|
170
|
-
* `state`, used once, for ten minutes. The PKCE verifier and any client secret are sealed under
|
|
171
|
-
* the vault key (`sealBytes`), which only the keys module holds.
|
|
172
|
-
*/
|
|
173
|
-
export const oauthPending = nylorun.table("oauth_pending", {
|
|
174
|
-
stateHash: text().primaryKey(),
|
|
175
|
-
vaultId: text().notNull(),
|
|
176
|
-
/** The MCP server's name in the agent, the credential's name. */
|
|
177
|
-
server: text().notNull(),
|
|
178
|
-
/** The MCP server's URL (normalized): the credential's binding. */
|
|
179
|
-
url: text().notNull(),
|
|
180
|
-
tokenEndpoint: text().notNull(),
|
|
181
|
-
clientId: text().notNull(),
|
|
182
|
-
/** How the client authenticates at the token endpoint: `none`, `client_secret_basic` or `client_secret_post`. */
|
|
183
|
-
tokenEndpointAuth: text({ enum: ["none", "client_secret_basic", "client_secret_post"] }).notNull(),
|
|
184
|
-
/** The RFC 8707 resource indicator sent with the authorization request, if any. */
|
|
185
|
-
resource: text(),
|
|
186
|
-
kekId: text().notNull(),
|
|
187
|
-
/** Sealed; null for a public client. */
|
|
188
|
-
clientSecret: bytes(),
|
|
189
|
-
/** Sealed. */
|
|
190
|
-
codeVerifier: bytes().notNull(),
|
|
191
|
-
redirectUri: text().notNull(),
|
|
192
|
-
expiresAt: textC().notNull(),
|
|
193
|
-
createdAt: textC().notNull(),
|
|
194
|
-
}, (t) => [
|
|
195
|
-
foreignKey({
|
|
196
|
-
name: "oauth_pending_vault_id_fkey",
|
|
197
|
-
columns: [t.vaultId],
|
|
198
|
-
foreignColumns: [vaults.id],
|
|
199
|
-
}).onDelete("cascade"),
|
|
200
|
-
index("oauth_pending_expires").on(t.expiresAt),
|
|
201
|
-
]);
|
|
202
168
|
export const tenantSettings = nylorun.table("tenant_settings", {
|
|
203
169
|
key: text().primaryKey(),
|
|
204
170
|
value: text().notNull(),
|
|
@@ -435,6 +401,26 @@ export const definitionFileUses = nylorun.table("definition_file_uses", {
|
|
|
435
401
|
primaryKey({ name: "definition_file_uses_pkey", columns: [t.agentId, t.manifestHash, t.sha256] }),
|
|
436
402
|
index("definition_file_uses_sha256").on(t.sha256),
|
|
437
403
|
]);
|
|
404
|
+
/**
|
|
405
|
+
* The control bus (D21, D48): signals between the processes that have the Tenant open,
|
|
406
|
+
* written in the transaction that commits what they announce and notified on
|
|
407
|
+
* `nylorun_control` at commit (`control.ts`). A row outlives its notification so a process
|
|
408
|
+
* whose listener was down catches up; the Tenant sweep deletes old ones. `created_at` is the
|
|
409
|
+
* insert's own clock (`clock_timestamp()`), not its transaction's start.
|
|
410
|
+
*/
|
|
411
|
+
export const controlSignals = nylorun.table("control_signals", {
|
|
412
|
+
id: bigint({ mode: "number" }).primaryKey().generatedAlwaysAsIdentity(),
|
|
413
|
+
kind: text().notNull(),
|
|
414
|
+
sessionId: textC(),
|
|
415
|
+
turnId: textC(),
|
|
416
|
+
generation: integer(),
|
|
417
|
+
createdAt: timestamp({ withTimezone: true, mode: "string" })
|
|
418
|
+
.notNull()
|
|
419
|
+
.default(sql `clock_timestamp()`),
|
|
420
|
+
}, (t) => [
|
|
421
|
+
index("control_signals_created_at").on(t.createdAt),
|
|
422
|
+
check("control_signals_kind_check", sql `${t.kind} IN ('session.cancel', 'sessions.reset')`),
|
|
423
|
+
]);
|
|
438
424
|
// ---------------------------------------------------------------------------
|
|
439
425
|
// nylorun_streams: the record
|
|
440
426
|
/**
|
|
@@ -52,11 +52,12 @@ import { AsyncLocalStorage } from "node:async_hooks";
|
|
|
52
52
|
import { and, count, eq, getTableColumns, gte, inArray, isNotNull, isNull, lt, lte, ne, or, sql, } from "drizzle-orm";
|
|
53
53
|
import { appendEvent, appendSandboxEvent } from "../../record/index.js";
|
|
54
54
|
import { OwnershipLostError, PrincipalRoleConflict } from "../ownership.js";
|
|
55
|
+
import { followControlSignals, pruneSignals, writeSignal } from "./control.js";
|
|
55
56
|
import { database, driverError } from "./db.js";
|
|
56
57
|
import { expectedSchemaVersion, readSchemaVersion } from "./migrate.js";
|
|
57
58
|
import { createPostgresRecordReader } from "./record.js";
|
|
58
59
|
import { postgresRecordWriter, postgresSandboxRecordWriter } from "./record-writer.js";
|
|
59
|
-
import { artifacts, artifactVersions, artifactContent, definitionFiles, definitionFileUses, commands, definitions, effects, links, modelBudgets, modelUsage, principals, sandboxes, sandboxEvents, sandboxResources, sessionEvents, sessionLogHeads, sessions, toJson, toolCrossings, signingKeys, tenant, tenantSettings, vaultAudit, vaultCredentials, vaultIdempotency, vaults,
|
|
60
|
+
import { artifacts, artifactVersions, artifactContent, definitionFiles, definitionFileUses, commands, definitions, effects, links, modelBudgets, modelUsage, principals, sandboxes, sandboxEvents, sandboxResources, sessionEvents, sessionLogHeads, sessions, toJson, toolCrossings, signingKeys, tenant, tenantSettings, vaultAudit, vaultCredentials, vaultIdempotency, vaults, } from "./schema.js";
|
|
60
61
|
export function createPostgresSessionStore(options) {
|
|
61
62
|
return new PostgresSessionStore(options);
|
|
62
63
|
}
|
|
@@ -175,6 +176,11 @@ class PostgresSessionStore {
|
|
|
175
176
|
return { ok: false, schemaVersion: 0, expectedSchemaVersion };
|
|
176
177
|
}
|
|
177
178
|
}
|
|
179
|
+
followSignals(onSignal, options) {
|
|
180
|
+
if (this.closed)
|
|
181
|
+
throw new Error("SessionStore is closed");
|
|
182
|
+
return followControlSignals(this.sql, this.db, onSignal, options);
|
|
183
|
+
}
|
|
178
184
|
/** Rejects new transactions and waits for running ones. Does not end the pool. */
|
|
179
185
|
async close() {
|
|
180
186
|
this.closed = true;
|
|
@@ -583,6 +589,15 @@ class PostgresTx {
|
|
|
583
589
|
definitions: row.definitions,
|
|
584
590
|
};
|
|
585
591
|
}
|
|
592
|
+
// --- control bus (D21) ---------------------------------------------------
|
|
593
|
+
async signal(signal) {
|
|
594
|
+
this.check();
|
|
595
|
+
await writeSignal(this.db, signal);
|
|
596
|
+
}
|
|
597
|
+
async pruneSignals(before) {
|
|
598
|
+
this.check();
|
|
599
|
+
return pruneSignals(this.db, before);
|
|
600
|
+
}
|
|
586
601
|
// --- basin generations --------------------------------------------------
|
|
587
602
|
async basinGenerations() {
|
|
588
603
|
this.check();
|
|
@@ -750,23 +765,6 @@ class PostgresTx {
|
|
|
750
765
|
this.check();
|
|
751
766
|
await this.db.insert(vaultIdempotency).values(row);
|
|
752
767
|
}
|
|
753
|
-
async insertOAuthPending(row) {
|
|
754
|
-
this.check();
|
|
755
|
-
await this.db.insert(oauthPending).values(row);
|
|
756
|
-
}
|
|
757
|
-
async takeOAuthPending(stateHash) {
|
|
758
|
-
this.check();
|
|
759
|
-
const [row] = await this.db
|
|
760
|
-
.delete(oauthPending)
|
|
761
|
-
.where(eq(oauthPending.stateHash, stateHash))
|
|
762
|
-
.returning();
|
|
763
|
-
return row;
|
|
764
|
-
}
|
|
765
|
-
async deleteExpiredOAuthPending(now) {
|
|
766
|
-
this.check();
|
|
767
|
-
const result = await this.db.delete(oauthPending).where(lt(oauthPending.expiresAt, now));
|
|
768
|
-
return result.count;
|
|
769
|
-
}
|
|
770
768
|
// --- signing keys --------------------------------------------------------
|
|
771
769
|
async lockSigningKeys() {
|
|
772
770
|
this.check();
|
|
@@ -11,6 +11,8 @@
|
|
|
11
11
|
* tables of a pre-release build of it. It is never touched: this release starts fresh.
|
|
12
12
|
* 2. Apply the missing migrations (`migrate.ts`). A database with migrations this Runtime
|
|
13
13
|
* does not know is `schema-too-new`; a migration Postgres rejects is `migration-failed`.
|
|
14
|
+
* `0016_mcp_oauth_removed` deletes the vault's MCP OAuth credentials (protocol 10), each
|
|
15
|
+
* with an audit row; the open returns them (`removedCredentials`) for a boot warning.
|
|
14
16
|
* 3. When `nylorun.tenant` is empty, create the Tenant: its row (id, name, created time) and
|
|
15
17
|
* its first principals. A database whose row is gone but that holds a Tenant's data
|
|
16
18
|
* (principals, sessions, agents, vaults, keys) is `envelope-invalid`, never given a new
|
|
@@ -74,6 +76,18 @@ export interface OpenedTenantDatabase {
|
|
|
74
76
|
from: number;
|
|
75
77
|
to: number;
|
|
76
78
|
};
|
|
79
|
+
/**
|
|
80
|
+
* The MCP OAuth credentials this call's migration `0016_mcp_oauth_removed` deleted (protocol
|
|
81
|
+
* 10), from the audit rows it wrote: the Host names each in a boot warning. Empty otherwise.
|
|
82
|
+
*/
|
|
83
|
+
removedCredentials: RemovedCredential[];
|
|
84
|
+
}
|
|
85
|
+
/** A vault credential a migration deleted. */
|
|
86
|
+
export interface RemovedCredential {
|
|
87
|
+
vaultId: string;
|
|
88
|
+
credentialId: string;
|
|
89
|
+
/** The URL it was bound to. */
|
|
90
|
+
url: string | null;
|
|
77
91
|
}
|
|
78
92
|
/**
|
|
79
93
|
* Migrates the database, creates its Tenant when it has none, and opens its Session Store.
|
|
@@ -4,8 +4,10 @@ import { TenantEnvelopeSchema, } from "@nylorun/core/contracts";
|
|
|
4
4
|
import { openError, TenantOpenError } from "../../tenant/cause.js";
|
|
5
5
|
import { database, driverError } from "./db.js";
|
|
6
6
|
import { applyMigrations, assertCurrentLayout, isStatementError, lockMigrations, shippedMigrations, } from "./migrate.js";
|
|
7
|
-
import { definitions, principals, sessions, signingKeys, TENANT_SCHEMA, tenant, vaults, } from "./schema.js";
|
|
7
|
+
import { definitions, principals, sessions, signingKeys, TENANT_SCHEMA, tenant, vaultAudit, vaults, } from "./schema.js";
|
|
8
8
|
import { createPostgresSessionStore } from "./store.js";
|
|
9
|
+
/** The migration that deletes the vault's `oauth` credentials, each with an audit row. */
|
|
10
|
+
const OAUTH_REMOVED_MIGRATION = "0016_mcp_oauth_removed";
|
|
9
11
|
/**
|
|
10
12
|
* Migrates the database, creates its Tenant when it has none, and opens its Session Store.
|
|
11
13
|
* Throws a `TenantOpenError` with the cause when the Tenant cannot be opened (see above).
|
|
@@ -22,7 +24,8 @@ export async function openTenantDatabase(options) {
|
|
|
22
24
|
await assertCurrentLayout(tx);
|
|
23
25
|
const migrated = await applyMigrations(tx, migrations);
|
|
24
26
|
const created = await ensureTenant(tx, options.create, migrated, now);
|
|
25
|
-
|
|
27
|
+
const removedCredentials = await removedBy(tx, migrations, migrated);
|
|
28
|
+
return { created, migrated, removedCredentials };
|
|
26
29
|
});
|
|
27
30
|
}
|
|
28
31
|
catch (thrown) {
|
|
@@ -82,6 +85,23 @@ export async function readTenantEnvelope(q) {
|
|
|
82
85
|
throw driverError(error);
|
|
83
86
|
}
|
|
84
87
|
}
|
|
88
|
+
/**
|
|
89
|
+
* The credentials `0016_mcp_oauth_removed` deleted, when this transaction applied it: its
|
|
90
|
+
* audit rows (actor `migration`). Empty when it ran before, or is not among `migrations`.
|
|
91
|
+
*/
|
|
92
|
+
async function removedBy(tx, migrations, migrated) {
|
|
93
|
+
const index = migrations.findIndex((migration) => migration.tag === OAUTH_REMOVED_MIGRATION);
|
|
94
|
+
if (index < migrated.from || index >= migrated.to)
|
|
95
|
+
return [];
|
|
96
|
+
const rows = await tx
|
|
97
|
+
.select({ vaultId: vaultAudit.vaultId, credentialId: vaultAudit.credentialId, url: vaultAudit.target })
|
|
98
|
+
.from(vaultAudit)
|
|
99
|
+
.where(and(eq(vaultAudit.actor, "migration"), eq(vaultAudit.action, "delete")))
|
|
100
|
+
.orderBy(vaultAudit.ord);
|
|
101
|
+
return rows.flatMap((row) => row.vaultId && row.credentialId
|
|
102
|
+
? [{ vaultId: row.vaultId, credentialId: row.credentialId, url: row.url }]
|
|
103
|
+
: []);
|
|
104
|
+
}
|
|
85
105
|
/**
|
|
86
106
|
* Creates the Tenant when there is none, and adds the principals it is missing. Records the
|
|
87
107
|
* schema version on the Tenant row when this transaction migrated.
|