@camstack/types 1.2.107 → 1.2.109

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/addon.js CHANGED
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  const require_event_category = require("./event-category-EY0GNjV9.js");
3
- const require_sleep = require("./sleep-CUuoW-kk.js");
3
+ const require_sleep = require("./sleep-BJTBu5cu.js");
4
4
  const require_err_msg = require("./err-msg-COpsHMw2.js");
5
5
  //#region src/generated/cap-input-defaults.ts
6
6
  /**
package/dist/addon.mjs CHANGED
@@ -1,5 +1,5 @@
1
1
  import { t as EventCategory } from "./event-category-CIa_iT6b.mjs";
2
- import { B as ReadinessRegistry, E as adminUiCapability, L as nodePin, R as readNodePin, St as emitReadiness, T as DeviceType, V as ReadinessTimeoutError, W as scopeKey, _t as DisposerChain, a as asJsonObject, b as deviceOpsCapability, d as BOOT_RECOVERY_BACKOFF_MS, f as DEVICE_SCOPED_CAPS, gt as DATAPLANE_SECRET_HEADER, h as createEventBusSliceSource, j as expandCapMethods, m as createDeviceProxy, p as isDeviceScopedCap, s as asString, t as sleep, u as parseJsonUnknown, vt as BaseAddon, x as viewerUiCapability, yt as normalizeAddonInitResult } from "./sleep-BLxqGLY0.mjs";
2
+ import { B as ReadinessRegistry, E as adminUiCapability, L as nodePin, R as readNodePin, St as emitReadiness, T as DeviceType, V as ReadinessTimeoutError, W as scopeKey, _t as DisposerChain, a as asJsonObject, b as deviceOpsCapability, d as BOOT_RECOVERY_BACKOFF_MS, f as DEVICE_SCOPED_CAPS, gt as DATAPLANE_SECRET_HEADER, h as createEventBusSliceSource, j as expandCapMethods, m as createDeviceProxy, p as isDeviceScopedCap, s as asString, t as sleep, u as parseJsonUnknown, vt as BaseAddon, x as viewerUiCapability, yt as normalizeAddonInitResult } from "./sleep-Dj1DG9Od.mjs";
3
3
  import { t as errMsg } from "./err-msg-IQTHeDzc.mjs";
4
4
  //#region src/generated/cap-input-defaults.ts
5
5
  /**
@@ -28,6 +28,16 @@ export declare const addonPagesSourceCapability: {
28
28
  readonly mode: "collection";
29
29
  readonly internal: true;
30
30
  readonly methods: {
31
+ /**
32
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
33
+ * `data-store-provider`) — this was reachable on the AppRouter by ANY
34
+ * authenticated session at the default `auth: 'protected'`. The only
35
+ * consumer, the `addon-pages-aggregator` builtin, reads it via
36
+ * `ctx.capabilities.getCollection('addon-pages-source')` — LOCAL-PROCESS
37
+ * only, never tRPC (per `ctx.capabilities` seeing only the local
38
+ * process). The public, enriched listing admin-ui actually consumes is
39
+ * the separate `addon-pages` cap, unaffected by this change.
40
+ */
31
41
  readonly listPages: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodReadonly<z.ZodArray<z.ZodObject<{
32
42
  id: z.ZodString;
33
43
  label: z.ZodString;
@@ -122,6 +122,18 @@ export declare const addonWidgetsSourceCapability: {
122
122
  readonly mode: "collection";
123
123
  readonly internal: true;
124
124
  readonly methods: {
125
+ /**
126
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
127
+ * `data-store-provider`) — this was reachable on the AppRouter by ANY
128
+ * authenticated session at the default `auth: 'protected'`. The only
129
+ * consumer, the `addon-widgets-aggregator` builtin, reads it via
130
+ * `ctx.capabilities.getCollection('addon-widgets-source')` — LOCAL-PROCESS
131
+ * only, never tRPC. The public, enriched listing admin-ui actually
132
+ * consumes is the separate `addon-widgets` cap (`listWidgets` there is
133
+ * gated separately, and a `preAuth: true` widget is surfaced through the
134
+ * PUBLIC `auth.listLoginMethods` contribution channel instead) —
135
+ * neither is affected by this change.
136
+ */
125
137
  readonly listWidgets: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodReadonly<z.ZodArray<z.ZodObject<{
126
138
  tab: z.ZodString;
127
139
  subTab: z.ZodOptional<z.ZodString>;
@@ -6,6 +6,15 @@ export declare const adminUiCapability: {
6
6
  readonly mode: "singleton";
7
7
  readonly internal: true;
8
8
  readonly methods: {
9
+ /**
10
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
11
+ * `data-store-provider`) — both methods were reachable on the AppRouter
12
+ * by ANY authenticated session at the default `auth: 'protected'`, and
13
+ * `getStaticDir` leaks a hub filesystem path. The only caller is
14
+ * `main.ts`'s static-file bootstrap, via `capRegistry.getSingletonForNode`
15
+ * — never tRPC — so `auth: 'admin'` costs it nothing. The actual admin-ui
16
+ * SPA assets are served as plain static files, unaffected by this gate.
17
+ */
9
18
  readonly getStaticDir: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodObject<{
10
19
  staticDir: z.ZodString;
11
20
  }, z.core.$strip>, import("./capability-definition.js").CapabilityMethodKind>;
@@ -10,7 +10,7 @@
10
10
  * makes the two paths provably agree. Each predicate accepts both Zod 4
11
11
  * (`_def.type`) and legacy Zod 3 (`_def.typeName` / `constructor.name`) shapes.
12
12
  */
13
- import type { CapabilityDefinition } from './capability-definition.js';
13
+ import type { CapabilityDefinition, CapabilityMethodAuth } from './capability-definition.js';
14
14
  /** `z.void()` — input carries no data. */
15
15
  export declare function isVoidInput(schema: unknown): boolean;
16
16
  /** `z.object()` — supports `.loose()` for out-of-band `nodeId`/`addonId` keys. */
@@ -86,6 +86,43 @@ export declare function extractNestedAddonId(input: unknown): string | undefined
86
86
  * for non-object schemas.
87
87
  */
88
88
  export declare function objectInputDeclaresAddonId(schema: unknown): boolean;
89
+ /**
90
+ * Effective auth for a cap method — the `internal: true` floor (Task 7.5c).
91
+ *
92
+ * `internal: true` on a cap def is a DECLARATION that its methods are for
93
+ * in-process (`ctx.api`) consumption only. Nothing enforced that:
94
+ * `resolveCapMount` never reads `internal` (an internal cap still gets a
95
+ * full tRPC router), and a method that omitted an explicit `auth` used to
96
+ * default — permanently, at `method()`-call time — to `'protected'`,
97
+ * reachable by any authenticated session regardless of `internal`. That
98
+ * silent default is how 45 procedures across 13 internal caps ended up
99
+ * exposed, including `ssoBridge.signBridgeToken`: it accepted
100
+ * caller-supplied claims (including `isAdmin`), was reachable by any
101
+ * authenticated session, and its token is redeemed at
102
+ * `/api/auth/sso/finish` to mint a session — a full privilege escalation.
103
+ * See `docs/decisions/adr-0240-an-internal-cap-floors-its-unannotated-methods-to-admin.md`
104
+ * (D240) for the record.
105
+ *
106
+ * The floor, exactly: an `internal` cap's method with NO explicit `auth`
107
+ * resolves to `'admin'` instead of `'protected'`. A method that DELIBERATELY
108
+ * declares an explicit `auth` — public, protected, or admin — keeps it
109
+ * unconditionally; the author already said what they meant, and an
110
+ * annotation that happens to agree with the floor is documentation, not
111
+ * redundancy. A non-`internal` cap's un-annotated method is unaffected
112
+ * (still `'protected'`). This is a FLOOR, not a hard `mount: 'skip'` — that
113
+ * would also override a deliberate `auth: 'public'`/`'protected'` choice,
114
+ * which is not the defect being closed.
115
+ *
116
+ * `method()` (`capability-definition.ts`) deliberately leaves `auth`
117
+ * UNSET when the caller omits it (rather than defaulting there) so the
118
+ * "was this explicit" bit survives to this single resolution point. Single
119
+ * source of truth shared by the runtime builder (`cap-router-builder.ts`)
120
+ * and the codegen (`generate-cap-routers.ts`, `gen-api-reference.ts`) — the
121
+ * two must never disagree, a documented failure mode in this repo.
122
+ */
123
+ export declare function resolveMethodAuth(def: Pick<CapabilityDefinition, 'internal'>, method: {
124
+ readonly auth?: CapabilityMethodAuth;
125
+ }): CapabilityMethodAuth;
89
126
  /** Auth level → base-procedure key. `superAdmin` collapses to `admin`. */
90
127
  export declare function procedureAuthKey(auth: string): 'public' | 'protected' | 'admin';
91
128
  /** kebab-case cap name → camelCase router-map key. */
@@ -80,8 +80,21 @@ export interface CapabilityMethodSchema<TInput extends z.ZodType = z.ZodType, TO
80
80
  readonly output: TOutput;
81
81
  /** tRPC procedure kind. Default: 'query'. */
82
82
  readonly kind: TKind;
83
- /** Auth level. Default: 'protected'. */
84
- readonly auth: CapabilityMethodAuth;
83
+ /**
84
+ * Auth level. OPTIONAL and left unset by `method()` when the caller
85
+ * doesn't pass one — the DEFAULT is resolved later, per-cap, by
86
+ * {@link resolveMethodAuth} (`cap-router-predicates.ts`), never baked in
87
+ * here. That deferral is load-bearing: `resolveMethodAuth` floors an
88
+ * un-set `auth` to `'admin'` on an `internal: true` cap and to
89
+ * `'protected'` otherwise (Task 7.5c). Baking a `'protected'` default in
90
+ * at THIS layer would erase the "did the author actually decide this"
91
+ * bit before it ever reached that floor — which is exactly how 45
92
+ * procedures across 13 internal caps (including
93
+ * `ssoBridge.signBridgeToken`, a caller-suppliable-`isAdmin` privilege
94
+ * escalation) ended up reachable by any authenticated session. An
95
+ * EXPLICIT `auth` here — of any value — always wins over the floor.
96
+ */
97
+ readonly auth?: CapabilityMethodAuth;
85
98
  /** Per-method access flavour. When unset, codegen derives it from `kind` + name heuristic. */
86
99
  readonly access?: CapabilityMethodAccess;
87
100
  /** Moleculer action timeout override (ms). Overrides broker global requestTimeout for this action only. */
@@ -161,6 +161,15 @@ export declare const customModelRegistryCapability: {
161
161
  readonly mode: "collection";
162
162
  readonly internal: true;
163
163
  readonly methods: {
164
+ /**
165
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
166
+ * `data-store-provider`) — this was reachable on the AppRouter by ANY
167
+ * authenticated session at the default `auth: 'protected'`. The only
168
+ * consumer, the detection-pipeline's model resolution
169
+ * (`addon-pipeline/src/detection-pipeline/provider.ts`), calls
170
+ * `ctx.api.customModelRegistry.listModels.query()` — UDS/Moleculer,
171
+ * never tRPC — so `auth: 'admin'` costs it nothing.
172
+ */
164
173
  readonly listModels: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodReadonly<z.ZodArray<z.ZodObject<{
165
174
  stepId: z.ZodString;
166
175
  entry: z.ZodObject<{
@@ -22,6 +22,13 @@ export declare const embeddingEncoderCapability: {
22
22
  readonly mode: "collection";
23
23
  readonly internal: true;
24
24
  readonly methods: {
25
+ /**
26
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
27
+ * `data-store-provider`) — every method below was reachable on the
28
+ * AppRouter by ANY authenticated session at the default
29
+ * `auth: 'protected'`. Consumers reach the encoder via `ctx.api` from
30
+ * `addon-post-analysis`, never tRPC.
31
+ */
25
32
  readonly encode: import("./capability-definition.js").CapabilityMethodSchema<z.ZodObject<{
26
33
  crop: z.ZodCustom<Uint8Array<ArrayBuffer>, Uint8Array<ArrayBuffer>>;
27
34
  width: z.ZodNumber;
@@ -35,7 +35,7 @@ export { ArchiveEntrySchema, ArchiveManifestSchema, BackupDestinationInfoSchema,
35
35
  export { BrokerAddInputSchema, BrokerGetStateInputSchema, type BrokerInfo as UnifiedBrokerInfo, BrokerInfoSchema as UnifiedBrokerInfoSchema, type BrokerProviderInfo, BrokerProviderInfoSchema, BrokerPublishInputSchema, BrokerRegistryStatusSchema, type BrokerStatus as UnifiedBrokerStatus, BrokerStatusEnum, BrokerSubscribeInputSchema, BrokerSubscribeResultSchema, BrokerTestConnectionResultSchema, BrokerUnsubscribeInputSchema, brokerCapability, type IBrokerProvider, } from './broker.cap.js';
36
36
  export { cameraPipelineConfigCapability, type ICameraPipelineConfigProvider, } from './camera-pipeline-config.cap.js';
37
37
  export { cameraStreamsCapability, type ICameraStreamsProvider, type PickedCamStream, PickedCamStreamSchema, PickStreamPreferencesSchema, PickStreamRequirementsSchema, type StreamCodec, StreamCodecSchema, } from './camera-streams.cap.js';
38
- export { extractNestedAddonId, isArrayOutputSchema, isCollectionArrayMethod, isObjectInput, isVoidInput, kebabToCamel, looseSchema, objectInputDeclaresAddonId, procedureAuthKey, } from './cap-router-predicates.js';
38
+ export { extractNestedAddonId, isArrayOutputSchema, isCollectionArrayMethod, isObjectInput, isVoidInput, kebabToCamel, looseSchema, objectInputDeclaresAddonId, procedureAuthKey, resolveMethodAuth, } from './cap-router-predicates.js';
39
39
  export type { CapabilityDefinition, CapabilityEventSchema, CapabilityMethodAuth, CapabilityMethodCaller, CapabilityMethodKind, CapabilityMethodOptions, CapabilityMethodSchema, CapabilityMountHint, CapabilityMountKind, CapabilityStatusItemArray, CapabilityStatusKind, CapabilityStatusSchema, CapCaller, DeviceConfigDerivedFormUi, DeviceConfigSpec, DeviceConfigUiSpec, DeviceConfigWidgetUi, DeviceSettingsContribution, InferDeviceProxyCap, InferEvents, InferName, InferNativeProvider, InferProvider, InferRuntimeState, ProviderKind, RuntimeStateDurability, UiContribution, UiContributionKind, UiContributionRemote, } from './capability-definition.js';
40
40
  export { DEFAULT_RUNTIME_STATE_DURABILITY, DEVICE_SETTINGS_CONTRIBUTION_METHODS, DEVICE_STATUS_METHOD, event, expandCapMethods, isDeviceConfigCap, method, resolveCapMount, } from './capability-definition.js';
41
41
  export { CORE_BLOCK_ADDON_PREFIX, CORE_BLOCKS_ADDON_ID, type CoreBlock, type CoreBlockCompileResult, CoreBlockCompileResultSchema, type CoreBlockInput, CoreBlockInputSchema, type CoreBlockPlacement, CoreBlockPlacementSchema, CoreBlockSchema, type CoreBlockStatus, CoreBlockStatusSchema, coreBlockAddonId, coreBlockIdFromAddonId, coreBlocksCapability, type ICoreBlocksProvider, } from './core-blocks.cap.js';
@@ -248,6 +248,19 @@ export declare const llmRuntimeCapability: {
248
248
  readonly mode: "singleton";
249
249
  readonly internal: true;
250
250
  readonly methods: {
251
+ /**
252
+ * `complete`, `status`, `listLocalModels` and `getDiskUsage` had NO
253
+ * `auth` override — `internal: true` did not gate the mount (see the
254
+ * 2026-08-26 note on `data-store-provider`), so they were reachable on
255
+ * the AppRouter by ANY authenticated session at the default
256
+ * `auth: 'protected'`, inconsistent with the rest of this cap (already
257
+ * `auth: 'admin'`) and with this file's own docblock: "the operator
258
+ * reaches this only through the `llm` cap's methods." The sole caller,
259
+ * `addon-ai`'s `runtime-client.ts`, reaches every method here via
260
+ * `ctx.api` + `nodePin` — never tRPC — so `auth: 'admin'` costs it
261
+ * nothing; the public `llm` cap (which end users and non-admin sessions
262
+ * legitimately call for chat/generation) is untouched.
263
+ */
251
264
  readonly complete: import("./capability-definition.js").CapabilityMethodSchema<z.ZodObject<{
252
265
  addonId: z.ZodOptional<z.ZodString>;
253
266
  profileId: z.ZodOptional<z.ZodString>;
@@ -140,6 +140,15 @@ export declare const oauthIntegrationCapability: {
140
140
  readonly mode: "collection";
141
141
  readonly internal: true;
142
142
  readonly methods: {
143
+ /**
144
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
145
+ * `data-store-provider`) — `getDescriptor` was reachable on the AppRouter
146
+ * by ANY authenticated session at the default `auth: 'protected'`. The
147
+ * real caller is `/api/oauth2/authorize` and `/api/oauth2/integrations`
148
+ * (`oauth2-routes.ts`), which resolve the provider directly off the
149
+ * capability registry — never through tRPC. `auth: 'admin'` closes the
150
+ * tRPC surface without touching that path.
151
+ */
143
152
  readonly getDescriptor: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodObject<{
144
153
  integrationId: z.ZodString;
145
154
  displayName: z.ZodString;
@@ -83,6 +83,20 @@ export declare const ssoBridgeCapability: {
83
83
  readonly mode: "singleton";
84
84
  readonly internal: true;
85
85
  readonly methods: {
86
+ /**
87
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
88
+ * `data-store-provider`) — `signBridgeToken` was reachable on the
89
+ * AppRouter by ANY authenticated session at the default
90
+ * `auth: 'protected'`. The claims (including `isAdmin`) are CALLER-
91
+ * SUPPLIED: an unprivileged session could have minted its own
92
+ * `isAdmin: true` bridge token and redeemed it at
93
+ * `/api/auth/sso/finish` to become admin — a full privilege escalation
94
+ * through the exact surface this cap exists to close (see the module
95
+ * docblock). Every real caller (`oauth-grants.ts`, `main.ts`
96
+ * registration, the OIDC/magic-link addons) reaches this through
97
+ * `ctx.api` / the in-process registry — never through tRPC — so
98
+ * `auth: 'admin'` costs those callers nothing.
99
+ */
86
100
  readonly signBridgeToken: import("./capability-definition.js").CapabilityMethodSchema<z.ZodObject<{
87
101
  claims: z.ZodObject<{
88
102
  userId: z.ZodString;
@@ -29,6 +29,13 @@ export declare const storageEvictableCapability: {
29
29
  readonly mode: "collection";
30
30
  readonly internal: true;
31
31
  readonly methods: {
32
+ /**
33
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
34
+ * `data-store-provider`) — this was reachable on the AppRouter by ANY
35
+ * authenticated session at the default `auth: 'protected'`. The only
36
+ * consumer is the orchestrator's `StoragePressureManager`, which calls
37
+ * `ctx.api` — never tRPC — so `auth: 'admin'` costs it nothing.
38
+ */
32
39
  /** Bytes this provider holds on the given location — drives proportional fan-out. */
33
40
  readonly getEvictableUsage: import("./capability-definition.js").CapabilityMethodSchema<z.ZodObject<{
34
41
  locationId: z.ZodString;
@@ -112,6 +112,21 @@ export declare const storageProviderCapability: {
112
112
  readonly mode: "collection";
113
113
  readonly internal: true;
114
114
  readonly methods: {
115
+ /**
116
+ * Every method below except `testLocation` had NO `auth` override —
117
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
118
+ * `data-store-provider`), so this was reachable on the AppRouter by ANY
119
+ * authenticated session at the default `auth: 'protected'`: arbitrary
120
+ * read/write/delete/list against any storage location the operator has
121
+ * configured, keyed only by a caller-supplied `location` + `relativePath`
122
+ * — the same "public consumers never see this cap" claim that was false
123
+ * for `data-store-provider`, here gating raw file I/O instead of raw
124
+ * settings rows. The only legitimate caller,
125
+ * `addon-registry.service.ts`'s `activeStorageProvider`, calls the
126
+ * provider object directly (in-process) — never tRPC — so `auth: 'admin'`
127
+ * on every method costs it nothing. Public consumers already go through
128
+ * the separate `storage` singleton cap.
129
+ */
115
130
  /** Self-description for the "Add location" wizard. */
116
131
  readonly getProviderInfo: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodDiscriminatedUnion<[z.ZodObject<{
117
132
  providerId: z.ZodString;
@@ -81,6 +81,24 @@ export declare const userPasskeysCapability: {
81
81
  success: z.ZodLiteral<true>;
82
82
  credentialId: z.ZodString;
83
83
  }, z.core.$strip>, "mutation">;
84
+ /**
85
+ * The four methods below had NO `auth` override — `internal: true` did
86
+ * not gate the mount (see the 2026-08-26 note on `data-store-provider`),
87
+ * so they were reachable on the AppRouter at the default
88
+ * `auth: 'protected'` (any authenticated session), inconsistent with
89
+ * every other method on this cap (all already `auth: 'admin'`).
90
+ *
91
+ * ⚠ Checked before gating: these are also the PRE-AUTH login-ceremony
92
+ * methods, so admin-gating them here must not break login for an
93
+ * unauthenticated principal. It doesn't — the real login path is the
94
+ * PUBLIC `auth.beginAuthentication` / `auth.finishAuthentication` /
95
+ * `auth.beginDiscoverableAuthentication` / `auth.finishDiscoverableAuthentication`
96
+ * procedures in `server/backend/src/api/core/auth.router.ts`, which call
97
+ * `provider.beginAuthentication(...)` etc. directly against the
98
+ * capability-registry-resolved provider — never through this cap's own
99
+ * tRPC route. `auth: 'admin'` here only closes a redundant, unused
100
+ * second entry point onto the same ceremony.
101
+ */
84
102
  readonly beginAuthentication: import("./capability-definition.js").CapabilityMethodSchema<z.ZodObject<{
85
103
  userId: z.ZodOptional<z.ZodString>;
86
104
  }, z.core.$strip>, z.ZodObject<{
@@ -164,6 +164,14 @@ export declare const VectorStatsResultSchema: z.ZodObject<{
164
164
  bytes: z.ZodOptional<z.ZodNumber>;
165
165
  exact: z.ZodBoolean;
166
166
  }, z.core.$strip>;
167
+ /**
168
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
169
+ * `data-store-provider`) — every method below was reachable on the AppRouter
170
+ * by ANY authenticated session at the default `auth: 'protected'`. The only
171
+ * consumers (`addon-post-analysis`'s embedding stores) reach this cap via
172
+ * `ctx.api` — UDS/Moleculer, never tRPC — so `auth: 'admin'` on every method
173
+ * costs them nothing. No client (viewer or admin-ui) calls `vectorStore.*`.
174
+ */
167
175
  export declare const vectorStoreCapability: {
168
176
  readonly name: "vector-store";
169
177
  readonly scope: "system";
@@ -13,6 +13,21 @@ export declare const viewerUiCapability: {
13
13
  readonly mode: "singleton";
14
14
  readonly internal: true;
15
15
  readonly methods: {
16
+ /**
17
+ * `internal: true` did not gate the mount (see the 2026-08-26 note on
18
+ * `data-store-provider`) — both methods were reachable on the AppRouter
19
+ * by ANY authenticated session at the default `auth: 'protected'`, and
20
+ * `getStaticDir` leaks a hub filesystem path.
21
+ *
22
+ * ⚠ Checked before gating: the VIEWER app IS used by a non-admin user
23
+ * (`roberta`), but it never calls `viewerUi.*` over tRPC. The static SPA
24
+ * it loads is served by the plain `GET /viewer/*` Fastify route in
25
+ * `main.ts`, which reads `staticDir`/`indexPath` from a module-level
26
+ * cache populated ONCE at boot via `capRegistry.getSingletonForNode`
27
+ * (in-process, not tRPC) — the cap's tRPC procedure is never on that
28
+ * request path. `auth: 'admin'` here does not block a single viewer
29
+ * user from loading the app.
30
+ */
16
31
  readonly getStaticDir: import("./capability-definition.js").CapabilityMethodSchema<z.ZodVoid, z.ZodObject<{
17
32
  staticDir: z.ZodString;
18
33
  }, z.core.$strip>, import("./capability-definition.js").CapabilityMethodKind>;