@tai42/api-client 14.0.0 → 16.0.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.
@@ -0,0 +1,126 @@
1
+ // DO NOT EDIT — generated from the platform contract JSON-schema bundle.
2
+ // Source: packages/api-client/contract-schema/contract-schema.json
3
+ // Regenerate with: pnpm --filter @tai42/api-client run schema:generate
4
+ //
5
+ // One zod const + inferred type per published served document and per shared
6
+ // sub-shape. A templated-text field is the shared `templatedText` zod, never a
7
+ // bare string, so a body can never drift back to `z.string()`.
8
+ import { z } from 'zod';
9
+
10
+ import { templatedText } from '../templated-text';
11
+
12
+ export const hookSubject = z.object({ "key_expr": templatedText, "kind": z.string(), "target_kind": z.enum(["agent","tool"]), "target_name": z.string().min(1) }).strict();
13
+ export type HookSubject = z.infer<typeof hookSubject>;
14
+
15
+ export const mediaKind = z.enum(["image","link","document","video","audio"]);
16
+ export type MediaKind = z.infer<typeof mediaKind>;
17
+
18
+ export const mediaItem = z.object({ "caption": z.union([z.string(), z.null()]).default(null), "filename": z.union([z.string(), z.null()]).default(null), "kind": mediaKind, "url": z.string() });
19
+ export type MediaItem = z.infer<typeof mediaItem>;
20
+
21
+ export const presetSeedToolMeta = z.object({ "display_name": z.union([z.string(), z.null()]).default(null), "folder_path": z.union([z.string(), z.null()]).default(null), "tags": z.union([z.array(z.string()), z.null()]).default(null) });
22
+ export type PresetSeedToolMeta = z.infer<typeof presetSeedToolMeta>;
23
+
24
+ export const presetSpec = z.object({ "base_tool": z.string(), "description": z.string().default(""), "fixed_kwargs": z.record(z.string(), z.unknown()).default({}), "name": z.string() });
25
+ export type PresetSpec = z.infer<typeof presetSpec>;
26
+
27
+ export const quickReplyButtonParam = z.object({ "kind": z.literal("quick_reply").default("quick_reply"), "payload": z.string() });
28
+ export type QuickReplyButtonParam = z.infer<typeof quickReplyButtonParam>;
29
+
30
+ export const stateInjection = z.object({ "into": z.string().min(1), "jq": z.union([templatedText, z.null()]).default(null), "template_jq": z.union([z.string(), z.null()]).default(null) }).strict();
31
+ export type StateInjection = z.infer<typeof stateInjection>;
32
+
33
+ export const stateUpdate = z.object({ "adapter": z.union([templatedText, z.null()]).default(null), "jq": z.union([templatedText, z.null()]).default(null), "op_id": z.union([templatedText, z.null()]).default(null), "template_jq": z.union([z.string(), z.null()]).default(null) }).strict();
34
+ export type StateUpdate = z.infer<typeof stateUpdate>;
35
+
36
+ export const stateAttach = z.object({ "input_injections": z.array(stateInjection).default([]), "scope_expr": z.union([templatedText, z.null()]).default(null), "state": z.string(), "subject_expr": templatedText, "templates": z.array(z.string()).default([]), "updates": z.array(stateUpdate).default([]) }).strict();
37
+ export type StateAttach = z.infer<typeof stateAttach>;
38
+
39
+ export const stateBinding = z.object({ "states": z.array(stateAttach).min(1) }).strict();
40
+ export type StateBinding = z.infer<typeof stateBinding>;
41
+
42
+ export const stateTemplateDeclarations = z.object({ "check": z.union([templatedText, z.null()]).default(null), "schema": z.record(z.string(), z.unknown()) }).strict();
43
+ export type StateTemplateDeclarations = z.infer<typeof stateTemplateDeclarations>;
44
+
45
+ export const stateTemplateJq = z.object({ "description": z.string().default(""), "jq": templatedText, "params": z.array(z.string()).default([]), "purpose": z.enum(["input","update"]), "reads": z.array(z.array(z.string())).default([]), "writes": z.array(z.array(z.string())).default([]) }).strict();
46
+ export type StateTemplateJq = z.infer<typeof stateTemplateJq>;
47
+
48
+ export const stateTemplateReconcile = z.object({ "close": templatedText, "orphans": templatedText, "resolutions": templatedText }).strict();
49
+ export type StateTemplateReconcile = z.infer<typeof stateTemplateReconcile>;
50
+
51
+ export const subAgentSpec: z.ZodType = z.lazy(() => z.object({ "description": z.string().default(""), "inline_skills": z.array(z.record(z.string(), z.unknown())).default([]), "name": z.string(), "presets": z.array(presetSpec).default([]), "response_format": z.union([z.unknown(), templatedText, z.record(z.string(), z.unknown()), z.null()]).default(null), "skills": z.array(z.string()).default([]), "strategy": z.union([z.string(), z.null()]).default(null), "subagents": z.array(subAgentSpec).default([]), "system_prompt": z.union([templatedText, z.null()]).default(null), "tool_names": z.array(z.string()).default([]), "tools": z.array(z.unknown()).default([]) }));
52
+ export type SubAgentSpec = z.infer<typeof subAgentSpec>;
53
+
54
+ export const urlButtonParam = z.object({ "kind": z.literal("url").default("url"), "url_parameter": z.string() });
55
+ export type UrlButtonParam = z.infer<typeof urlButtonParam>;
56
+
57
+ export const accessPolicy = z.object({ "condition": z.union([templatedText, z.null()]).default(null), "policy_data": z.record(z.string(), z.unknown()).default({}), "scopes": z.array(z.string()).default([]) });
58
+ export type AccessPolicy = z.infer<typeof accessPolicy>;
59
+
60
+ export const callbackSchema = z.object({ "condition": z.union([templatedText, z.null()]).default(null), "expr": z.union([templatedText, z.null()]).default(null), "tool": z.string().default("") });
61
+ export type CallbackSchema = z.infer<typeof callbackSchema>;
62
+
63
+ export const channelTemplate = z.object({ "body_parameters": z.array(z.string()).default([]), "buttons": z.array(z.unknown().superRefine((x, ctx) => {
64
+ const schemas = [quickReplyButtonParam, urlButtonParam];
65
+ const { errors, failed } = schemas.reduce<{
66
+ errors: z.core.$ZodIssue[];
67
+ failed: number;
68
+ }>(
69
+ ({ errors, failed }, schema) =>
70
+ ((result) =>
71
+ result.error
72
+ ? {
73
+ errors: [...errors, ...result.error.issues],
74
+ failed: failed + 1,
75
+ }
76
+ : { errors, failed })(
77
+ schema.safeParse(x),
78
+ ),
79
+ { errors: [], failed: 0 },
80
+ );
81
+ const passed = schemas.length - failed;
82
+ if (passed !== 1) {
83
+ ctx.addIssue(errors.length ? {
84
+ path: [],
85
+ code: "invalid_union",
86
+ errors: [errors],
87
+ message: "Invalid input: Should pass single schema. Passed " + passed,
88
+ } : {
89
+ path: [],
90
+ code: "custom",
91
+ errors: [errors],
92
+ message: "Invalid input: Should pass single schema. Passed " + passed,
93
+ });
94
+ }
95
+ })).default([]), "header_media": z.union([mediaItem, z.null()]).default(null), "language": z.string(), "name": z.string() });
96
+ export type ChannelTemplate = z.infer<typeof channelTemplate>;
97
+
98
+ export const conversationRoute = z.object({ "callback_secret": z.union([z.string(), z.null()]).default(null), "callback_url": z.union([z.string(), z.null()]).default(null), "channel": z.union([z.string(), z.null()]).default(null), "door": z.enum(["api","channel"]), "error_reply_text": z.union([z.string().min(1).max(2000), z.null()]).default(null), "execution_key": z.string().min(1), "execution_key_fingerprint": z.string().min(1), "initial_mode": z.enum(["agent","manual"]).default("agent"), "locale": z.union([z.string(), z.null()]).default(null), "our_identity": z.union([z.string(), z.null()]).default(null), "payload_expr": z.union([templatedText, z.null()]).default(null), "reply_expr": z.union([templatedText, z.null()]).default(null), "route_name": z.string(), "target_kind": z.enum(["agent","tool"]), "target_name": z.string().min(1), "turns_per_hour_override": z.union([z.number().int().gt(0), z.null()]).default(null) });
99
+ export type ConversationRoute = z.infer<typeof conversationRoute>;
100
+
101
+ export const conversationRouteCreate = z.object({ "callback_url": z.union([z.string(), z.null()]).default(null), "channel": z.union([z.string(), z.null()]).default(null), "door": z.enum(["api","channel"]), "error_reply_text": z.union([z.string().min(1).max(2000), z.null()]).default(null), "execution_key": z.string().min(1), "initial_mode": z.enum(["agent","manual"]).default("agent"), "locale": z.union([z.string(), z.null()]).default(null), "our_identity": z.union([z.string(), z.null()]).default(null), "payload_expr": z.union([templatedText, z.null()]).default(null), "reply_expr": z.union([templatedText, z.null()]).default(null), "route_name": z.string(), "target_kind": z.enum(["agent","tool"]), "target_name": z.string().min(1), "turns_per_hour_override": z.union([z.number().int().gt(0), z.null()]).default(null) });
102
+ export type ConversationRouteCreate = z.infer<typeof conversationRouteCreate>;
103
+
104
+ export const hookParams = z.object({ "condition": z.union([templatedText, z.null()]).default(null), "execution_key": z.string().min(1), "execution_key_fingerprint": z.string().min(1), "expr": z.union([templatedText, z.null()]).default(null), "name": z.string().min(1), "state_binding": z.union([stateBinding, z.null()]).default(null), "subject": z.union([hookSubject, z.null()]).default(null), "tool": z.string().min(1), "tool_kwargs": z.record(z.string(), z.unknown()).default({}), "topic": z.string().min(1) });
105
+ export type HookParams = z.infer<typeof hookParams>;
106
+
107
+ export const hookRegister = z.object({ "condition": z.union([templatedText, z.null()]).default(null), "execution_key": z.string().min(1), "expr": z.union([templatedText, z.null()]).default(null), "name": z.string().min(1), "state_binding": z.union([stateBinding, z.null()]).default(null), "subject": z.union([hookSubject, z.null()]).default(null), "tool": z.string().min(1), "tool_kwargs": z.record(z.string(), z.unknown()).default({}), "topic": z.string().min(1) });
108
+ export type HookRegister = z.infer<typeof hookRegister>;
109
+
110
+ export const presetBody = z.object({ "base_tool": z.string(), "description": z.string().default(""), "extensions": z.array(z.array(z.union([z.string(), z.record(z.string(), z.unknown())]))).default([]), "fixed_kwargs": z.record(z.string(), z.unknown()).default({}), "input_schema": z.union([templatedText, z.record(z.string(), z.unknown()), z.null()]).default(null), "output_schema": z.union([templatedText, z.record(z.string(), z.unknown()), z.null()]).default(null), "state_binding": z.union([stateBinding, z.null()]).default(null) });
111
+ export type PresetBody = z.infer<typeof presetBody>;
112
+
113
+ export const presetSeed = z.object({ "base_tool": z.string(), "description": z.string(), "fixed_kwargs": z.record(z.string(), z.unknown()).default({}), "input_schema": z.union([templatedText, z.record(z.string(), z.unknown()), z.null()]).default(null), "name": z.string(), "output_schema": z.union([templatedText, z.record(z.string(), z.unknown()), z.null()]).default(null), "state_binding": z.union([stateBinding, z.null()]).default(null), "tool_meta": z.union([presetSeedToolMeta, z.null()]).default(null) });
114
+ export type PresetSeed = z.infer<typeof presetSeed>;
115
+
116
+ export const roleDefinition = z.object({ "allow_all": z.boolean().default(false), "base_tier": z.union([z.string(), z.null()]).default(null), "condition": z.union([templatedText, z.null()]).default(null), "description": z.string(), "grants": z.record(z.string(), z.enum(["none","read","write"])), "name": z.string(), "scopes": z.array(z.string()).default([]) });
117
+ export type RoleDefinition = z.infer<typeof roleDefinition>;
118
+
119
+ export const stateDeclaration = z.object({ "default_subject_kind": z.string(), "description": z.string().default(""), "effective_schema": z.union([z.record(z.string(), z.unknown()), z.null()]).default(null), "name": z.string(), "regimes": z.union([z.array(z.record(z.string(), z.unknown())), z.null()]).default(null), "retention_days": z.union([z.number().int().gt(0).lte(2147483647), z.null()]).default(null), "schema": z.union([templatedText, z.record(z.string(), z.unknown())]).optional(), "subject_kinds": z.array(z.string()).min(1), "updated_at": z.union([z.string().datetime({ offset: true }), z.null()]).default(null) }).strict();
120
+ export type StateDeclaration = z.infer<typeof stateDeclaration>;
121
+
122
+ export const stateTemplateDocument = z.object({ "declarations": z.union([stateTemplateDeclarations, z.null()]).default(null), "description": z.string().default(""), "kind": z.literal("state-template").default("state-template"), "name": z.string(), "parameters": z.record(z.string(), z.unknown()).default({}), "reconcile": z.union([stateTemplateReconcile, z.null()]).default(null), "regimes": z.array(z.record(z.string(), z.unknown())).default([]), "schema": z.union([templatedText, z.record(z.string(), z.unknown())]).optional(), "template_jq": z.union([z.record(z.string(), stateTemplateJq), z.null()]).default(null), "trace": z.record(z.string(), z.unknown()).default({}) }).strict();
123
+ export type StateTemplateDocument = z.infer<typeof stateTemplateDocument>;
124
+
125
+ export const targetConversationConfig = z.object({ "greeting_template": z.union([z.string(), z.null()]).default(null), "multichannel": z.boolean().default(false), "state_binding": z.union([stateBinding, z.null()]).default(null), "target_kind": z.enum(["agent","tool"]), "target_name": z.string().min(1) });
126
+ export type TargetConversationConfig = z.infer<typeof targetConversationConfig>;
package/src/index.ts CHANGED
@@ -86,6 +86,7 @@ export type {
86
86
  } from './fleet-report';
87
87
  export * as schemas from './schemas';
88
88
  export type {
89
+ TemplatedText,
89
90
  ToolSchema,
90
91
  ToolMediaResult,
91
92
  ToolTagEntry,
@@ -114,6 +115,7 @@ export type {
114
115
  StateStats,
115
116
  TemplateJq,
116
117
  TemplateReconcile,
118
+ TemplateDeclarations,
117
119
  StateTemplateDocument,
118
120
  StateTemplateListItem,
119
121
  StateInjection,
@@ -205,6 +207,7 @@ export type {
205
207
  Notifications,
206
208
  ChannelTemplate,
207
209
  HookParams,
210
+ HookRegister,
208
211
  HookSubject,
209
212
  HookList,
210
213
  TriggerAuth,
package/src/schemas.ts CHANGED
@@ -6,6 +6,55 @@
6
6
  */
7
7
  import { z } from 'zod';
8
8
 
9
+ import { templatedText } from './templated-text';
10
+ import * as generated from './generated/served-schemas';
11
+
12
+ export { templatedText, requiredTemplatedText } from './templated-text';
13
+ export type { TemplatedText } from './templated-text';
14
+
15
+ // Served-document schemas are GENERATED from the platform contract JSON-schema
16
+ // bundle (src/generated/served-schemas.ts) and re-exported here under the names the
17
+ // rest of the client uses. The generator maps every `x-tai42-templated-text` field
18
+ // to the shared `templatedText` zod, so a served body can never be a bare string.
19
+ // The plain response DTOs below (list wrappers, acks, version rows) stay hand-written.
20
+ export const stateInjection = generated.stateInjection;
21
+ export type StateInjection = z.infer<typeof stateInjection>;
22
+ export const stateUpdate = generated.stateUpdate;
23
+ export type StateUpdate = z.infer<typeof stateUpdate>;
24
+ export const stateAttach = generated.stateAttach;
25
+ export type StateAttach = z.infer<typeof stateAttach>;
26
+ export const stateBinding = generated.stateBinding;
27
+ export type StateBinding = z.infer<typeof stateBinding>;
28
+ export const presetBody = generated.presetBody;
29
+ export type PresetBody = z.input<typeof presetBody>;
30
+ export const conversationRoute = generated.conversationRoute;
31
+ export type ConversationRoute = z.infer<typeof conversationRoute>;
32
+ export const conversationRouteCreate = generated.conversationRouteCreate;
33
+ export type ConversationRouteCreate = z.input<typeof conversationRouteCreate>;
34
+ export const targetConversationConfig = generated.targetConversationConfig;
35
+ export type TargetConversationConfig = z.input<typeof targetConversationConfig>;
36
+ export const channelTemplate = generated.channelTemplate;
37
+ export type ChannelTemplate = z.infer<typeof channelTemplate>;
38
+ export const hookSubject = generated.hookSubject;
39
+ export type HookSubject = z.infer<typeof hookSubject>;
40
+ export const hookParams = generated.hookParams;
41
+ export type HookParams = z.infer<typeof hookParams>;
42
+ export const hookRegister = generated.hookRegister;
43
+ export type HookRegister = z.input<typeof hookRegister>;
44
+ export const stateDeclaration = generated.stateDeclaration;
45
+ export type StateDeclaration = z.infer<typeof stateDeclaration>;
46
+ export const stateTemplateDocument = generated.stateTemplateDocument;
47
+ export type StateTemplateDocument = z.infer<typeof stateTemplateDocument>;
48
+ export const templateJq = generated.stateTemplateJq;
49
+ export type TemplateJq = z.infer<typeof templateJq>;
50
+ export const templateReconcile = generated.stateTemplateReconcile;
51
+ export type TemplateReconcile = z.infer<typeof templateReconcile>;
52
+ export const templateDeclarations = generated.stateTemplateDeclarations;
53
+ export type TemplateDeclarations = z.infer<typeof templateDeclarations>;
54
+ export const policyBody = generated.accessPolicy;
55
+ export type PolicyBody = z.infer<typeof policyBody>;
56
+ export const roleBody = generated.roleDefinition;
57
+ export type RoleBody = z.infer<typeof roleBody>;
9
58
  /** An arbitrary JSON value (tool results, rendered payloads). */
10
59
  export const jsonValue: z.ZodType = z.unknown();
11
60
 
@@ -149,89 +198,6 @@ export const presetDetail = presetRecord.extend({
149
198
  });
150
199
  export type PresetDetail = z.infer<typeof presetDetail>;
151
200
 
152
- /**
153
- * One input injection of a state binding: BEFORE the run, a value is produced and
154
- * placed into the run input under `into` (the run-input field name). A template
155
- * `input` jq (`template_jq`, named `name` or attachment-qualified `template.name`) reads the
156
- * record — its input is the record (`.`), with declared params bound as `$params`; a
157
- * custom `jq` reads `{record, input}` → the value. Exactly one of `template_jq`/`jq`
158
- * carries the program; the other is `null`.
159
- */
160
- export const stateInjection = z.object({
161
- template_jq: z.string().nullable().default(null),
162
- jq: z.string().nullable().default(null),
163
- into: z.string(),
164
- });
165
- export type StateInjection = z.infer<typeof stateInjection>;
166
-
167
- /**
168
- * One update of a state binding: AFTER the run, a template-relative op batch is
169
- * applied through the store. A NAMED update (`template_jq`) runs the template `update`
170
- * jq over `{record, input}` where `input` is built by `adapter` — a jq over
171
- * `{output, input}` that constructs the update jq's declared input object. A custom
172
- * `jq` runs over `{record, output, input}` → `[{op, path, value}]` and carries no
173
- * adapter. `op_id` is an optional idempotency-key expression. Exactly one of
174
- * `template_jq`/`jq` carries the program.
175
- */
176
- export const stateUpdate = z.object({
177
- template_jq: z.string().nullable().default(null),
178
- jq: z.string().nullable().default(null),
179
- // A named update's adapter is either a non-empty jq or `null` (no adapter — the
180
- // run input passes through). `min(1)` makes the empty string impossible to
181
- // round-trip: the platform compile-checks any non-null adapter and refuses `''`.
182
- adapter: z.string().min(1).nullable().default(null),
183
- op_id: z.string().nullable().default(null),
184
- });
185
- export type StateUpdate = z.infer<typeof stateUpdate>;
186
-
187
- /**
188
- * One attached state of a binding: the `state`, one or more `templates`
189
- * (attach-on-use — attached to the state on the binding's save), the `subject_expr`
190
- * (a jq yielding the record KEY — a bare key string OR a full subject object — that
191
- * this binding reads and updates), an optional `scope_expr` (a boolean jq predicate;
192
- * when it is false this state is skipped for the run), and the ordered
193
- * `input_injections` (before the run) and `updates` (after it).
194
- */
195
- export const stateAttach = z.object({
196
- state: z.string(),
197
- templates: z.array(z.string()).default([]),
198
- // The platform contract enforces a non-empty subject (min_length=1); an empty
199
- // expression is rejected here, never sent for the server to refuse.
200
- subject_expr: z.string().min(1),
201
- scope_expr: z.string().nullable().default(null),
202
- input_injections: z.array(stateInjection).default([]),
203
- updates: z.array(stateUpdate).default([]),
204
- });
205
- export type StateAttach = z.infer<typeof stateAttach>;
206
-
207
- /**
208
- * The one generic binding shape carried, optionally, on every runnable definition
209
- * (a preset, a channel route, a schedule, a hook) and repeated per node by the
210
- * flow engine. It attaches one or more states, each with its templates, subject,
211
- * injections and updates. `null` on a definition means no binding. Mirrors the
212
- * platform `StateBinding` document.
213
- */
214
- export const stateBinding = z.object({
215
- // At least one attached state: the platform contract refuses a zero-state binding, so
216
- // "no binding" is spelled `null` on the definition, never `{ states: [] }`.
217
- states: z.array(stateAttach).min(1),
218
- });
219
- export type StateBinding = z.infer<typeof stateBinding>;
220
-
221
- /** The full version body a preset stores under `kind="preset"`. */
222
- export const presetBody = z.object({
223
- base_tool: z.string(),
224
- description: z.string(),
225
- fixed_kwargs: z.record(z.string(), z.unknown()),
226
- extensions: presetExtensions,
227
- output_schema: z.record(z.string(), z.unknown()).nullable(),
228
- input_schema: z.record(z.string(), z.unknown()).nullable(),
229
- // The optional door-layer state binding this preset applies around every run
230
- // (`null` when the preset touches no state).
231
- state_binding: stateBinding.nullable().default(null),
232
- });
233
- export type PresetBody = z.infer<typeof presetBody>;
234
-
235
201
  /**
236
202
  * One immutable version row (`GET /api/presets/{name}/versions[/{version}]`).
237
203
  * `is_current` flags the active version; `tags` here is the GENERIC per-version
@@ -1192,74 +1158,12 @@ export type ConversationAnswerStatus = z.infer<typeof conversationAnswerStatus>;
1192
1158
  export const conversationRecordOrigin = z.enum(['client', 'operator']);
1193
1159
  export type ConversationRecordOrigin = z.infer<typeof conversationRecordOrigin>;
1194
1160
 
1195
- /**
1196
- * A stored routing row as a read door returns it, its `callback_secret` withheld.
1197
- *
1198
- * `initial_mode`, `turns_per_hour_override`, and `error_reply_text` carry defaults
1199
- * because a stored row always returns them, while a hand-built stub/fixture may
1200
- * omit them — the default keeps such a payload valid without inventing a field the
1201
- * server never sends.
1202
- */
1203
- export const conversationRoute = z.object({
1204
- route_name: z.string(),
1205
- door: conversationDoor,
1206
- target_kind: conversationTargetKind,
1207
- target_name: z.string(),
1208
- payload_expr: z.string().nullable(),
1209
- reply_expr: z.string().nullable(),
1210
- initial_mode: conversationMode.default('agent'),
1211
- execution_key: z.string(),
1212
- channel: z.string().nullable(),
1213
- our_identity: z.string().nullable(),
1214
- callback_url: z.string().nullable(),
1215
- turns_per_hour_override: z.number().int().nullable().default(null),
1216
- error_reply_text: z.string().nullable().default(null),
1217
- execution_key_fingerprint: z.string(),
1218
- // The door-layer state binding the backend stores on the route's target config and
1219
- // returns on read (`null` when the route touches no state) — the edit form prefills it.
1220
- state_binding: stateBinding.nullable().default(null),
1221
- });
1222
- export type ConversationRoute = z.infer<typeof conversationRoute>;
1223
-
1224
1161
  export const conversationRoutes = z.object({
1225
1162
  items: z.array(conversationRoute),
1226
1163
  total: z.number(),
1227
1164
  });
1228
1165
  export type ConversationRoutes = z.infer<typeof conversationRoutes>;
1229
1166
 
1230
- /**
1231
- * The client-facing create/edit body for a conversation route — the wire model of
1232
- * `tai42_contract.conversations.ConversationRouteCreate`. `POST
1233
- * /api/conversations/{route_name}` is an UPSERT, so this one shape is both the
1234
- * create AND the edit body. `route_name` rides the URL path; it is carried here too
1235
- * (the door rejects a body whose `route_name` disagrees with the path).
1236
- *
1237
- * The contract's cross-field validators are mirrored where the form authors this
1238
- * body: `payload_expr`/`reply_expr` are tool-only; an `api` door carries a
1239
- * `callback_url` (and no channel identity); a `channel` door carries `channel` +
1240
- * `our_identity` (and no callback). Sent explicitly (including `null`) so an edit
1241
- * clears a field the operator emptied rather than leaving the stored value.
1242
- */
1243
- export const conversationRouteCreate = z.object({
1244
- route_name: z.string(),
1245
- door: conversationDoor,
1246
- target_kind: conversationTargetKind,
1247
- target_name: z.string().min(1),
1248
- payload_expr: z.string().nullable().default(null),
1249
- reply_expr: z.string().nullable().default(null),
1250
- initial_mode: conversationMode.default('agent'),
1251
- execution_key: z.string().min(1),
1252
- channel: z.string().nullable().default(null),
1253
- our_identity: z.string().nullable().default(null),
1254
- callback_url: z.string().nullable().default(null),
1255
- turns_per_hour_override: z.number().int().positive().nullable().default(null),
1256
- error_reply_text: z.string().min(1).max(2000).nullable().default(null),
1257
- // The optional door-layer state binding this route applies around every turn's
1258
- // tool run (`null` when the route touches no state).
1259
- state_binding: stateBinding.nullable().default(null),
1260
- });
1261
- export type ConversationRouteCreate = z.infer<typeof conversationRouteCreate>;
1262
-
1263
1167
  /**
1264
1168
  * The create/replace reply: whether THIS call created the row (vs. replaced an
1265
1169
  * existing one), the row itself (its `callback_secret` withheld), and the
@@ -1388,28 +1292,6 @@ export const conversationThreadMessageSent = z.object({
1388
1292
  });
1389
1293
  export type ConversationThreadMessageSent = z.infer<typeof conversationThreadMessageSent>;
1390
1294
 
1391
- /**
1392
- * Per-target presentation config for the conversation bridge, keyed by
1393
- * `(target_kind, target_name)` — the wire model of
1394
- * `tai42_contract.conversations.TargetConversationConfig`. The row carries no
1395
- * server-derived fields, so this ONE shape is the stored row AND the upsert body
1396
- * (`PUT /api/conversation-configs/{target_kind}/{target_name}` is the create AND
1397
- * the edit path).
1398
- *
1399
- * `multichannel` opts the target into person linking; `greeting_template` is the
1400
- * first-contact greeting. `greeting_template` is a `str.format` template (NOT a jq
1401
- * expression) that may reference at most the `{pairing_code}` placeholder — it
1402
- * carries no `x-tai42-expression`. `null` is the explicit spelling for "no
1403
- * greeting"; a blank string is refused server-side.
1404
- */
1405
- export const targetConversationConfig = z.object({
1406
- target_kind: conversationTargetKind,
1407
- target_name: z.string().min(1),
1408
- multichannel: z.boolean().default(false),
1409
- greeting_template: z.string().nullable().default(null),
1410
- });
1411
- export type TargetConversationConfig = z.infer<typeof targetConversationConfig>;
1412
-
1413
1295
  /** Every stored per-target config (`GET /api/conversation-configs`). */
1414
1296
  export const conversationConfigs = z.object({
1415
1297
  items: z.array(targetConversationConfig),
@@ -1530,19 +1412,6 @@ export type WebEntryCodeRevoked = z.infer<typeof webEntryCodeRevoked>;
1530
1412
  // send), `options` (tappable option labels) — plus the `audience` identity the
1531
1413
  // record is addressed to; the inbox renders them.
1532
1414
 
1533
- /**
1534
- * A pre-approved channel template a notification carried, stored raw on the sink
1535
- * record when the notify supplied one (server-side it is mutually exclusive with
1536
- * `media`/`options`). `parameters` is the POSITIONAL list of body-text values
1537
- * substituted into the template's placeholders in order; empty when it has none.
1538
- */
1539
- export const channelTemplate = z.object({
1540
- name: z.string(),
1541
- language: z.string(),
1542
- parameters: z.array(z.string()).default([]),
1543
- });
1544
- export type ChannelTemplate = z.infer<typeof channelTemplate>;
1545
-
1546
1415
  export const notification = z.object({
1547
1416
  id: z.string(),
1548
1417
  message: z.string(),
@@ -1575,9 +1444,10 @@ export const notifications = z.object({
1575
1444
  export type Notifications = z.infer<typeof notifications>;
1576
1445
 
1577
1446
  // -- hooks -------------------------------------------------------------------
1578
- // Shapes match tai42_contract.hooks.HookParams: a hook fires a `tool` on a `topic`,
1579
- // optionally gated by a `condition` and shaped by an `expr` (each either an inline
1580
- // spec or a registered id, with its own kwargs).
1447
+ // The hand-written hook response DTOs: the fire-door authority enum, the list rows and
1448
+ // their wrapper, and the per-topic verifier/trigger metadata. The served hook DOCUMENT
1449
+ // schemas (`hookSubject`/`hookParams`/`hookRegister`) are generated from the contract
1450
+ // bundle and re-exported at the top of this file, not defined here.
1581
1451
 
1582
1452
  /** A fire door — who may trigger a path, not what the fire may do. A string enum. */
1583
1453
  export const triggerAuth = z.enum([
@@ -1589,44 +1459,6 @@ export const triggerAuth = z.enum([
1589
1459
  ]);
1590
1460
  export type TriggerAuth = z.infer<typeof triggerAuth>;
1591
1461
 
1592
- /**
1593
- * The optional state subject a hook fire targets (mirrors
1594
- * `tai42_contract.hooks.HookSubject`): the conversation-target scope plus the subject
1595
- * `kind` and a `key_expr` jq evaluated over the event payload at fire. `null` leaves the
1596
- * fire with no ambient state context.
1597
- */
1598
- export const hookSubject = z.object({
1599
- target_kind: conversationTargetKind,
1600
- target_name: z.string(),
1601
- kind: z.string(),
1602
- key_expr: z.string(),
1603
- });
1604
- export type HookSubject = z.infer<typeof hookSubject>;
1605
-
1606
- export const hookParams = z.object({
1607
- name: z.string(),
1608
- topic: z.string(),
1609
- tool: z.string(),
1610
- // The api-key `user_id` the fire runs AS.
1611
- execution_key: z.string().min(1),
1612
- tool_kwargs: z.record(z.string(), z.unknown()).default({}),
1613
- // The optional state subject the fire targets; `null` leaves it with no ambient
1614
- // state context (a state tool it calls must then carry an explicit subject).
1615
- subject: hookSubject.nullable().default(null),
1616
- condition: z.string().nullable().default(null),
1617
- condition_id: z.string().nullable().default(null),
1618
- // The `*_kwargs` pair is non-optional in the contract (defaults to {}, never
1619
- // null) — unlike the sibling condition/expr string fields, which are nullable.
1620
- condition_kwargs: z.record(z.string(), z.unknown()).default({}),
1621
- expr: z.string().nullable().default(null),
1622
- expr_id: z.string().nullable().default(null),
1623
- expr_kwargs: z.record(z.string(), z.unknown()).default({}),
1624
- // The optional door-layer state binding this hook applies around its fire's tool
1625
- // run (`null` when the hook touches no state).
1626
- state_binding: stateBinding.nullable().default(null),
1627
- });
1628
- export type HookParams = z.infer<typeof hookParams>;
1629
-
1630
1462
  export const hookList = z.object({
1631
1463
  items: z.array(hookParams),
1632
1464
  total: z.number(),
@@ -1797,26 +1629,6 @@ export type GrantLevel = z.infer<typeof grantLevel>;
1797
1629
  export const roleGrants = z.record(z.string(), grantLevel);
1798
1630
  export type RoleGrants = z.infer<typeof roleGrants>;
1799
1631
 
1800
- /**
1801
- * A role body (`GET /api/auth/roles`, and the write routes' echo). Layer 1 is the
1802
- * read-only base-tier ceiling — the seeded jq `condition` plus `base_tier`
1803
- * (`editor`/`viewer`, or `null` for the reserved `allow_all` admin). Layer 2 is the
1804
- * editable per-tag `grants` map. `allow_all` (admin) carries an empty `grants` map
1805
- * and reaches everything, un-lockable. `condition`/`condition_id`/`condition_kwargs`
1806
- * are the base-tier jq — READ-ONLY here (no raw-jq authoring surface).
1807
- */
1808
- export const roleBody = z.object({
1809
- name: z.string(),
1810
- description: z.string(),
1811
- scopes: z.array(z.string()),
1812
- condition: z.string().nullable(),
1813
- condition_id: z.string().nullable(),
1814
- condition_kwargs: jsonValue.nullable(),
1815
- base_tier: z.string().nullable(),
1816
- allow_all: z.boolean(),
1817
- grants: roleGrants,
1818
- });
1819
- export type RoleBody = z.infer<typeof roleBody>;
1820
1632
  export const roleList = z.array(roleBody);
1821
1633
 
1822
1634
  /** `DELETE /api/auth/roles/{name}` — the deleted role's name. */
@@ -1879,9 +1691,7 @@ export const tokensPayload = z.array(
1879
1691
  description: z.string(),
1880
1692
  scopes: z.array(z.string()),
1881
1693
  policy_data: jsonValue,
1882
- condition: z.string().nullable().optional(),
1883
- condition_id: z.string().nullable().optional(),
1884
- condition_kwargs: jsonValue.nullable().optional(),
1694
+ condition: templatedText.nullable().optional(),
1885
1695
  }),
1886
1696
  );
1887
1697
  export type TokensPayload = z.infer<typeof tokensPayload>;
@@ -2058,21 +1868,6 @@ export const validateConditionResult = z.object({
2058
1868
  });
2059
1869
  export type ValidateConditionResult = z.infer<typeof validateConditionResult>;
2060
1870
 
2061
- /**
2062
- * The enforced policy shape a version body carries. SECRET-ADJACENT — `condition`
2063
- * can reveal auth logic, so its fixtures are hand-authored, never captured.
2064
- * `condition`/`condition_id` are mutually exclusive at author time; both are
2065
- * nullable here because whichever mode is unused is stored as `null`.
2066
- */
2067
- export const policyBody = z.object({
2068
- scopes: z.array(z.string()),
2069
- policy_data: jsonValue,
2070
- condition: z.string().nullable(),
2071
- condition_id: z.string().nullable(),
2072
- condition_kwargs: jsonValue.nullable(),
2073
- });
2074
- export type PolicyBody = z.infer<typeof policyBody>;
2075
-
2076
1871
  /**
2077
1872
  * One immutable policy version row
2078
1873
  * (`GET /api/auth/api-keys/{user_id}/policy/versions`). `is_current` flags the
@@ -2696,12 +2491,13 @@ export type MarketplaceUninstallResult = z.infer<typeof marketplaceUninstallResu
2696
2491
  export { toolRunSubmitResult, toolRunRecord, toolRunList } from './tool-runs';
2697
2492
 
2698
2493
  // -- states ------------------------------------------------------------------
2699
- // Shapes mirror tai42_contract.states.models: a declared JSON document, one per
2700
- // subject. The base document, template fragments, write regimes and effective schema
2701
- // are permissive JSON records — the auto-form and JsonTree interpret them at runtime;
2702
- // a drift throws ApiSchemaError. Server-composed fields (`effective_schema`, `regimes`,
2703
- // list/stats derived columns) are modelled optional so a response that omits them still
2704
- // parses.
2494
+ // The hand-written state response DTOs — list rows and detail (built on the generated
2495
+ // `stateDeclaration`), attachments, per-subject records and subjects, stats and consumers.
2496
+ // The served DOCUMENT schemas (`stateDeclaration`/`stateTemplateDocument` and the template
2497
+ // sub-shapes) are generated from the contract bundle and re-exported at the top of this
2498
+ // file. The composed `effective_schema` and write `regimes` stay permissive JSON records
2499
+ // (the auto-form and JsonTree interpret them at runtime) and are server-computed, so they
2500
+ // are modelled optional and a response that omits them still parses.
2705
2501
 
2706
2502
  /** One addressed subject: the conversation-target scope plus the (kind, key) within it. */
2707
2503
  export const stateSubject = z.object({
@@ -2715,25 +2511,6 @@ export type StateSubject = z.infer<typeof stateSubject>;
2715
2511
  /** One absolute write-regime rule composed over the attachments: `{path, regime}`, permissive. */
2716
2512
  export const stateRegime = z.record(z.string(), z.unknown());
2717
2513
 
2718
- /**
2719
- * A declared state served on every read. `schema` is the base JSON Schema;
2720
- * `effective_schema` (the base composed with every attached template's fragment) and
2721
- * `regimes` (the absolute write-regime rules) are platform-COMPUTED and served on every
2722
- * read — modelled optional so a write body that omits them, or a server yet to compose
2723
- * them, still parses. A drift throws ApiSchemaError.
2724
- */
2725
- export const stateDeclaration = z.object({
2726
- name: z.string(),
2727
- description: z.string().default(''),
2728
- schema: jsonSchema,
2729
- subject_kinds: z.array(z.string()),
2730
- default_subject_kind: z.string(),
2731
- retention_days: z.number().nullable().default(null),
2732
- effective_schema: jsonSchema.nullable().optional(),
2733
- regimes: z.array(stateRegime).nullable().optional(),
2734
- });
2735
- export type StateDeclaration = z.infer<typeof stateDeclaration>;
2736
-
2737
2514
  /**
2738
2515
  * One row of `GET /api/states` — a served declaration (`list_states` dumps every
2739
2516
  * `StateDeclaration`) plus `updated_at` (the row's last-write timestamp, ISO or
@@ -2776,55 +2553,6 @@ export const stateStats = z.object({
2776
2553
  });
2777
2554
  export type StateStats = z.infer<typeof stateStats>;
2778
2555
 
2779
- /**
2780
- * One template jq: `jq` is a program over the subject's attached subtree, its `purpose`
2781
- * either `input` (a read-only program feeding a tool argument) or `update` (a program
2782
- * returning an op batch that mutates the record). `params` are its declared argument
2783
- * names; `reads`/`writes` are the template-relative record paths an `update` declares,
2784
- * each a list of key segments; `description` is the human label.
2785
- */
2786
- export const templateJq = z.object({
2787
- description: z.string().default(''),
2788
- purpose: z.enum(['input', 'update']),
2789
- params: z.array(z.string()).default([]),
2790
- reads: z.array(z.array(z.string())).default([]),
2791
- writes: z.array(z.array(z.string())).default([]),
2792
- jq: z.string(),
2793
- });
2794
- export type TemplateJq = z.infer<typeof templateJq>;
2795
-
2796
- /**
2797
- * How a declarations edit settles open records: `view` reads the record, `close`
2798
- * builds the op batch that settles it, `resolutions` names the resolutions a close
2799
- * may name — each a jq program.
2800
- */
2801
- export const templateReconcile = z.object({
2802
- view: z.string(),
2803
- close: z.string(),
2804
- resolutions: z.string(),
2805
- });
2806
- export type TemplateReconcile = z.infer<typeof templateReconcile>;
2807
-
2808
- /**
2809
- * The platform half of a state-template document (mirrors StateTemplateDocument).
2810
- * `template_jq` maps a name to its definition (each carrying its `purpose`);
2811
- * `reconcile` is the settle policy — both optional (`null` when the template declares
2812
- * none).
2813
- */
2814
- export const stateTemplateDocument = z.object({
2815
- kind: z.literal('state-template').default('state-template'),
2816
- name: z.string(),
2817
- description: z.string().default(''),
2818
- parameters: z.record(z.string(), z.unknown()).default({}),
2819
- schema: jsonSchema,
2820
- regimes: z.array(stateRegime).default([]),
2821
- declarations: z.record(z.string(), z.unknown()).nullable().default(null),
2822
- trace: z.record(z.string(), z.unknown()).default({}),
2823
- template_jq: z.record(z.string(), templateJq).nullable().default(null),
2824
- reconcile: templateReconcile.nullable().default(null),
2825
- });
2826
- export type StateTemplateDocument = z.infer<typeof stateTemplateDocument>;
2827
-
2828
2556
  /**
2829
2557
  * One row of `GET /api/state-templates`. The template document plus the two derived columns
2830
2558
  * the Templates tab shows: `attached_to` (how many states attach it — a delete is refused