@substrat-run/control-plane-api 0.112.0 → 0.114.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.
- package/dist/api.d.ts.map +1 -1
- package/dist/api.js +67 -1
- package/dist/api.js.map +1 -1
- package/dist/cf-observability.d.ts.map +1 -1
- package/dist/cf-observability.js +32 -7
- package/dist/cf-observability.js.map +1 -1
- package/dist/pipelines-sink.d.ts.map +1 -1
- package/dist/pipelines-sink.js +61 -3
- package/dist/pipelines-sink.js.map +1 -1
- package/dist/vertical-client.d.ts +10 -1
- package/dist/vertical-client.d.ts.map +1 -1
- package/dist/vertical-client.js +24 -0
- package/dist/vertical-client.js.map +1 -1
- package/package.json +5 -5
package/dist/api.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AAE5B,OAAO,
|
|
1
|
+
{"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"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"}
|
package/dist/api.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Hono } from 'hono';
|
|
2
|
-
import { parseHostname, withLabel, RESERVED_LABEL_SEPARATOR, adminAction, ASSET_PART_PREFIX, assetHash, channelName, connectionActivity, connectionActivitySource, connectionCredential, connectionFilter, connectionProbe, createTenantInput, entitlementGrantInput, hostname as hostnameSchema, hostnameRegion, hostnameStatus, identityLink, errorCode, issueStatus, issueStatusInput, listPageQuery, matchesOutboundHost, pageOf, platformRequestFilter, principalId as principalIdSchema, promotionAcknowledgement, provisionableJurisdiction, publishVersionInput, queryScopeInput, readScopeTableInput, entityHistoryInput, eventFacetInput, eventCauseInput, eventEffectsInput, delegatedReadParams, createOrgInput, roleKey as roleKeySchema, DEFAULT_DENIAL_LIMIT, DENIAL_LIMIT_MAX, denialGroupBy, registerVerticalInput, serviceDimensions, sweepRunKind, sweepRunOutcome, scopeDump, dataSubjectId as dataSubjectIdSchema, scopeId as scopeIdSchema, scopeStatus, storageShape, surfaceName, tenantId as tenantIdSchema, tenantStatus, versionOrigin, z, PROBLEM_CONTENT_TYPE, toProblem, } from '@substrat-run/contracts';
|
|
2
|
+
import { parseHostname, withLabel, RESERVED_LABEL_SEPARATOR, adminAction, ASSET_PART_PREFIX, assetHash, channelName, connectionActivity, connectionActivitySource, connectionCredential, connectionFilter, connectionProbe, createTenantInput, entitlementGrantInput, hostname as hostnameSchema, hostnameRegion, hostnameStatus, identityLink, errorCode, issueStatus, issueStatusInput, listPageQuery, matchesOutboundHost, pageOf, platformRequestFilter, principalId as principalIdSchema, promotionAcknowledgement, provisionableJurisdiction, publishVersionInput, queryScopeInput, readScopeTableInput, entityHistoryInput, eventFacetInput, eventCauseInput, eventEffectsInput, invocationEventsInput, deadLettersInput, delegatedReadParams, createOrgInput, roleKey as roleKeySchema, DEFAULT_DENIAL_LIMIT, DENIAL_LIMIT_MAX, denialGroupBy, registerVerticalInput, serviceDimensions, sweepRunKind, sweepRunOutcome, scopeDump, dataSubjectId as dataSubjectIdSchema, scopeId as scopeIdSchema, scopeStatus, storageShape, surfaceName, tenantId as tenantIdSchema, tenantStatus, versionOrigin, z, PROBLEM_CONTENT_TYPE, toProblem, redrainEventsInput, REDRAIN_BATCH, } from '@substrat-run/contracts';
|
|
3
3
|
import { attributeFailure } from './failure-attribution.js';
|
|
4
4
|
import { migrationProgress, ulid } from '@substrat-run/kernel';
|
|
5
5
|
import { TENANT_HEADER } from './auth.js';
|
|
@@ -1643,6 +1643,40 @@ export function createControlPlaneApi(options) {
|
|
|
1643
1643
|
colocated: () => admin.eventEffects(c.get('actor'), tenantId, scopeId, input),
|
|
1644
1644
|
}, (r) => r.count));
|
|
1645
1645
|
});
|
|
1646
|
+
// #1237: everything one call emitted — the siblings neither walk reaches. Delegated
|
|
1647
|
+
// like the two walks, and logged against the call id rather than its page size.
|
|
1648
|
+
app.get('/tenants/:tenantId/scopes/:scopeId/invocation', async (c) => {
|
|
1649
|
+
const tenantId = tenantIdSchema.parse(c.req.param('tenantId'));
|
|
1650
|
+
const scopeId = scopeIdSchema.parse(c.req.param('scopeId'));
|
|
1651
|
+
const input = invocationEventsInput.parse({
|
|
1652
|
+
invocationId: c.req.query('invocationId'),
|
|
1653
|
+
limit: c.req.query('limit') ? Number(c.req.query('limit')) : undefined,
|
|
1654
|
+
});
|
|
1655
|
+
const scope = await admin.getScopeRecord(c.get('actor'), tenantId, scopeId);
|
|
1656
|
+
if (!scope)
|
|
1657
|
+
return c.json({ error: `unknown scope for tenant: (${tenantId}, ${scopeId})` }, 404);
|
|
1658
|
+
return c.json(await delegatedRead(c, tenantId, scopeId, scope, 'invocationEvents', input, {
|
|
1659
|
+
viaVertical: (v) => v.invocationEvents(scopeId, input),
|
|
1660
|
+
colocated: () => admin.invocationEvents(c.get('actor'), tenantId, scopeId, input),
|
|
1661
|
+
}, (r) => r.events.length));
|
|
1662
|
+
});
|
|
1663
|
+
// #1525: every delivery in the scope that gave up — the list the walks can only reach
|
|
1664
|
+
// one event at a time. Delegated like them; the row names no subject, so it logs none.
|
|
1665
|
+
app.get('/tenants/:tenantId/scopes/:scopeId/dead-letters', async (c) => {
|
|
1666
|
+
const tenantId = tenantIdSchema.parse(c.req.param('tenantId'));
|
|
1667
|
+
const scopeId = scopeIdSchema.parse(c.req.param('scopeId'));
|
|
1668
|
+
const input = deadLettersInput.parse({
|
|
1669
|
+
limit: c.req.query('limit') ? Number(c.req.query('limit')) : undefined,
|
|
1670
|
+
cursor: c.req.query('cursor') ?? undefined,
|
|
1671
|
+
});
|
|
1672
|
+
const scope = await admin.getScopeRecord(c.get('actor'), tenantId, scopeId);
|
|
1673
|
+
if (!scope)
|
|
1674
|
+
return c.json({ error: `unknown scope for tenant: (${tenantId}, ${scopeId})` }, 404);
|
|
1675
|
+
return c.json(await delegatedRead(c, tenantId, scopeId, scope, 'deadLetters', input, {
|
|
1676
|
+
viaVertical: (v) => v.deadLetters(scopeId, input),
|
|
1677
|
+
colocated: () => admin.deadLetters(c.get('actor'), tenantId, scopeId, input),
|
|
1678
|
+
}, (r) => r.entries.length));
|
|
1679
|
+
});
|
|
1646
1680
|
// #1235: one record's event history — the per-entity pivot of the audit spine.
|
|
1647
1681
|
// Delegated exactly like the table reads: through the vertical that holds the
|
|
1648
1682
|
// scope's data when one resolves, the co-located host otherwise.
|
|
@@ -2168,6 +2202,38 @@ export function createControlPlaneApi(options) {
|
|
|
2168
2202
|
// vertical must never be asked to wipe a live scope) and re-checked below the seam by
|
|
2169
2203
|
// reapScope. Same storage-before-row ordering as deleteSnapshot: the vertical wipes its
|
|
2170
2204
|
// co-located DO first, then the in-process reapScope flips the status and audits.
|
|
2205
|
+
// #1334 — reopen one scope's drained events so the Tier-2 drain ships them again: the
|
|
2206
|
+
// rebuild path for a lake table that was dropped (a Pipelines stream cannot change its
|
|
2207
|
+
// schema in place, so a new column means a new table, and every stamped row would
|
|
2208
|
+
// otherwise be history the drain never offers again). Staff/service only — deliberately
|
|
2209
|
+
// absent from BUILDER_ROUTES: it re-exports a tenant's payloads, and nothing a builder
|
|
2210
|
+
// does should be able to cause that. `scripts/lake-redrain.mjs` walks the fleet with it.
|
|
2211
|
+
app.post('/tenants/:tenantId/scopes/:scopeId/redrain-events', async (c) => {
|
|
2212
|
+
const tenantId = tenantIdSchema.parse(c.req.param('tenantId'));
|
|
2213
|
+
const scopeId = scopeIdSchema.parse(c.req.param('scopeId'));
|
|
2214
|
+
const actor = c.get('actor');
|
|
2215
|
+
const parsed = redrainEventsInput.safeParse(await c.req.json().catch(() => ({})));
|
|
2216
|
+
if (!parsed.success) {
|
|
2217
|
+
return c.json({ error: 'body must be { drainedBefore: <ISO 8601 instant> } — the end of the window to reopen' }, 400);
|
|
2218
|
+
}
|
|
2219
|
+
// Refused at the door rather than left to the adapters: an instant in the future
|
|
2220
|
+
// reopens rows the drain shipped AFTER the rebuild, which is exactly the double-write
|
|
2221
|
+
// the required instant exists to prevent. Host code, so it may read the real clock.
|
|
2222
|
+
if (Date.parse(parsed.data.drainedBefore) > Date.now()) {
|
|
2223
|
+
return c.json({
|
|
2224
|
+
error: `drainedBefore ${parsed.data.drainedBefore} is in the future — it would reopen rows ` +
|
|
2225
|
+
'already shipped to the rebuilt table. Pass the instant the old table stopped receiving.',
|
|
2226
|
+
}, 400);
|
|
2227
|
+
}
|
|
2228
|
+
const scope = await admin.getScopeRecord(actor, tenantId, scopeId);
|
|
2229
|
+
if (!scope)
|
|
2230
|
+
return c.json({ error: `unknown scope for tenant: (${tenantId}, ${scopeId})` }, 404);
|
|
2231
|
+
const redrained = await admin.redrainEvents(actor, tenantId, scopeId, parsed.data);
|
|
2232
|
+
// `more` rather than silence: the verb reopens a bounded batch, so a caller that posts
|
|
2233
|
+
// once can be holding a partial reopen. Saying so is what stops it reading as a finished
|
|
2234
|
+
// window — the operator (or `pnpm lake:redrain`) posts again until `redrained` is 0.
|
|
2235
|
+
return c.json({ redrained, more: redrained >= REDRAIN_BATCH, drainedBefore: parsed.data.drainedBefore });
|
|
2236
|
+
});
|
|
2171
2237
|
app.post('/tenants/:tenantId/scopes/:scopeId/reap', async (c) => {
|
|
2172
2238
|
const tenantId = tenantIdSchema.parse(c.req.param('tenantId'));
|
|
2173
2239
|
const scopeId = scopeIdSchema.parse(c.req.param('scopeId'));
|