openapi.yaml yaml
4,319 lines 135.1 KB
Raw
sha256:49f768e5fb72e8d17321410817422fc5cab8f0a1b66a1e1da8bdd4cd251c4f7e Merge 'feat/ourware-landing-rebrand' into 'main' — proposal… Human 18 days ago
1 openapi: 3.0.3
2 info:
3 title: Knowtation Hub API
4 description: REST API for the Knowtation Hub (vault read/write, proposals, capture). Same contract as CLI/MCP where applicable.
5 version: 1.0.0
6 links:
7 - description: API contract (human-readable)
8 url: ./HUB-API.md
9
10 servers:
11 - url: /api/v1
12 description: Relative to Hub base URL (e.g. https://hub.example.com)
13
14 tags:
15 - name: Health
16 - name: Auth
17 - name: Notes
18 - name: Search
19 - name: Proposals
20 - name: Capture
21 - name: Flows
22 - name: Tasks
23 - name: LearningPaths
24 - name: Attachments
25 - name: DocsConnectors
26
27 security:
28 - BearerAuth: []
29
30 paths:
31 /health:
32 get:
33 tags: [Health]
34 summary: Health check
35 security: []
36 responses:
37 '200':
38 description: Hub is up
39 content:
40 application/json:
41 schema: { type: object, properties: { ok: { type: boolean } }, required: [ok] }
42
43 /auth/agent/credentials:
44 post:
45 tags: [Auth]
46 summary: Phase C — mint scoped REST agent credential (secret once)
47 description: |
48 Requires a human session JWT. Returns opaque `kt_agent_<id>.<secret>` once.
49 Default scopes: propose + vault:read. No admin scopes.
50 responses:
51 '201':
52 description: Credential minted
53 '401':
54 description: Unauthorized
55 '409':
56 description: Credential limit
57 get:
58 tags: [Auth]
59 summary: Phase C — list agent credentials (metadata only)
60 responses:
61 '200':
62 description: Credential list without secrets
63 /auth/agent/credentials/{id}:
64 delete:
65 tags: [Auth]
66 summary: Phase C — revoke agent credential
67 parameters:
68 - name: id
69 in: path
70 required: true
71 schema: { type: string }
72 responses:
73 '200':
74 description: Revoked (idempotent)
75 /auth/agent/credentials/{id}/rotate:
76 post:
77 tags: [Auth]
78 summary: Phase C — rotate agent credential secret (shown once)
79 parameters:
80 - name: id
81 in: path
82 required: true
83 schema: { type: string }
84 responses:
85 '200':
86 description: New secret issued
87 /auth/agent/token:
88 post:
89 tags: [Auth]
90 summary: Phase C — exchange kt_agent_ credential for agent_access JWT
91 security: []
92 responses:
93 '200':
94 description: Access token issued
95 '401':
96 description: Invalid credential
97 '503':
98 description: Store unavailable
99
100 /api/v1/auth/session:
101 get:
102 tags: [Auth]
103 summary: C7 Session introspection — current identity and scopes
104 description: |
105 Returns the verified identity and derived API scopes for the caller. Accepts only a
106 `Bearer` JWT in the `Authorization` header — no cookie required, making it safe to call
107 cross-origin from Scooling or any other consumer.
108
109 The response is derived entirely from the signed token — no database call is made.
110 Scopes are role-derived today (C4 will replace this with per-user explicit grants without
111 changing the response shape).
112 security:
113 - bearerAuth: []
114 responses:
115 '200':
116 description: Verified session
117 content:
118 application/json:
119 schema:
120 type: object
121 required: [sub, provider, id, name, role, iat, exp, scopes]
122 properties:
123 sub:
124 type: string
125 description: Canonical user ID (`provider:id`)
126 example: google:104164334692309763642
127 provider:
128 type: string
129 enum: [google, github, apple]
130 id:
131 type: string
132 description: Provider-specific user ID
133 name:
134 type: string
135 description: Display name (empty for refresh-path tokens)
136 role:
137 type: string
138 enum: [admin, member]
139 iat:
140 type: integer
141 description: Token issued-at (Unix seconds)
142 exp:
143 type: integer
144 description: Token expires-at (Unix seconds)
145 scopes:
146 type: array
147 items: { type: string }
148 description: Derived API scopes. `admin` role → `[vault:read, vault:write, admin]`; `member` → `[vault:read, vault:write]`
149 example: [vault:read, vault:write]
150 '401':
151 description: Missing, expired, or tampered token
152 content:
153 application/json:
154 schema:
155 type: object
156 properties:
157 error: { type: string }
158 code: { type: string, enum: [UNAUTHORIZED] }
159
160 /auth/providers:
161 get:
162 tags: [Auth]
163 summary: OAuth providers configured
164 security: []
165 responses:
166 '200':
167 content:
168 application/json:
169 schema:
170 type: object
171 properties:
172 google: { type: boolean }
173 github: { type: boolean }
174 apple: { type: boolean }
175 local: { type: boolean }
176
177 /api/v1/auth/native-apple-exchange:
178 post:
179 tags: [Auth]
180 summary: Sign in with Apple identity-assertion exchange (native)
181 description: |
182 Verifies an Apple `identity_token` (JWKS) and mints a hosted session JWT
183 (`provider: apple`, `type: session`). Not Passport Google/GitHub and not
184 `api/v1/auth/native` PKCE. Does not return `scooling_uid`.
185 security: []
186 requestBody:
187 required: true
188 content:
189 application/json:
190 schema:
191 type: object
192 required: [identity_token]
193 additionalProperties: false
194 properties:
195 identity_token: { type: string }
196 nonce: { type: string }
197 full_name: { type: string, maxLength: 128 }
198 responses:
199 '200':
200 description: Hosted session minted
201 content:
202 application/json:
203 schema:
204 type: object
205 required: [schema_version, token_type, access_token, expires_in]
206 properties:
207 schema_version: { type: integer, enum: [1] }
208 token_type: { type: string, enum: [Bearer] }
209 access_token: { type: string }
210 expires_in: { type: integer }
211 '400':
212 description: Bad request
213 '401':
214 description: Apple assertion invalid
215 '403':
216 description: Offline-locked OAuth disabled
217 '503':
218 description: Not configured or Apple JWKS unavailable
219
220 /notes/facets:
221 get:
222 tags: [Notes]
223 summary: Projects, tags, folders for filter dropdowns
224 responses:
225 '200':
226 content:
227 application/json:
228 schema:
229 type: object
230 properties:
231 projects: { type: array, items: { type: string } }
232 tags: { type: array, items: { type: string } }
233 folders: { type: array, items: { type: string } }
234
235 /notes:
236 get:
237 tags: [Notes]
238 summary: List notes
239 parameters:
240 - name: folder
241 in: query
242 schema: { type: string }
243 - name: project
244 in: query
245 schema: { type: string }
246 - name: tag
247 in: query
248 schema: { type: string }
249 - name: since
250 in: query
251 schema: { type: string }
252 - name: until
253 in: query
254 schema: { type: string }
255 - name: limit
256 in: query
257 schema: { type: integer, minimum: 0, maximum: 100 }
258 - name: offset
259 in: query
260 schema: { type: integer, minimum: 0 }
261 - name: order
262 in: query
263 schema: { type: string, enum: [date, date-asc] }
264 - name: fields
265 in: query
266 schema: { type: string, enum: [path, path+metadata, full] }
267 - name: count_only
268 in: query
269 schema: { type: boolean }
270 responses:
271 '200':
272 content:
273 application/json:
274 schema:
275 oneOf:
276 - type: object
277 properties:
278 notes: { type: array, items: { $ref: '#/components/schemas/NoteListItem' } }
279 total: { type: integer }
280 - type: object
281 properties:
282 total: { type: integer }
283 post:
284 tags: [Notes]
285 summary: Write or update a note
286 requestBody:
287 required: true
288 content:
289 application/json:
290 schema:
291 type: object
292 required: [path]
293 properties:
294 path: { type: string }
295 body: { type: string }
296 frontmatter: { type: object }
297 append: { type: boolean }
298 responses:
299 '200':
300 content:
301 application/json:
302 schema: { type: object, properties: { path: { type: string }, written: { type: boolean } } }
303 '400':
304 '500':
305 content:
306 application/json:
307 schema: { $ref: '#/components/schemas/Error' }
308
309 /notes/{path}:
310 get:
311 tags: [Notes]
312 summary: Get one note by path
313 parameters:
314 - name: path
315 in: path
316 required: true
317 schema: { type: string }
318 responses:
319 '200':
320 content:
321 application/json:
322 schema: { $ref: '#/components/schemas/NoteFull' }
323 '404':
324 content:
325 application/json:
326 schema: { $ref: '#/components/schemas/Error' }
327
328 /note-outline:
329 get:
330 tags: [Notes]
331 summary: Body-free NoteOutline headings for one note
332 description: >
333 Returns knowtation.note_outline/v1 metadata for one authorized vault-relative note.
334 The response excludes note body text, snippets, full frontmatter, absolute paths,
335 provider payloads, MCP resource URIs, summaries, vectors, OCR, PageIndex output,
336 persistence records, and write-back state.
337 parameters:
338 - name: path
339 in: query
340 required: true
341 schema: { type: string }
342 description: Vault-relative Markdown note path.
343 responses:
344 '200':
345 content:
346 application/json:
347 schema: { $ref: '#/components/schemas/NoteOutline' }
348 '400':
349 content:
350 application/json:
351 schema: { $ref: '#/components/schemas/Error' }
352 '401':
353 content:
354 application/json:
355 schema: { $ref: '#/components/schemas/Error' }
356 '403':
357 content:
358 application/json:
359 schema: { $ref: '#/components/schemas/Error' }
360 '404':
361 content:
362 application/json:
363 schema: { $ref: '#/components/schemas/Error' }
364 '502':
365 content:
366 application/json:
367 schema: { $ref: '#/components/schemas/Error' }
368
369 /document-tree:
370 get:
371 tags: [Notes]
372 summary: Body-free DocumentTree heading hierarchy for one note
373 description: >
374 Returns knowtation.document_tree/v0 metadata for one authorized vault-relative note.
375 The response excludes note body text, snippets, full frontmatter, absolute paths,
376 provider payloads, MCP resource URIs, summaries, vectors, OCR, PageIndex output,
377 persistence records, sidecars, LLM calls, and write-back state.
378 parameters:
379 - name: path
380 in: query
381 required: true
382 schema: { type: string }
383 description: Vault-relative Markdown note path.
384 responses:
385 '200':
386 content:
387 application/json:
388 schema: { $ref: '#/components/schemas/DocumentTree' }
389 '400':
390 content:
391 application/json:
392 schema: { $ref: '#/components/schemas/Error' }
393 '401':
394 content:
395 application/json:
396 schema: { $ref: '#/components/schemas/Error' }
397 '403':
398 content:
399 application/json:
400 schema: { $ref: '#/components/schemas/Error' }
401 '404':
402 content:
403 application/json:
404 schema: { $ref: '#/components/schemas/Error' }
405 '502':
406 content:
407 application/json:
408 schema: { $ref: '#/components/schemas/Error' }
409
410 /calendar/timeline:
411 get:
412 tags: [Calendar]
413 summary: Merged note-date and external-event timeline (self-hosted)
414 description: >
415 Returns knowtation.calendar_timeline/v0 items for an authorized vault.
416 Merges note-date buckets and stored calendar events. No OAuth tokens or connector secrets.
417 parameters:
418 - name: from
419 in: query
420 required: true
421 schema: { type: string }
422 description: Range start (YYYY-MM-DD or ISO8601).
423 - name: to
424 in: query
425 required: true
426 schema: { type: string }
427 description: Range end (YYYY-MM-DD or ISO8601).
428 - name: layers
429 in: query
430 required: false
431 schema: { type: string }
432 description: Comma-separated layers (`notes`, `events`). Default both.
433 - name: source_calendar_ids
434 in: query
435 required: false
436 schema: { type: string }
437 description: Comma-separated source calendar ids to include for the events layer.
438 responses:
439 '200':
440 content:
441 application/json:
442 schema: { $ref: '#/components/schemas/CalendarTimeline' }
443 '400':
444 content:
445 application/json:
446 schema: { $ref: '#/components/schemas/Error' }
447 '401':
448 content:
449 application/json:
450 schema: { $ref: '#/components/schemas/Error' }
451 '403':
452 content:
453 application/json:
454 schema: { $ref: '#/components/schemas/Error' }
455
456 /calendar/agent-context:
457 get:
458 tags: [Calendar]
459 summary: Tier-enforced calendar context for agents (self-hosted)
460 description: >
461 Returns knowtation.calendar_agent_context/v0 — redacted calendar events an agent
462 may see. Enforced server-side: calendars with enabled_for_agents=false contribute
463 nothing; per-calendar agent_context_tier_max and the org policy cap clamp the tier;
464 the v0 retrieval ceiling is tier 2. Agent visibility is independent of
465 enabled_for_display. Tier 1 omits the event summary; tier 0 returns no events.
466 Calendar text is untrusted prompt content.
467 parameters:
468 - name: from
469 in: query
470 required: true
471 schema: { type: string }
472 description: Range start (YYYY-MM-DD or ISO8601).
473 - name: to
474 in: query
475 required: true
476 schema: { type: string }
477 description: Range end (YYYY-MM-DD or ISO8601).
478 - name: agent_context_tier
479 in: query
480 required: true
481 schema: { type: integer, minimum: 0, maximum: 2 }
482 description: Requested agent tier (0 none, 1 busy blocks, 2 titles + label). Clamped by caps.
483 - name: source_calendar_ids
484 in: query
485 required: false
486 schema: { type: string }
487 description: Comma-separated source calendar ids to restrict the agent scope.
488 responses:
489 '200':
490 content:
491 application/json:
492 schema: { $ref: '#/components/schemas/CalendarAgentContext' }
493 '400':
494 content:
495 application/json:
496 schema: { $ref: '#/components/schemas/Error' }
497 '401':
498 content:
499 application/json:
500 schema: { $ref: '#/components/schemas/Error' }
501 '403':
502 content:
503 application/json:
504 schema: { $ref: '#/components/schemas/Error' }
505
506 /calendar/source-calendars:
507 get:
508 tags: [Calendar]
509 summary: List source calendars and display/agent toggles (self-hosted)
510 responses:
511 '200':
512 content:
513 application/json:
514 schema: { $ref: '#/components/schemas/SourceCalendarList' }
515 '401':
516 content:
517 application/json:
518 schema: { $ref: '#/components/schemas/Error' }
519 '403':
520 content:
521 application/json:
522 schema: { $ref: '#/components/schemas/Error' }
523
524 /calendar/source-calendars/{id}:
525 patch:
526 tags: [Calendar]
527 summary: Update source calendar display/agent toggles (self-hosted)
528 description: >
529 Partial update for enabled_for_display, enabled_for_agents, agent_context_tier_max (0–4),
530 and optional user_group. Org policy may cap agent_context_tier_max via
531 KNOWTATION_CALENDAR_AGENT_TIER_MAX_CAP or data/hub_calendar_policy.json.
532 parameters:
533 - name: id
534 in: path
535 required: true
536 schema: { type: string }
537 description: Source calendar id.
538 requestBody:
539 required: true
540 content:
541 application/json:
542 schema: { $ref: '#/components/schemas/SourceCalendarPatchRequest' }
543 responses:
544 '200':
545 content:
546 application/json:
547 schema: { $ref: '#/components/schemas/SourceCalendarPatchResult' }
548 '400':
549 content:
550 application/json:
551 schema: { $ref: '#/components/schemas/Error' }
552 '401':
553 content:
554 application/json:
555 schema: { $ref: '#/components/schemas/Error' }
556 '403':
557 content:
558 application/json:
559 schema: { $ref: '#/components/schemas/Error' }
560 '404':
561 content:
562 application/json:
563 schema: { $ref: '#/components/schemas/Error' }
564
565 /calendar/events/import:
566 post:
567 tags: [Calendar]
568 summary: Import ICS text into the local event store (read-only, self-hosted)
569 requestBody:
570 required: true
571 content:
572 application/json:
573 schema: { $ref: '#/components/schemas/CalendarIcsImportRequest' }
574 responses:
575 '200':
576 content:
577 application/json:
578 schema: { $ref: '#/components/schemas/CalendarIcsImportResult' }
579 '400':
580 content:
581 application/json:
582 schema: { $ref: '#/components/schemas/Error' }
583 '401':
584 content:
585 application/json:
586 schema: { $ref: '#/components/schemas/Error' }
587 '403':
588 content:
589 application/json:
590 schema: { $ref: '#/components/schemas/Error' }
591
592 /flows:
593 get:
594 tags: [Flows]
595 summary: List scope-visible flows (content-minimized)
596 description: >
597 Returns knowtation.flow_list/v0 summaries for flows visible in the caller's
598 authorized workspace scope. Scope query param narrows only — never widens.
599 Step bodies are never included in list responses.
600 parameters:
601 - name: scope
602 in: query
603 schema: { type: string, enum: [personal, project, org] }
604 description: Narrow within authorized scopes only.
605 - name: tag
606 in: query
607 schema: { type: string }
608 description: Filter by single tag membership.
609 - name: limit
610 in: query
611 schema: { type: integer, minimum: 1, maximum: 200 }
612 description: Max summaries (default 200).
613 responses:
614 '200':
615 content:
616 application/json:
617 schema: { $ref: '#/components/schemas/FlowListResponse' }
618 '400':
619 content:
620 application/json:
621 schema: { $ref: '#/components/schemas/Error' }
622 '401':
623 content:
624 application/json:
625 schema: { $ref: '#/components/schemas/Error' }
626 '403':
627 content:
628 application/json:
629 schema: { $ref: '#/components/schemas/Error' }
630 post:
631 tags: [Flows]
632 summary: Propose a new Flow (review-before-write)
633 description: >
634 Validates a knowtation.flow/v0 + flow_step/v0 bundle, resolves write
635 authority server-side (scope × role, deny-by-default), and creates a
636 standard proposal targeting the Flow's mirror note (SD-4). Returns a
637 knowtation.flow_proposal/v0 envelope (pointers/labels only). Gated by
638 FLOW_AUTHORING_WRITES — when off returns 403 FLOW_AUTHORING_DISABLED.
639 No Flow index write happens here; the index changes only at approve→apply.
640 requestBody:
641 required: true
642 content:
643 application/json:
644 schema: { $ref: '#/components/schemas/FlowProposeRequest' }
645 responses:
646 '201':
647 content:
648 application/json:
649 schema: { $ref: '#/components/schemas/FlowProposalResponse' }
650 '400':
651 content:
652 application/json:
653 schema: { $ref: '#/components/schemas/Error' }
654 '401':
655 content:
656 application/json:
657 schema: { $ref: '#/components/schemas/Error' }
658 '403':
659 content:
660 application/json:
661 schema: { $ref: '#/components/schemas/Error' }
662 '409':
663 content:
664 application/json:
665 schema: { $ref: '#/components/schemas/Error' }
666
667 /flows/import:
668 post:
669 tags: [Flows]
670 summary: Import a portable Flow bundle as a scope-checked proposal
671 description: >
672 Routes a portable { flow, steps } bundle through the same propose path.
673 The bundle scope is validated against the actor's write tier; unwritable
674 ⇒ 403 FLOW_IMPORT_SCOPE_DENIED, malformed ⇒ 400 FLOW_IMPORT_BUNDLE_MALFORMED.
675 Lineage pointers (external_ref / source_vault_hint) are preserved. Never
676 auto-applied — creates a proposed proposal. Gated by FLOW_AUTHORING_WRITES.
677 requestBody:
678 required: true
679 content:
680 application/json:
681 schema: { $ref: '#/components/schemas/FlowImportRequest' }
682 responses:
683 '201':
684 content:
685 application/json:
686 schema: { $ref: '#/components/schemas/FlowProposalResponse' }
687 '400':
688 content:
689 application/json:
690 schema: { $ref: '#/components/schemas/Error' }
691 '401':
692 content:
693 application/json:
694 schema: { $ref: '#/components/schemas/Error' }
695 '403':
696 content:
697 application/json:
698 schema: { $ref: '#/components/schemas/Error' }
699 '409':
700 content:
701 application/json:
702 schema: { $ref: '#/components/schemas/Error' }
703
704 /flows/capture/observe:
705 post:
706 tags: [Flows]
707 summary: Observe content-minimized session signals (capture detection)
708 description: >
709 Runs bounded structural detectors when FLOW_CAPTURE_DETECTION_ENABLED is on.
710 Creates/updates flow_candidate/v0 records; returns content-minimized summaries.
711 When detection is off, returns detection_authorized=false with no store mutation.
712 requestBody:
713 required: true
714 content:
715 application/json:
716 schema:
717 type: object
718 required: [session_id, step_sequence_refs, observed_counts]
719 responses:
720 '200':
721 description: Observe envelope
722 '400':
723 content:
724 application/json:
725 schema: { $ref: '#/components/schemas/Error' }
726 '403':
727 content:
728 application/json:
729 schema: { $ref: '#/components/schemas/Error' }
730
731 /flows/candidates:
732 get:
733 tags: [Flows]
734 summary: List flow capture candidates (read store)
735 description: Returns pending_review candidate summaries; read path does not require detection sub-gate.
736 parameters:
737 - name: scope
738 in: query
739 schema: { type: string, enum: [personal, project, org] }
740 - name: include_low_confidence
741 in: query
742 schema: { type: boolean }
743 - name: limit
744 in: query
745 schema: { type: integer, minimum: 1, maximum: 50 }
746 responses:
747 '200':
748 description: Candidate list envelope
749 '400':
750 content:
751 application/json:
752 schema: { $ref: '#/components/schemas/Error' }
753
754 /flows/candidates/{candidate_id}/propose:
755 post:
756 tags: [Flows]
757 summary: Propose candidate promotion (review-before-write)
758 description: >
759 Creates a flow_candidate_promote or flow_candidate_merge proposal.
760 Gated by FLOW_CAPTURE_WRITES_ENABLED (default off).
761 parameters:
762 - name: candidate_id
763 in: path
764 required: true
765 schema: { type: string }
766 requestBody:
767 required: true
768 content:
769 application/json:
770 schema:
771 type: object
772 required: [confirmed_scope, intent]
773 responses:
774 '201':
775 description: Capture proposal envelope
776 '403':
777 content:
778 application/json:
779 schema: { $ref: '#/components/schemas/Error' }
780 '404':
781 content:
782 application/json:
783 schema: { $ref: '#/components/schemas/Error' }
784 '409':
785 content:
786 application/json:
787 schema: { $ref: '#/components/schemas/Error' }
788
789 /flows/candidates/{candidate_id}/dismiss:
790 post:
791 tags: [Flows]
792 summary: Propose candidate dismissal
793 description: >
794 Creates a flow_candidate_dismiss proposal; on approve candidate status becomes rejected.
795 Gated by FLOW_CAPTURE_WRITES_ENABLED (default off).
796 parameters:
797 - name: candidate_id
798 in: path
799 required: true
800 schema: { type: string }
801 requestBody:
802 required: true
803 content:
804 application/json:
805 schema:
806 type: object
807 required: [intent]
808 responses:
809 '201':
810 description: Capture proposal envelope
811 '403':
812 content:
813 application/json:
814 schema: { $ref: '#/components/schemas/Error' }
815 '404':
816 content:
817 application/json:
818 schema: { $ref: '#/components/schemas/Error' }
819
820 /flows/{id}/proposals:
821 post:
822 tags: [Flows]
823 summary: Propose an edit to an existing Flow (review-before-write)
824 description: >
825 Like POST /flows but for an edit. Requires base_version + base_state_id
826 (the flowst1_ optimistic-concurrency token); a mismatch at propose or
827 approve time ⇒ 409 FLOW_LINEAGE_CONFLICT. flow.version must be strictly
828 greater than base_version. Editing a flow the actor cannot read ⇒ 404
829 unknown_flow (no existence leak). Gated by FLOW_AUTHORING_WRITES.
830 parameters:
831 - name: id
832 in: path
833 required: true
834 schema: { type: string }
835 description: Flow id (flow_<slug>); must match the bundle's flow_id.
836 requestBody:
837 required: true
838 content:
839 application/json:
840 schema: { $ref: '#/components/schemas/FlowProposeEditRequest' }
841 responses:
842 '201':
843 content:
844 application/json:
845 schema: { $ref: '#/components/schemas/FlowProposalResponse' }
846 '400':
847 content:
848 application/json:
849 schema: { $ref: '#/components/schemas/Error' }
850 '401':
851 content:
852 application/json:
853 schema: { $ref: '#/components/schemas/Error' }
854 '403':
855 content:
856 application/json:
857 schema: { $ref: '#/components/schemas/Error' }
858 '404':
859 content:
860 application/json:
861 schema: { $ref: '#/components/schemas/Error' }
862 '409':
863 content:
864 application/json:
865 schema: { $ref: '#/components/schemas/Error' }
866
867 /flows/{id}/projection:
868 get:
869 tags: [Flows]
870 summary: Derive a read-only harness projection of a canonical flow
871 description: >
872 Renders the canonical flow (latest visible, or pinned ?version) into the requested
873 harness as knowtation.flow_project/v0. Derived and read-only — generated_from_canonical
874 is always true and editable is always false. No secrets appear in rendered text.
875 parameters:
876 - name: id
877 in: path
878 required: true
879 schema: { type: string }
880 - name: harness
881 in: query
882 required: true
883 schema:
884 type: string
885 enum: [cursor_rule, cursor_skill, mcp_prompt, cli_runbook, agent_bundle]
886 - name: version
887 in: query
888 schema: { type: string }
889 responses:
890 '200':
891 content:
892 application/json:
893 schema: { $ref: '#/components/schemas/FlowProjectResponse' }
894 '400':
895 content:
896 application/json:
897 schema: { $ref: '#/components/schemas/Error' }
898 '401':
899 content:
900 application/json:
901 schema: { $ref: '#/components/schemas/Error' }
902 '403':
903 content:
904 application/json:
905 schema: { $ref: '#/components/schemas/Error' }
906 '404':
907 content:
908 application/json:
909 schema: { $ref: '#/components/schemas/Error' }
910
911 /flows/{id}/external-grants:
912 post:
913 tags: [Flows]
914 summary: Mint a short-lived external-agent grant (gated; default off)
915 description: >
916 Mints knowtation.flow_external_grant/v0 for a pinned flow version and requested tools.
917 Returns a one-time bearer at mint only. Requires FLOW_EXTERNAL_AGENT_ENABLED.
918 parameters:
919 - name: id
920 in: path
921 required: true
922 schema: { type: string }
923 requestBody:
924 required: true
925 content:
926 application/json:
927 schema: { $ref: '#/components/schemas/FlowExternalGrantMintRequest' }
928 responses:
929 '201':
930 content:
931 application/json:
932 schema: { $ref: '#/components/schemas/FlowExternalGrantMintResponse' }
933 '400':
934 content:
935 application/json:
936 schema: { $ref: '#/components/schemas/Error' }
937 '403':
938 content:
939 application/json:
940 schema: { $ref: '#/components/schemas/Error' }
941 '404':
942 content:
943 application/json:
944 schema: { $ref: '#/components/schemas/Error' }
945
946 /flows/external-grants:
947 get:
948 tags: [Flows]
949 summary: List external-agent grant metadata (no bearer)
950 parameters:
951 - name: flow_id
952 in: query
953 schema: { type: string }
954 responses:
955 '200':
956 content:
957 application/json:
958 schema: { $ref: '#/components/schemas/FlowExternalGrantListResponse' }
959 '403':
960 content:
961 application/json:
962 schema: { $ref: '#/components/schemas/Error' }
963
964 /flows/external-grants/{grant_id}:
965 delete:
966 tags: [Flows]
967 summary: Revoke an external-agent grant
968 parameters:
969 - name: grant_id
970 in: path
971 required: true
972 schema: { type: string }
973 responses:
974 '200':
975 content:
976 application/json:
977 schema: { $ref: '#/components/schemas/FlowExternalGrant' }
978 '403':
979 content:
980 application/json:
981 schema: { $ref: '#/components/schemas/Error' }
982 '404':
983 content:
984 application/json:
985 schema: { $ref: '#/components/schemas/Error' }
986
987 /tasks:
988 get:
989 tags: [Tasks]
990 summary: List scope-visible tasks (content-minimized)
991 description: >
992 Returns knowtation.task_list/v0 summaries for tasks visible in the caller's
993 authorized workspace scope. Scope query param narrows only — never widens.
994 List responses never include assignee refs or artifact_links.
995 parameters:
996 - name: scope
997 in: query
998 schema: { type: string, enum: [personal, project, org] }
999 description: Narrow within authorized scopes only.
1000 - name: workspace_id
1001 in: query
1002 schema: { type: string }
1003 description: Filter by workspace_id equality.
1004 - name: status
1005 in: query
1006 schema:
1007 type: string
1008 enum: [pending, in_progress, blocked, done, cancelled]
1009 - name: kind
1010 in: query
1011 schema:
1012 type: string
1013 enum: [personal, assignment, mentor_checkin, org_work_job]
1014 - name: limit
1015 in: query
1016 schema: { type: integer, minimum: 1, maximum: 500 }
1017 description: Max summaries (default 500).
1018 responses:
1019 '200':
1020 content:
1021 application/json:
1022 schema: { $ref: '#/components/schemas/TaskListResponse' }
1023 '400':
1024 content:
1025 application/json:
1026 schema: { $ref: '#/components/schemas/Error' }
1027 '401':
1028 content:
1029 application/json:
1030 schema: { $ref: '#/components/schemas/Error' }
1031 '403':
1032 content:
1033 application/json:
1034 schema: { $ref: '#/components/schemas/Error' }
1035
1036 /tasks/{id}:
1037 get:
1038 tags: [Tasks]
1039 summary: Get one authorized task
1040 description: >
1041 Returns knowtation.task_get/v0 with the full task record when the caller
1042 is authorized for the task scope. Missing or invisible tasks return 404
1043 unknown_task (no existence leak).
1044 parameters:
1045 - name: id
1046 in: path
1047 required: true
1048 schema: { type: string }
1049 responses:
1050 '200':
1051 content:
1052 application/json:
1053 schema: { $ref: '#/components/schemas/TaskGetResponse' }
1054 '400':
1055 content:
1056 application/json:
1057 schema: { $ref: '#/components/schemas/Error' }
1058 '401':
1059 content:
1060 application/json:
1061 schema: { $ref: '#/components/schemas/Error' }
1062 '403':
1063 content:
1064 application/json:
1065 schema: { $ref: '#/components/schemas/Error' }
1066 '404':
1067 content:
1068 application/json:
1069 schema: { $ref: '#/components/schemas/Error' }
1070
1071 /learning-paths:
1072 get:
1073 tags: [LearningPaths]
1074 summary: List scope-visible learning paths (content-minimized)
1075 description: >
1076 Returns knowtation.learning_path_list/v0 summaries. JWT + vault; no write gate.
1077 Default omits archived. Empty list is paths: [] (never a fabricated sample).
1078 PATH_WRITES_ENABLED does not affect this read.
1079 parameters:
1080 - name: scope
1081 in: query
1082 schema: { type: string, enum: [personal, project, org] }
1083 - name: workspace_id
1084 in: query
1085 schema: { type: string }
1086 - name: status
1087 in: query
1088 schema: { type: string, enum: [active, paused, archived] }
1089 - name: limit
1090 in: query
1091 schema: { type: integer, minimum: 1, maximum: 200 }
1092 description: Max summaries (default 200; invalid treated as 200).
1093 responses:
1094 '200':
1095 content:
1096 application/json:
1097 schema: { $ref: '#/components/schemas/LearningPathListResponse' }
1098 '400':
1099 content:
1100 application/json:
1101 schema: { $ref: '#/components/schemas/Error' }
1102 '401':
1103 content:
1104 application/json:
1105 schema: { $ref: '#/components/schemas/Error' }
1106 '403':
1107 content:
1108 application/json:
1109 schema: { $ref: '#/components/schemas/Error' }
1110
1111 /learning-paths/{path_id}:
1112 get:
1113 tags: [LearningPaths]
1114 summary: Get one authorized learning path
1115 description: >
1116 Missing, invalid path_id, or out-of-scope returns 404 PATH_NOT_FOUND (no existence leak).
1117 Archived paths still return when authorized.
1118 parameters:
1119 - name: path_id
1120 in: path
1121 required: true
1122 schema: { type: string }
1123 responses:
1124 '200':
1125 content:
1126 application/json:
1127 schema: { $ref: '#/components/schemas/LearningPathGetResponse' }
1128 '401':
1129 content:
1130 application/json:
1131 schema: { $ref: '#/components/schemas/Error' }
1132 '403':
1133 content:
1134 application/json:
1135 schema: { $ref: '#/components/schemas/Error' }
1136 '404':
1137 content:
1138 application/json:
1139 schema: { $ref: '#/components/schemas/Error' }
1140
1141 /learning-paths/proposals:
1142 post:
1143 tags: [LearningPaths]
1144 summary: Propose a learning-path write (SD-4; gated; default off)
1145 description: >
1146 path_create, path_update, or path_archive. Missing kind defaults to path_create.
1147 Requires PATH_WRITES_ENABLED (default off). Propose only — apply stays after approve.
1148 Path kinds are not admitted to personal self-apply (T5).
1149 requestBody:
1150 required: true
1151 content:
1152 application/json:
1153 schema: { $ref: '#/components/schemas/LearningPathProposalRequest' }
1154 responses:
1155 '201':
1156 content:
1157 application/json:
1158 schema: { $ref: '#/components/schemas/LearningPathProposalResponse' }
1159 '400':
1160 content:
1161 application/json:
1162 schema: { $ref: '#/components/schemas/Error' }
1163 '403':
1164 content:
1165 application/json:
1166 schema: { $ref: '#/components/schemas/Error' }
1167 '404':
1168 content:
1169 application/json:
1170 schema: { $ref: '#/components/schemas/Error' }
1171
1172 /attachments:
1173 get:
1174 tags: [Attachments]
1175 summary: List scope-visible attachments (content-minimized)
1176 description: >
1177 Returns knowtation.attachment_list/v0 summaries for attachments visible in
1178 the caller's authorized workspace scope. Scope query param narrows only — never widens.
1179 List responses never include linked_note_refs, byte_size, mime_type, or agent_visible.
1180 On hosted gateway→bridge (SEC-SEAM-MEDIA), connector_ref rows from
1181 hub_attachment_external_refs.json are included after media external-link apply.
1182 parameters:
1183 - name: scope
1184 in: query
1185 schema: { type: string, enum: [personal, project, org] }
1186 description: Narrow within authorized scopes only.
1187 - name: note_ref
1188 in: query
1189 schema: { type: string }
1190 description: Filter attachments linked to a specific note (note:path).
1191 - name: source
1192 in: query
1193 schema:
1194 type: string
1195 enum: [vault_file, mist_blob, embedded_url, connector_ref]
1196 - name: mime_class
1197 in: query
1198 schema:
1199 type: string
1200 enum: [image, video, audio, document, unknown]
1201 - name: storage_kind
1202 in: query
1203 schema:
1204 type: string
1205 enum: [vault_blob, external_link]
1206 - name: agent_visible
1207 in: query
1208 schema: { type: boolean }
1209 description: When true, return only attachments with agent_visible consent.
1210 - name: limit
1211 in: query
1212 schema: { type: integer, minimum: 1, maximum: 500 }
1213 description: Max summaries (default 500).
1214 responses:
1215 '200':
1216 content:
1217 application/json:
1218 schema: { $ref: '#/components/schemas/AttachmentListResponse' }
1219 '400':
1220 content:
1221 application/json:
1222 schema: { $ref: '#/components/schemas/Error' }
1223 '401':
1224 content:
1225 application/json:
1226 schema: { $ref: '#/components/schemas/Error' }
1227 '403':
1228 content:
1229 application/json:
1230 schema: { $ref: '#/components/schemas/Error' }
1231
1232 '404':
1233 content:
1234 application/json:
1235 schema: { $ref: '#/components/schemas/Error' }
1236
1237 /attachments/link-proposals:
1238 post:
1239 tags: [Attachments]
1240 summary: Propose an external media link (review-before-write)
1241 description: >
1242 Creates a media_external_link proposal. Gated by MEDIA_EXTERNAL_LINK_ENABLED (default off).
1243 Requires an active import consent and allowlisted connector. Never fetches opaque_ref.
1244 Available on self-hosted Hub and on hosted gateway→bridge (SEC-SEAM-MEDIA) when the
1245 same gate is enabled; hosted creates the proposal on the canister proposal store.
1246 requestBody:
1247 required: true
1248 content:
1249 application/json:
1250 schema:
1251 type: object
1252 required: [intent, scope, connector_id, opaque_ref, consent_id]
1253 properties:
1254 intent: { type: string }
1255 scope: { type: string, enum: [personal, project, org] }
1256 connector_id: { type: string }
1257 opaque_ref: { type: string }
1258 consent_id: { type: string }
1259 display_label: { type: string }
1260 responses:
1261 '201':
1262 content:
1263 application/json:
1264 schema: { $ref: '#/components/schemas/MediaProposalResponse' }
1265 '403':
1266 content:
1267 application/json:
1268 schema: { $ref: '#/components/schemas/Error' }
1269
1270 /attachments/attach-proposals:
1271 post:
1272 tags: [Attachments]
1273 summary: Propose attaching media to a note (review-before-write)
1274 description: >
1275 Creates a media_attach proposal. Gated by MEDIA_ATTACH_ENABLED (default off).
1276 Available on self-hosted Hub and on hosted gateway→bridge (SEC-SEAM-MEDIA) when the
1277 same gate is enabled. Hosted propose stamps media_pointer onto the canister row so
1278 apply does not require a vault-wide mist walk on the bridge.
1279 requestBody:
1280 required: true
1281 content:
1282 application/json:
1283 schema:
1284 type: object
1285 required: [intent, scope, attachment_id, note_ref, base_state_id]
1286 properties:
1287 intent: { type: string }
1288 scope: { type: string, enum: [personal, project, org] }
1289 attachment_id: { type: string }
1290 note_ref: { type: string }
1291 base_state_id: { type: string }
1292 responses:
1293 '201':
1294 content:
1295 application/json:
1296 schema: { $ref: '#/components/schemas/MediaProposalResponse' }
1297 '403':
1298 content:
1299 application/json:
1300 schema: { $ref: '#/components/schemas/Error' }
1301
1302 /attachments/import-consents:
1303 get:
1304 tags: [Attachments]
1305 summary: List import consents (read-only)
1306 parameters:
1307 - name: scope
1308 in: query
1309 schema: { type: string, enum: [personal, project, org] }
1310 responses:
1311 '200':
1312 content:
1313 application/json:
1314 schema:
1315 type: object
1316 required: [schema, vault_id, consents]
1317 properties:
1318 schema:
1319 type: string
1320 enum: [knowtation.media_import_consent_list/v0]
1321 vault_id: { type: string }
1322 consents:
1323 type: array
1324 items:
1325 type: object
1326 post:
1327 tags: [Attachments]
1328 summary: Grant import consent for external linking
1329 description: Requires MEDIA_EXTERNAL_LINK_ENABLED. Not exposed as MCP write tool.
1330 requestBody:
1331 required: true
1332 content:
1333 application/json:
1334 schema:
1335 type: object
1336 required: [connector_id, scope]
1337 properties:
1338 connector_id: { type: string }
1339 scope: { type: string, enum: [personal, project, org] }
1340 expires_at: { type: [string, 'null'] }
1341 responses:
1342 '201':
1343 content:
1344 application/json:
1345 schema:
1346 type: object
1347 delete:
1348 tags: [Attachments]
1349 summary: Revoke import consent (not supported at collection path)
1350 responses:
1351 '405':
1352 content:
1353 application/json:
1354 schema: { $ref: '#/components/schemas/Error' }
1355
1356 /attachments/import-consents/{id}:
1357 delete:
1358 tags: [Attachments]
1359 summary: Revoke an import consent by id
1360 parameters:
1361 - name: id
1362 in: path
1363 required: true
1364 schema: { type: string }
1365 responses:
1366 '200':
1367 content:
1368 application/json:
1369 schema:
1370 type: object
1371 '404':
1372 content:
1373 application/json:
1374 schema: { $ref: '#/components/schemas/Error' }
1375
1376 /attachments/proposals/{proposal_id}/apply-approved:
1377 post:
1378 tags: [Attachments]
1379 summary: Apply an approved media proposal (hosted Hub-complete / ops recovery)
1380 description: >
1381 Runs the shared media precheck + reconcile against bridge dataDir stores
1382 (and canister note RMW for media_attach). Requires proposal status approved
1383 (409 CONFLICT otherwise). The mandatory client path is the gateway post-approve
1384 hook (maybeApplyHostedMediaAfterApprove); this route is the ops recovery surface
1385 and the hook's bridge target (SEC-SEAM-MEDIA SM-C4 / SM-C12). Self-hosted Hub
1386 applies on approve without this route.
1387 parameters:
1388 - name: proposal_id
1389 in: path
1390 required: true
1391 schema: { type: string }
1392 responses:
1393 '200':
1394 content:
1395 application/json:
1396 schema:
1397 type: object
1398 required: [applied, proposal_id, vault_id, proposal_kind]
1399 properties:
1400 applied: { type: boolean, enum: [true] }
1401 proposal_id: { type: string }
1402 vault_id: { type: string }
1403 proposal_kind:
1404 type: string
1405 enum: [media_external_link, media_attach]
1406 attachment_id: { type: string }
1407 connector_id: { type: ['string', 'null'] }
1408 note_ref: { type: string }
1409 '400':
1410 content:
1411 application/json:
1412 schema: { $ref: '#/components/schemas/Error' }
1413 '403':
1414 content:
1415 application/json:
1416 schema: { $ref: '#/components/schemas/Error' }
1417 '404':
1418 content:
1419 application/json:
1420 schema: { $ref: '#/components/schemas/Error' }
1421 '409':
1422 content:
1423 application/json:
1424 schema: { $ref: '#/components/schemas/Error' }
1425
1426 /attachments/{id}:
1427 get:
1428 tags: [Attachments]
1429 summary: Get one authorized attachment
1430 description: >
1431 Returns knowtation.attachment_get/v0 with the full attachment record when
1432 the caller is authorized. Missing or invisible attachments return 404
1433 unknown_attachment (no existence leak). On hosted gateway→bridge, connector_ref
1434 rows derived from hub_attachment_external_refs.json are visible after media
1435 external-link apply (blob-backed stores).
1436 parameters:
1437 - name: id
1438 in: path
1439 required: true
1440 schema: { type: string }
1441 responses:
1442 '200':
1443 content:
1444 application/json:
1445 schema: { $ref: '#/components/schemas/AttachmentGetResponse' }
1446 '400':
1447 content:
1448 application/json:
1449 schema: { $ref: '#/components/schemas/Error' }
1450 '401':
1451 content:
1452 application/json:
1453 schema: { $ref: '#/components/schemas/Error' }
1454 '403':
1455 content:
1456 application/json:
1457 schema: { $ref: '#/components/schemas/Error' }
1458 '404':
1459 content:
1460 application/json:
1461 schema: { $ref: '#/components/schemas/Error' }
1462
1463 /tasks/proposals:
1464 post:
1465 tags: [Tasks]
1466 summary: Propose a one-time task write (SD-4; gated; default off)
1467 description: >
1468 Typed facade over /proposals for task_create, task_status_update, task_assign,
1469 and task_artifact_link. Requires TASK_WRITES_ENABLED (default off).
1470 requestBody:
1471 required: true
1472 content:
1473 application/json:
1474 schema: { $ref: '#/components/schemas/TaskWriteProposalRequest' }
1475 responses:
1476 '201':
1477 content:
1478 application/json:
1479 schema: { $ref: '#/components/schemas/TaskProposalResponse' }
1480 '403':
1481 content:
1482 application/json:
1483 schema: { $ref: '#/components/schemas/Error' }
1484 '409':
1485 content:
1486 application/json:
1487 schema: { $ref: '#/components/schemas/Error' }
1488
1489 /task-loops/proposals:
1490 post:
1491 tags: [Tasks]
1492 summary: Propose a task loop series write (SD-4; gated; default off)
1493 description: >
1494 task_loop_create, task_loop_pause, or task_loop_cancel proposal. Requires TASK_WRITES_ENABLED.
1495 requestBody:
1496 required: true
1497 content:
1498 application/json:
1499 schema: { $ref: '#/components/schemas/TaskLoopWriteProposalRequest' }
1500 responses:
1501 '201':
1502 content:
1503 application/json:
1504 schema: { $ref: '#/components/schemas/TaskProposalResponse' }
1505 '403':
1506 content:
1507 application/json:
1508 schema: { $ref: '#/components/schemas/Error' }
1509
1510 /task-loops/{loop_id}/instances/proposals:
1511 post:
1512 tags: [Tasks]
1513 summary: Propose materializing one loop occurrence task (SD-4; gated; default off)
1514 parameters:
1515 - name: loop_id
1516 in: path
1517 required: true
1518 schema: { type: string }
1519 requestBody:
1520 required: true
1521 content:
1522 application/json:
1523 schema: { $ref: '#/components/schemas/TaskInstanceMaterializeRequest' }
1524 responses:
1525 '201':
1526 content:
1527 application/json:
1528 schema: { $ref: '#/components/schemas/TaskInstanceProposalResponse' }
1529 '403':
1530 content:
1531 application/json:
1532 schema: { $ref: '#/components/schemas/Error' }
1533 '409':
1534 content:
1535 application/json:
1536 schema: { $ref: '#/components/schemas/Error' }
1537
1538 /agents/identities:
1539 post:
1540 tags: [Delegation]
1541 summary: Propose agent identity registration (SD-4; gated; default off)
1542 description: >
1543 Creates an SD-4 proposal with intent agent_identity_register. Requires DELEGATION_ENABLED.
1544 requestBody:
1545 required: true
1546 content:
1547 application/json:
1548 schema: { $ref: '#/components/schemas/AgentIdentityRegisterRequest' }
1549 responses:
1550 '201':
1551 content:
1552 application/json:
1553 schema: { $ref: '#/components/schemas/DelegationProposalResponse' }
1554 '403':
1555 content:
1556 application/json:
1557 schema: { $ref: '#/components/schemas/Error' }
1558 get:
1559 tags: [Delegation]
1560 summary: List agent identities (gated; default off)
1561 parameters:
1562 - name: kind
1563 in: query
1564 schema:
1565 type: string
1566 enum: [user_owned, org_owned, delegate]
1567 - name: status
1568 in: query
1569 schema:
1570 type: string
1571 enum: [active, suspended, revoked]
1572 responses:
1573 '200':
1574 content:
1575 application/json:
1576 schema: { $ref: '#/components/schemas/AgentIdentityListResponse' }
1577 '403':
1578 content:
1579 application/json:
1580 schema: { $ref: '#/components/schemas/Error' }
1581
1582 /delegation/consents:
1583 post:
1584 tags: [Delegation]
1585 summary: Propose delegation consent (SD-4; gated; default off)
1586 requestBody:
1587 required: true
1588 content:
1589 application/json:
1590 schema: { $ref: '#/components/schemas/DelegationConsentProposeRequest' }
1591 responses:
1592 '201':
1593 content:
1594 application/json:
1595 schema: { $ref: '#/components/schemas/DelegationConsentProposeResponse' }
1596 '403':
1597 content:
1598 application/json:
1599 schema: { $ref: '#/components/schemas/Error' }
1600
1601 /delegation/consents/{consent_id}:
1602 delete:
1603 tags: [Delegation]
1604 summary: Revoke delegation consent
1605 parameters:
1606 - name: consent_id
1607 in: path
1608 required: true
1609 schema: { type: string }
1610 responses:
1611 '200':
1612 content:
1613 application/json:
1614 schema: { $ref: '#/components/schemas/DelegationConsent' }
1615 '403':
1616 content:
1617 application/json:
1618 schema: { $ref: '#/components/schemas/Error' }
1619 '404':
1620 content:
1621 application/json:
1622 schema: { $ref: '#/components/schemas/Error' }
1623
1624 /delegation/grants:
1625 post:
1626 tags: [Delegation]
1627 summary: Mint short-lived delegation grant (gated; default off)
1628 requestBody:
1629 required: true
1630 content:
1631 application/json:
1632 schema: { $ref: '#/components/schemas/DelegationGrantMintRequest' }
1633 responses:
1634 '201':
1635 content:
1636 application/json:
1637 schema: { $ref: '#/components/schemas/DelegationGrantMintResponse' }
1638 '403':
1639 content:
1640 application/json:
1641 schema: { $ref: '#/components/schemas/Error' }
1642 '404':
1643 content:
1644 application/json:
1645 schema: { $ref: '#/components/schemas/Error' }
1646 get:
1647 tags: [Delegation]
1648 summary: List delegation grant metadata (no bearer)
1649 parameters:
1650 - name: actor_agent_id
1651 in: query
1652 schema: { type: string }
1653 responses:
1654 '200':
1655 content:
1656 application/json:
1657 schema: { $ref: '#/components/schemas/DelegationGrantListResponse' }
1658 '403':
1659 content:
1660 application/json:
1661 schema: { $ref: '#/components/schemas/Error' }
1662
1663 /delegation/grants/{grant_id}:
1664 delete:
1665 tags: [Delegation]
1666 summary: Revoke delegation grant
1667 parameters:
1668 - name: grant_id
1669 in: path
1670 required: true
1671 schema: { type: string }
1672 responses:
1673 '200':
1674 content:
1675 application/json:
1676 schema: { $ref: '#/components/schemas/DelegationGrant' }
1677 '403':
1678 content:
1679 application/json:
1680 schema: { $ref: '#/components/schemas/Error' }
1681 '404':
1682 content:
1683 application/json:
1684 schema: { $ref: '#/components/schemas/Error' }
1685
1686 /delegation/audit:
1687 post:
1688 tags: [Delegation]
1689 summary: Append delegation audit entry (pointer-safe)
1690 requestBody:
1691 required: true
1692 content:
1693 application/json:
1694 schema: { $ref: '#/components/schemas/DelegationAuditAppendRequest' }
1695 responses:
1696 '201':
1697 content:
1698 application/json:
1699 schema: { $ref: '#/components/schemas/DelegationAudit' }
1700 '403':
1701 content:
1702 application/json:
1703 schema: { $ref: '#/components/schemas/Error' }
1704
1705 /flows/{id}:
1706 get:
1707 tags: [Flows]
1708 summary: Get one flow definition + ordered steps
1709 description: >
1710 Returns knowtation.flow_get/v0 with full flow definition and steps in ascending
1711 ordinal order. Missing and scope-invisible flows both return 404 unknown_flow.
1712 Step text is untrusted input — returned verbatim as data.
1713 parameters:
1714 - name: id
1715 in: path
1716 required: true
1717 schema: { type: string }
1718 description: Flow id (flow_<slug>).
1719 - name: version
1720 in: query
1721 schema: { type: string }
1722 description: Pin semver version; default latest visible.
1723 responses:
1724 '200':
1725 content:
1726 application/json:
1727 schema: { $ref: '#/components/schemas/FlowGetResponse' }
1728 '400':
1729 content:
1730 application/json:
1731 schema: { $ref: '#/components/schemas/Error' }
1732 '401':
1733 content:
1734 application/json:
1735 schema: { $ref: '#/components/schemas/Error' }
1736 '403':
1737 content:
1738 application/json:
1739 schema: { $ref: '#/components/schemas/Error' }
1740 '404':
1741 content:
1742 application/json:
1743 schema: { $ref: '#/components/schemas/Error' }
1744
1745 /flow-runs/{run_id}:
1746 get:
1747 tags: [Flows]
1748 summary: Get one flow run by run id or portable run_ref
1749 description: >
1750 Returns knowtation.flow_run/v0 for a scope-visible run. Accepts canonical
1751 run_id (run_…) or portable run_ref (flow_run:…). Missing and
1752 scope-invisible runs both return 404 unknown_run.
1753 parameters:
1754 - name: run_id
1755 in: path
1756 required: true
1757 schema: { type: string }
1758 responses:
1759 '200':
1760 content:
1761 application/json:
1762 schema: { $ref: '#/components/schemas/FlowRunResponse' }
1763 '404':
1764 content:
1765 application/json:
1766 schema: { $ref: '#/components/schemas/Error' }
1767
1768 /flows/{id}/runs:
1769 get:
1770 tags: [Flows]
1771 summary: List runs for a flow
1772 parameters:
1773 - name: id
1774 in: path
1775 required: true
1776 schema: { type: string }
1777 responses:
1778 '200':
1779 content:
1780 application/json:
1781 schema: { $ref: '#/components/schemas/FlowRunListResponse' }
1782 post:
1783 tags: [Flows]
1784 summary: Start a flow run
1785 description: >
1786 Gated by FLOW_RUN_WRITES_ENABLED (default off). Pins flow_version for the run life.
1787 parameters:
1788 - name: id
1789 in: path
1790 required: true
1791 schema: { type: string }
1792 requestBody:
1793 required: true
1794 content:
1795 application/json:
1796 schema:
1797 type: object
1798 required: [flow_version]
1799 properties:
1800 flow_version: { type: string }
1801 task_ref: { type: string }
1802 external_ref: { type: string }
1803 responses:
1804 '201':
1805 content:
1806 application/json:
1807 schema: { $ref: '#/components/schemas/FlowRunStartResponse' }
1808 '403':
1809 content:
1810 application/json:
1811 schema: { $ref: '#/components/schemas/Error' }
1812
1813 /flows/{id}/runs/{run_id}:
1814 get:
1815 tags: [Flows]
1816 summary: Get one flow run
1817 parameters:
1818 - name: id
1819 in: path
1820 required: true
1821 schema: { type: string }
1822 - name: run_id
1823 in: path
1824 required: true
1825 schema: { type: string }
1826 responses:
1827 '200':
1828 content:
1829 application/json:
1830 schema: { $ref: '#/components/schemas/FlowRunResponse' }
1831 post:
1832 tags: [Flows]
1833 summary: Advance, record evidence, execute automatable, or submit review
1834 description: >
1835 Use dedicated sub-paths (/advance, /evidence, /execute-automatable, /submit-review).
1836 Run writes gated by FLOW_RUN_WRITES_ENABLED; automatable by FLOW_AUTOMATABLE_EXECUTION_ENABLED.
1837
1838 /flows/{id}/runs/{run_id}/advance:
1839 post:
1840 tags: [Flows]
1841 summary: Advance a step manually
1842 parameters:
1843 - name: id
1844 in: path
1845 required: true
1846 schema: { type: string }
1847 - name: run_id
1848 in: path
1849 required: true
1850 schema: { type: string }
1851 requestBody:
1852 required: true
1853 content:
1854 application/json:
1855 schema:
1856 type: object
1857 required: [step_id, to_status]
1858 properties:
1859 step_id: { type: string }
1860 to_status: { type: string }
1861 skip_reason: { type: string }
1862 responses:
1863 '200':
1864 content:
1865 application/json:
1866 schema: { $ref: '#/components/schemas/FlowRunResponse' }
1867
1868 /flows/{id}/runs/{run_id}/evidence:
1869 post:
1870 tags: [Flows]
1871 summary: Record evidence pointer on a step
1872 parameters:
1873 - name: id
1874 in: path
1875 required: true
1876 schema: { type: string }
1877 - name: run_id
1878 in: path
1879 required: true
1880 schema: { type: string }
1881 requestBody:
1882 required: true
1883 content:
1884 application/json:
1885 schema:
1886 type: object
1887 required: [step_id, evidence_ref, pointer_kind]
1888 properties:
1889 step_id: { type: string }
1890 evidence_ref: { type: string }
1891 pointer_kind: { type: string }
1892 responses:
1893 '200':
1894 content:
1895 application/json:
1896 schema: { $ref: '#/components/schemas/FlowRunResponse' }
1897
1898 /flows/{id}/runs/{run_id}/execute-automatable:
1899 post:
1900 tags: [Flows]
1901 summary: Execute an automatable step (server orchestration stub)
1902 description: Requires valid knowtation.flow_execution_consent/v0. Gated by FLOW_AUTOMATABLE_EXECUTION_ENABLED.
1903 parameters:
1904 - name: id
1905 in: path
1906 required: true
1907 schema: { type: string }
1908 - name: run_id
1909 in: path
1910 required: true
1911 schema: { type: string }
1912 requestBody:
1913 required: true
1914 content:
1915 application/json:
1916 schema:
1917 type: object
1918 required: [step_id, consent_id]
1919 properties:
1920 step_id: { type: string }
1921 consent_id: { type: string }
1922 model_lane: { type: string }
1923 dry_run: { type: boolean }
1924 responses:
1925 '200':
1926 content:
1927 application/json:
1928 schema: { $ref: '#/components/schemas/FlowExecuteAutomatableResponse' }
1929
1930 /flows/{id}/runs/{run_id}/submit-review:
1931 post:
1932 tags: [Flows]
1933 summary: Submit run outcome to review tray
1934 parameters:
1935 - name: id
1936 in: path
1937 required: true
1938 schema: { type: string }
1939 - name: run_id
1940 in: path
1941 required: true
1942 schema: { type: string }
1943 requestBody:
1944 required: true
1945 content:
1946 application/json:
1947 schema:
1948 type: object
1949 required: [intent]
1950 properties:
1951 intent: { type: string }
1952 responses:
1953 '200':
1954 content:
1955 application/json:
1956 schema: { $ref: '#/components/schemas/FlowRunSubmitReviewResponse' }
1957
1958 /flows/{id}/runs/{run_id}/consent:
1959 post:
1960 tags: [Flows]
1961 summary: Mint execution consent for automatable steps
1962 parameters:
1963 - name: id
1964 in: path
1965 required: true
1966 schema: { type: string }
1967 - name: run_id
1968 in: path
1969 required: true
1970 schema: { type: string }
1971 requestBody:
1972 required: true
1973 content:
1974 application/json:
1975 schema:
1976 type: object
1977 required: [allowed_lanes, cost_cap_units]
1978 properties:
1979 allowed_lanes: { type: array, items: { type: string } }
1980 cost_cap_units: { type: integer }
1981 ttl_seconds: { type: integer }
1982 responses:
1983 '201':
1984 content:
1985 application/json:
1986 schema: { $ref: '#/components/schemas/FlowExecutionConsentMintResponse' }
1987
1988 /metadata-facets:
1989 get:
1990 tags: [Notes]
1991 summary: Body-free MetadataFacets hints for one note
1992 description: >
1993 Returns knowtation.metadata_facets/v0 metadata for one authorized vault-relative note.
1994 The response excludes note body text, snippets, full frontmatter, absolute paths,
1995 provider payloads, MCP resource URIs, summaries, labels, vectors, OCR, PageIndex output,
1996 media metadata, memory events, persistence records, sidecars, LLM calls, and write-back state.
1997 parameters:
1998 - name: path
1999 in: query
2000 required: true
2001 schema: { type: string }
2002 description: Vault-relative Markdown note path.
2003 responses:
2004 '200':
2005 content:
2006 application/json:
2007 schema: { $ref: '#/components/schemas/MetadataFacets' }
2008 '400':
2009 content:
2010 application/json:
2011 schema: { $ref: '#/components/schemas/Error' }
2012 '401':
2013 content:
2014 application/json:
2015 schema: { $ref: '#/components/schemas/Error' }
2016 '403':
2017 content:
2018 application/json:
2019 schema: { $ref: '#/components/schemas/Error' }
2020 '404':
2021 content:
2022 application/json:
2023 schema: { $ref: '#/components/schemas/Error' }
2024 '502':
2025 content:
2026 application/json:
2027 schema: { $ref: '#/components/schemas/Error' }
2028
2029 /section-source:
2030 get:
2031 tags: [Notes]
2032 summary: Body-free SectionSource metadata for one note
2033 description: >
2034 Returns knowtation.section_source/v0 metadata for one authorized vault-relative note.
2035 The response excludes note body text, section body text, snippets, full frontmatter,
2036 line ranges, byte offsets, section body lengths, absolute paths, raw canister payloads,
2037 provider payloads, and MCP resource URIs.
2038 parameters:
2039 - name: path
2040 in: query
2041 required: true
2042 schema: { type: string }
2043 description: Vault-relative Markdown note path.
2044 responses:
2045 '200':
2046 content:
2047 application/json:
2048 schema: { $ref: '#/components/schemas/SectionSource' }
2049 '400':
2050 content:
2051 application/json:
2052 schema: { $ref: '#/components/schemas/Error' }
2053 '401':
2054 content:
2055 application/json:
2056 schema: { $ref: '#/components/schemas/Error' }
2057 '403':
2058 content:
2059 application/json:
2060 schema: { $ref: '#/components/schemas/Error' }
2061 '404':
2062 content:
2063 application/json:
2064 schema: { $ref: '#/components/schemas/Error' }
2065 '502':
2066 content:
2067 application/json:
2068 schema: { $ref: '#/components/schemas/Error' }
2069
2070 /index:
2071 post:
2072 tags: [Notes]
2073 summary: Re-run indexer (vault to vector store)
2074 responses:
2075 '200':
2076 content:
2077 application/json:
2078 schema:
2079 type: object
2080 properties:
2081 ok: { type: boolean }
2082 notesProcessed: { type: integer }
2083 chunksIndexed: { type: integer }
2084 vectors_deleted: { type: integer, description: Rows removed for this vault before upsert (hosted sqlite-vec) }
2085 '500':
2086 content:
2087 application/json:
2088 schema: { $ref: '#/components/schemas/Error' }
2089
2090 /export:
2091 post:
2092 tags: [Notes]
2093 summary: Export one note to content (returns body + filename for client download)
2094 requestBody:
2095 required: true
2096 content:
2097 application/json:
2098 schema:
2099 type: object
2100 required: [path]
2101 properties:
2102 path: { type: string }
2103 format: { type: string, enum: [md, html] }
2104 responses:
2105 '200':
2106 content:
2107 application/json:
2108 schema:
2109 type: object
2110 properties:
2111 content: { type: string }
2112 filename: { type: string }
2113 '400':
2114 content:
2115 application/json:
2116 schema: { $ref: '#/components/schemas/Error' }
2117 '404':
2118 content:
2119 application/json:
2120 schema: { $ref: '#/components/schemas/Error' }
2121
2122 /import:
2123 post:
2124 tags: [Notes]
2125 summary: Import from uploaded file or ZIP (multipart: source_type; file except for google-sheets; optional project, tags, spreadsheet_id for google-sheets)
2126 requestBody:
2127 required: true
2128 content:
2129 multipart/form-data:
2130 schema:
2131 type: object
2132 required: [source_type]
2133 properties:
2134 source_type:
2135 type: string
2136 description: Importer id. For google-sheets, omit file and set spreadsheet_id; optional sheets_range (A1 notation). See lib/import-source-types.mjs.
2137 file: { type: string, format: binary, description: Required for all importers except google-sheets. }
2138 spreadsheet_id:
2139 type: string
2140 description: Required when source_type is google-sheets (id from the Google Sheets URL).
2141 sheets_range:
2142 type: string
2143 description: Optional for google-sheets; A1 range. Omit to read the first sheet from A1.
2144 project: { type: string }
2145 output_dir: { type: string }
2146 tags: { type: string }
2147 responses:
2148 '200':
2149 content:
2150 application/json:
2151 schema:
2152 type: object
2153 properties:
2154 imported: { type: array, items: { type: object } }
2155 count: { type: integer }
2156 '400':
2157 content:
2158 application/json:
2159 schema: { $ref: '#/components/schemas/Error' }
2160 '500':
2161 content:
2162 application/json:
2163 schema: { $ref: '#/components/schemas/Error' }
2164
2165 /import-url:
2166 post:
2167 tags: [Notes]
2168 summary: Import from a public https URL (JSON body; editor/admin)
2169 requestBody:
2170 required: true
2171 content:
2172 application/json:
2173 schema:
2174 type: object
2175 required: [url]
2176 properties:
2177 url: { type: string, description: 'Full https URL' }
2178 mode: { type: string, enum: [auto, bookmark, extract], description: 'Capture mode (default auto)' }
2179 project: { type: string }
2180 output_dir: { type: string }
2181 tags: { oneOf: [{ type: string }, { type: array, items: { type: string } }] }
2182 responses:
2183 '200':
2184 content:
2185 application/json:
2186 schema:
2187 type: object
2188 properties:
2189 imported: { type: array, items: { type: object } }
2190 count: { type: integer }
2191 '400':
2192 content:
2193 application/json:
2194 schema: { $ref: '#/components/schemas/Error' }
2195 '500':
2196 content:
2197 application/json:
2198 schema: { $ref: '#/components/schemas/Error' }
2199
2200 /docs/connectors:
2201 get:
2202 tags: [DocsConnectors]
2203 summary: List docs connectors (Drive + Notion). Gate off → 501 NOT_AUTHORIZED. No secrets.
2204 responses:
2205 '200':
2206 content:
2207 application/json:
2208 schema:
2209 type: object
2210 required: [schema, connectors]
2211 properties:
2212 schema: { type: string, enum: [knowtation.docs_connectors/v0] }
2213 connectors:
2214 type: array
2215 items:
2216 type: object
2217 properties:
2218 connector_id: { type: string }
2219 provider: { type: string, enum: [google-drive, notion] }
2220 display_name: { type: string }
2221 status: { type: string, enum: [pending, connected, needs_reauth, revoked] }
2222 last_sync_at: { type: string, nullable: true }
2223 last_sync_error: { type: string }
2224 file_count: { type: integer }
2225 revoked_at: { type: string, nullable: true }
2226 '501':
2227 description: Gate not authorized
2228 post:
2229 tags: [DocsConnectors]
2230 summary: Begin Drive OAuth or Notion Hub-key connector (editor/admin). Gates hard-coded false.
2231 requestBody:
2232 required: true
2233 content:
2234 application/json:
2235 schema:
2236 type: object
2237 required: [provider]
2238 properties:
2239 provider: { type: string, enum: [google-drive, notion] }
2240 display_name: { type: string, maxLength: 128 }
2241 return_url: { type: string, description: Required for google-drive; exact-allowlisted }
2242 responses:
2243 '200':
2244 description: Drive returns authorization_url; Notion returns status
2245 '400':
2246 description: BAD_REQUEST / PROVIDER_DENIED / RETURN_URL_DENIED
2247 '501':
2248 description: NOT_AUTHORIZED
2249
2250 /docs/connectors/callback:
2251 get:
2252 tags: [DocsConnectors]
2253 summary: Google Drive OAuth callback (state-authenticated; no JWT)
2254 security: []
2255 parameters:
2256 - name: code
2257 in: query
2258 schema: { type: string }
2259 - name: state
2260 in: query
2261 schema: { type: string }
2262 responses:
2263 '302':
2264 description: Redirect to allowlisted return_url
2265
2266 /docs/connectors/{id}/files:
2267 get:
2268 tags: [DocsConnectors]
2269 summary: List importable file metadata (no bodies)
2270 parameters:
2271 - name: id
2272 in: path
2273 required: true
2274 schema: { type: string }
2275 - name: page_token
2276 in: query
2277 schema: { type: string }
2278 - name: q
2279 in: query
2280 schema: { type: string, pattern: '^[A-Za-z0-9 ._-]{1,128}$' }
2281 responses:
2282 '200':
2283 description: files + optional next_page_token
2284 '400':
2285 description: BAD_REQUEST (invalid q or ids)
2286 '501':
2287 description: NOT_AUTHORIZED
2288
2289 /docs/connectors/{id}/import:
2290 post:
2291 tags: [DocsConnectors]
2292 summary: Create docs-sync Review proposals for 1–20 file ids (never writeNote)
2293 parameters:
2294 - name: id
2295 in: path
2296 required: true
2297 schema: { type: string }
2298 requestBody:
2299 required: true
2300 content:
2301 application/json:
2302 schema:
2303 type: object
2304 required: [file_ids]
2305 properties:
2306 file_ids:
2307 type: array
2308 minItems: 1
2309 maxItems: 20
2310 items: { type: string }
2311 responses:
2312 '200':
2313 description: '{ proposed, skipped, proposal_ids }'
2314 '501':
2315 description: NOT_AUTHORIZED
2316
2317 /docs/connectors/{id}/sync:
2318 post:
2319 tags: [DocsConnectors]
2320 summary: Optional cursor sync; rate-limited ≥60s; creates proposals only
2321 parameters:
2322 - name: id
2323 in: path
2324 required: true
2325 schema: { type: string }
2326 responses:
2327 '200':
2328 description: '{ proposed, skipped, last_sync_at }'
2329 '429':
2330 description: RATE_LIMITED
2331 '501':
2332 description: NOT_AUTHORIZED
2333
2334 /docs/connectors/{id}:
2335 delete:
2336 tags: [DocsConnectors]
2337 summary: Revoke connector; imported vault notes stay
2338 parameters:
2339 - name: id
2340 in: path
2341 required: true
2342 schema: { type: string }
2343 responses:
2344 '200':
2345 description: '{ revoked: true }'
2346 '501':
2347 description: NOT_AUTHORIZED
2348
2349 /settings:
2350 get:
2351 tags: [Notes]
2352 summary: Config status for Settings UI (no secrets)
2353 responses:
2354 '200':
2355 content:
2356 application/json:
2357 schema:
2358 type: object
2359 properties:
2360 vault_path_display: { type: string }
2361 vault_git:
2362 type: object
2363 properties:
2364 enabled: { type: boolean }
2365 has_remote: { type: boolean }
2366 auto_commit: { type: boolean }
2367 auto_push: { type: boolean }
2368
2369 /vault/sync:
2370 post:
2371 tags: [Notes]
2372 summary: Manual vault backup (git add, commit, push)
2373 description: Self-hosted runs local git. Hosted (bridge) pushes notes as Markdown plus `.knowtation/backup/v1/snapshot.json` with full proposals.
2374 responses:
2375 '200':
2376 content:
2377 application/json:
2378 schema:
2379 type: object
2380 properties:
2381 ok: { type: boolean }
2382 message: { type: string }
2383 notesCount: { type: integer, description: Hosted bridge only }
2384 proposalsCount: { type: integer, description: Hosted bridge only }
2385 '400':
2386 content:
2387 application/json:
2388 schema: { $ref: '#/components/schemas/Error' }
2389 '500':
2390 content:
2391 application/json:
2392 schema: { $ref: '#/components/schemas/Error' }
2393
2394 /search:
2395 post:
2396 tags: [Search]
2397 summary: Vault search (semantic or keyword)
2398 requestBody:
2399 required: true
2400 content:
2401 application/json:
2402 schema:
2403 type: object
2404 required: [query]
2405 properties:
2406 query: { type: string }
2407 mode: { type: string, enum: [semantic, keyword], description: Omitted or semantic = vector search; keyword = substring/token match on note text }
2408 match: { type: string, enum: [phrase, all_terms], description: Keyword only; phrase = full query substring; all_terms = every token must appear }
2409 folder: { type: string }
2410 project: { type: string }
2411 tag: { type: string }
2412 since: { type: string }
2413 until: { type: string }
2414 chain: { type: string }
2415 entity: { type: string }
2416 episode: { type: string }
2417 limit: { type: integer }
2418 order: { type: string }
2419 fields: { type: string }
2420 content_scope: { type: string, enum: [notes, approval_logs], description: Narrow to normal notes vs approvals/ logs }
2421 snippetChars: { type: integer }
2422 count_only: { type: boolean }
2423 countOnly: { type: boolean }
2424 responses:
2425 '200':
2426 content:
2427 application/json:
2428 schema:
2429 type: object
2430 properties:
2431 results: { type: array, items: { $ref: '#/components/schemas/SearchResult' } }
2432 query: { type: string }
2433 mode: { type: string, enum: [semantic, keyword] }
2434 count: { type: integer, description: Present when count_only keyword search }
2435 '400':
2436 content:
2437 application/json:
2438 schema: { $ref: '#/components/schemas/Error' }
2439
2440 /proposals:
2441 get:
2442 tags: [Proposals]
2443 summary: List proposals
2444 parameters:
2445 - name: status
2446 in: query
2447 schema: { type: string }
2448 - name: limit
2449 in: query
2450 schema: { type: integer }
2451 - name: offset
2452 in: query
2453 schema: { type: integer }
2454 - name: label
2455 in: query
2456 description: Match if proposal labels include this string (case-insensitive)
2457 schema: { type: string }
2458 - name: source
2459 in: query
2460 schema: { type: string }
2461 - name: path_prefix
2462 in: query
2463 schema: { type: string }
2464 - name: evaluation_status
2465 in: query
2466 description: Filter by evaluation_status (none, pending, passed, failed, needs_changes)
2467 schema: { type: string }
2468 - name: review_queue
2469 in: query
2470 description: Exact match on proposal review_queue
2471 schema: { type: string }
2472 - name: review_severity
2473 in: query
2474 description: standard or elevated
2475 schema: { type: string }
2476 responses:
2477 '200':
2478 content:
2479 application/json:
2480 schema:
2481 type: object
2482 properties:
2483 proposals: { type: array, items: { $ref: '#/components/schemas/Proposal' } }
2484 total: { type: integer }
2485 post:
2486 tags: [Proposals]
2487 summary: Create proposal
2488 requestBody:
2489 content:
2490 application/json:
2491 schema:
2492 type: object
2493 properties:
2494 path: { type: string }
2495 body: { type: string }
2496 frontmatter: { type: object }
2497 intent: { type: string }
2498 base_state_id: { type: string }
2499 external_ref: { type: string }
2500 labels: { type: array, items: { type: string } }
2501 source: { type: string }
2502 responses:
2503 '201':
2504 content:
2505 application/json:
2506 schema:
2507 type: object
2508 properties:
2509 proposal_id: { type: string }
2510 path: { type: string }
2511 status: { type: string, enum: [proposed] }
2512 '400':
2513
2514 /proposals/{id}:
2515 get:
2516 tags: [Proposals]
2517 summary: Get one proposal
2518 parameters:
2519 - name: id
2520 in: path
2521 required: true
2522 schema: { type: string }
2523 responses:
2524 '200':
2525 content:
2526 application/json:
2527 schema: { $ref: '#/components/schemas/ProposalDetail' }
2528 '404':
2529
2530 /proposals/{id}/review-hints:
2531 post:
2532 tags: [Proposals]
2533 summary: Store async LLM review hints (canister; not a merge gate)
2534 parameters:
2535 - name: id
2536 in: path
2537 required: true
2538 schema: { type: string }
2539 requestBody:
2540 content:
2541 application/json:
2542 schema:
2543 type: object
2544 properties:
2545 review_hints: { type: string }
2546 review_hints_model: { type: string }
2547 responses:
2548 '200':
2549 content:
2550 application/json:
2551 schema:
2552 type: object
2553 properties:
2554 proposal_id: { type: string }
2555 ok: { type: boolean }
2556
2557 /proposals/{id}/evaluation:
2558 post:
2559 tags: [Proposals]
2560 summary: Submit human evaluation (admin or evaluator)
2561 parameters:
2562 - name: id
2563 in: path
2564 required: true
2565 schema: { type: string }
2566 requestBody:
2567 content:
2568 application/json:
2569 schema:
2570 type: object
2571 required: [outcome]
2572 properties:
2573 outcome:
2574 type: string
2575 enum: [pass, fail, needs_changes]
2576 checklist:
2577 type: array
2578 items:
2579 type: object
2580 properties:
2581 id: { type: string }
2582 passed: { type: boolean }
2583 grade: { type: string }
2584 comment: { type: string }
2585 responses:
2586 '200':
2587 content:
2588 application/json:
2589 schema: { $ref: '#/components/schemas/ProposalDetail' }
2590 '400':
2591 '404':
2592
2593 /proposals/{id}/approve:
2594 post:
2595 tags: [Proposals]
2596 summary: Apply proposal to vault
2597 parameters:
2598 - name: id
2599 in: path
2600 required: true
2601 schema: { type: string }
2602 requestBody:
2603 content:
2604 application/json:
2605 schema:
2606 type: object
2607 properties:
2608 base_state_id: { type: string }
2609 waiver_reason:
2610 type: string
2611 description: Admin override when evaluation is not passed (min length 3 after trim)
2612 external_ref:
2613 type: string
2614 description: Optional cross-system lineage id (e.g. Muse); server may resolve via MUSE_URL when omitted
2615 responses:
2616 '200':
2617 content:
2618 application/json:
2619 schema:
2620 type: object
2621 properties:
2622 proposal_id: { type: string }
2623 status: { type: string, enum: [approved] }
2624 external_ref: { type: string }
2625 '403':
2626 description: EVALUATION_REQUIRED — pass evaluation or provide waiver_reason
2627 '409':
2628 description: base_state_id mismatch (CONFLICT)
2629
2630 /proposals/{id}/enrich:
2631 post:
2632 tags: [Proposals]
2633 summary: Optional LLM summary and suggested labels (KNOWTATION_HUB_PROPOSAL_ENRICH=1)
2634 parameters:
2635 - name: id
2636 in: path
2637 required: true
2638 schema: { type: string }
2639 responses:
2640 '200':
2641 content:
2642 application/json:
2643 schema: { $ref: '#/components/schemas/ProposalDetail' }
2644 '400':
2645 description: >-
2646 ICP canister — suggested_labels_json or assistant_suggested_frontmatter_json is valid JSON
2647 but exceeds max length (4000 / 14000 characters) after validation.
2648 '404':
2649
2650 /proposals/{id}/discard:
2651 post:
2652 tags: [Proposals]
2653 summary: Discard proposal
2654 parameters:
2655 - name: id
2656 in: path
2657 required: true
2658 schema: { type: string }
2659 responses:
2660 '200':
2661 content:
2662 application/json:
2663 schema:
2664 type: object
2665 properties:
2666 proposal_id: { type: string }
2667 status: { type: string, enum: [discarded] }
2668
2669 /capture:
2670 post:
2671 tags: [Capture]
2672 summary: Ingest message into vault inbox (webhook-style)
2673 description: Same contract as capture-webhook. If CAPTURE_WEBHOOK_SECRET is set, require X-Webhook-Secret header.
2674 security: []
2675 requestBody:
2676 content:
2677 application/json:
2678 schema:
2679 type: object
2680 required: [body]
2681 properties:
2682 body: { type: string }
2683 source_id: { type: string }
2684 source: { type: string }
2685 project: { type: string }
2686 tags: { type: array, items: { type: string } }
2687 responses:
2688 '200':
2689 content:
2690 application/json:
2691 schema: { type: object, properties: { ok: { type: boolean }, path: { type: string } } }
2692 '400':
2693
2694 components:
2695 securitySchemes:
2696 BearerAuth:
2697 type: http
2698 scheme: bearer
2699 bearerFormat: JWT
2700
2701 schemas:
2702 Error:
2703 type: object
2704 properties:
2705 error: { type: string }
2706 code: { type: string }
2707
2708 NoteListItem:
2709 type: object
2710 properties:
2711 path: { type: string }
2712 title: { type: string, nullable: true }
2713 project: { type: string, nullable: true }
2714 tags: { type: array, items: { type: string } }
2715 date: { type: string, nullable: true }
2716
2717 NoteFull:
2718 type: object
2719 properties:
2720 path: { type: string }
2721 frontmatter: { type: object }
2722 body: { type: string }
2723
2724 SearchResult:
2725 type: object
2726 properties:
2727 path: { type: string }
2728 snippet: { type: string }
2729 score: { type: number }
2730 project: { type: string }
2731 tags: { type: array, items: { type: string } }
2732
2733 NoteOutline:
2734 type: object
2735 required: [schema, path, headings, truncated]
2736 properties:
2737 schema:
2738 type: string
2739 enum: [knowtation.note_outline/v1]
2740 path: { type: string }
2741 title: { type: string, nullable: true }
2742 headings:
2743 type: array
2744 maxItems: 500
2745 items: { $ref: '#/components/schemas/NoteOutlineHeading' }
2746 truncated: { type: boolean }
2747
2748 NoteOutlineHeading:
2749 type: object
2750 required: [level, text, id]
2751 properties:
2752 level: { type: integer, minimum: 1, maximum: 6 }
2753 text: { type: string }
2754 id: { type: string }
2755
2756 DocumentTree:
2757 type: object
2758 required: [schema, path, root, truncated]
2759 properties:
2760 schema:
2761 type: string
2762 enum: [knowtation.document_tree/v0]
2763 path: { type: string }
2764 title: { type: string, nullable: true }
2765 root:
2766 type: object
2767 required: [children]
2768 properties:
2769 children:
2770 type: array
2771 maxItems: 500
2772 items: { $ref: '#/components/schemas/DocumentTreeNode' }
2773 truncated: { type: boolean }
2774
2775 DocumentTreeNode:
2776 type: object
2777 required: [id, level, text, children]
2778 properties:
2779 id: { type: string }
2780 level: { type: integer, minimum: 1, maximum: 6 }
2781 text: { type: string }
2782 children:
2783 type: array
2784 items: { $ref: '#/components/schemas/DocumentTreeNode' }
2785
2786 MetadataFacets:
2787 type: object
2788 required: [schema, path, facets, inferred, truncated]
2789 properties:
2790 schema:
2791 type: string
2792 enum: [knowtation.metadata_facets/v0]
2793 path: { type: string }
2794 facets:
2795 type: object
2796 required: [project, tags, date, updated, causal_chain_id, entity, episode_id]
2797 properties:
2798 project: { type: string, nullable: true }
2799 tags:
2800 type: array
2801 maxItems: 100
2802 items: { type: string }
2803 date: { type: string, nullable: true }
2804 updated: { type: string, nullable: true }
2805 causal_chain_id: { type: string, nullable: true }
2806 entity:
2807 type: array
2808 maxItems: 100
2809 items: { type: string }
2810 episode_id: { type: string, nullable: true }
2811 inferred:
2812 type: object
2813 required: [folder, source_type]
2814 properties:
2815 folder: { type: string, nullable: true }
2816 source_type: { nullable: true, enum: [null] }
2817 truncated: { type: boolean }
2818
2819 SectionSource:
2820 type: object
2821 required: [schema, path, sections, truncated]
2822 properties:
2823 schema:
2824 type: string
2825 enum: [knowtation.section_source/v0]
2826 path: { type: string }
2827 title: { type: string, nullable: true }
2828 sections:
2829 type: array
2830 items: { $ref: '#/components/schemas/SectionSourceSection' }
2831 truncated: { type: boolean }
2832
2833 SectionSourceSection:
2834 type: object
2835 required:
2836 - section_id
2837 - heading_id
2838 - level
2839 - heading_path
2840 - heading_text
2841 - child_section_ids
2842 - body_available
2843 - body_returned
2844 - snippet_returned
2845 properties:
2846 section_id: { type: string }
2847 heading_id: { type: string }
2848 level: { type: integer, minimum: 1, maximum: 6 }
2849 heading_path: { type: array, items: { type: string } }
2850 heading_text: { type: string }
2851 child_section_ids: { type: array, items: { type: string } }
2852 body_available: { type: boolean }
2853 body_returned: { type: boolean, enum: [false] }
2854 snippet_returned: { type: boolean, enum: [false] }
2855
2856 Proposal:
2857 type: object
2858 properties:
2859 proposal_id: { type: string }
2860 path: { type: string }
2861 status: { type: string }
2862 intent: { type: string }
2863 base_state_id: { type: string }
2864 external_ref: { type: string }
2865 vault_id: { type: string }
2866 proposed_by: { type: string }
2867 labels: { type: array, items: { type: string } }
2868 source: { type: string }
2869 suggested_labels: { type: array, items: { type: string } }
2870 assistant_notes: { type: string }
2871 assistant_model: { type: string }
2872 assistant_at: { type: string }
2873 created_at: { type: string }
2874 updated_at: { type: string }
2875 evaluation_status:
2876 type: string
2877 enum: [none, pending, passed, failed, needs_changes]
2878 evaluation_grade: { type: string }
2879 evaluation_comment: { type: string }
2880 evaluated_by: { type: string }
2881 evaluated_at: { type: string }
2882 evaluation_waiver:
2883 type: object
2884 nullable: true
2885 properties:
2886 by: { type: string }
2887 at: { type: string }
2888 reason: { type: string }
2889 review_queue: { type: string }
2890 review_severity: { type: string, enum: [standard, elevated] }
2891 auto_flag_reasons:
2892 type: array
2893 items: { type: string }
2894 auto_flag_reasons_json: { type: string, description: JSON array string on canister }
2895 review_hints: { type: string }
2896 review_hints_at: { type: string }
2897 review_hints_model: { type: string }
2898 assistant_suggested_frontmatter:
2899 type: object
2900 description: Normalized SPEC-aligned suggested note metadata from Enrich (object on GET); omitted or empty on older proposals
2901 additionalProperties: true
2902
2903 ProposalDetail:
2904 allOf:
2905 - { $ref: '#/components/schemas/Proposal' }
2906 - type: object
2907 properties:
2908 body: { type: string }
2909 frontmatter: { type: object }
2910 evaluation_checklist:
2911 type: array
2912 items:
2913 type: object
2914 properties:
2915 id: { type: string }
2916 label: { type: string }
2917 passed: { type: boolean }
2918
2919 CalendarTimeline:
2920 type: object
2921 required: [schema, vault_id, from, to, layers, items]
2922 properties:
2923 schema:
2924 type: string
2925 enum: [knowtation.calendar_timeline/v0]
2926 vault_id: { type: string }
2927 from: { type: string }
2928 to: { type: string }
2929 layers:
2930 type: array
2931 items:
2932 type: string
2933 enum: [notes, events]
2934 items:
2935 type: array
2936 items:
2937 oneOf:
2938 - { $ref: '#/components/schemas/CalendarTimelineNoteItem' }
2939 - { $ref: '#/components/schemas/CalendarTimelineEventItem' }
2940
2941 CalendarTimelineNoteItem:
2942 type: object
2943 required: [kind, date, path, title, project, tags, sort_at]
2944 properties:
2945 kind:
2946 type: string
2947 enum: [note]
2948 date: { type: string }
2949 path: { type: string }
2950 title: { type: string, nullable: true }
2951 project: { type: string, nullable: true }
2952 tags:
2953 type: array
2954 items: { type: string }
2955 sort_at: { type: string }
2956
2957 CalendarTimelineEventItem:
2958 type: object
2959 required: [kind, event_id, source_calendar_id, start, end, timezone, summary, busy, status, calendar_label, sort_at]
2960 properties:
2961 kind:
2962 type: string
2963 enum: [event]
2964 event_id: { type: string }
2965 source_calendar_id: { type: string }
2966 start: { type: string }
2967 end: { type: string }
2968 timezone: { type: string }
2969 summary: { type: string, nullable: true }
2970 busy: { type: boolean }
2971 status:
2972 type: string
2973 enum: [confirmed, cancelled, tentative]
2974 calendar_label: { type: string, nullable: true }
2975 sort_at: { type: string }
2976
2977 CalendarAgentContext:
2978 type: object
2979 required: [schema, vault_id, from, to, requested_tier, effective_tier, policy_agent_context_tier_max_cap, source_calendars, items]
2980 properties:
2981 schema:
2982 type: string
2983 enum: [knowtation.calendar_agent_context/v0]
2984 vault_id: { type: string }
2985 from: { type: string }
2986 to: { type: string }
2987 requested_tier:
2988 type: integer
2989 minimum: 0
2990 maximum: 2
2991 effective_tier:
2992 type: integer
2993 minimum: 0
2994 maximum: 2
2995 description: Requested tier after the org policy cap is applied.
2996 policy_agent_context_tier_max_cap:
2997 type: integer
2998 minimum: 0
2999 maximum: 4
3000 source_calendars:
3001 type: array
3002 items: { $ref: '#/components/schemas/AgentContextCalendarSummary' }
3003 items:
3004 type: array
3005 items: { $ref: '#/components/schemas/CalendarAgentContextEventItem' }
3006
3007 AgentContextCalendarSummary:
3008 type: object
3009 required: [source_calendar_id, display_name, user_group, enabled_for_agents, agent_context_tier_max, effective_tier, event_count]
3010 properties:
3011 source_calendar_id: { type: string }
3012 display_name: { type: string }
3013 user_group:
3014 type: string
3015 nullable: true
3016 enum: [personal, work, school, other, null]
3017 enabled_for_agents: { type: boolean }
3018 agent_context_tier_max:
3019 type: integer
3020 minimum: 0
3021 maximum: 4
3022 effective_tier:
3023 type: integer
3024 minimum: 0
3025 maximum: 2
3026 event_count: { type: integer }
3027
3028 CalendarAgentContextEventItem:
3029 type: object
3030 required: [event_id, source_calendar_id, external_uid, start, end, timezone, busy, status, agent_tier]
3031 description: >
3032 Redacted event. `summary` and `calendar_label` are present only at tier 2;
3033 tier 1 omits the event title entirely.
3034 properties:
3035 event_id: { type: string }
3036 source_calendar_id: { type: string }
3037 external_uid: { type: string }
3038 start: { type: string }
3039 end: { type: string }
3040 timezone: { type: string }
3041 busy: { type: boolean }
3042 status:
3043 type: string
3044 enum: [confirmed, cancelled, tentative]
3045 agent_tier:
3046 type: integer
3047 minimum: 1
3048 maximum: 2
3049 summary: { type: string, nullable: true }
3050 calendar_label: { type: string, nullable: true }
3051
3052 SourceCalendarList:
3053 type: object
3054 required: [schema, vault_id, source_calendars]
3055 properties:
3056 schema:
3057 type: string
3058 enum: [knowtation.source_calendars/v0]
3059 vault_id: { type: string }
3060 source_calendars:
3061 type: array
3062 items: { $ref: '#/components/schemas/SourceCalendar' }
3063
3064 SourceCalendar:
3065 type: object
3066 required: [source_calendar_id, connector_id, display_name, enabled_for_sync, enabled_for_display, enabled_for_agents, agent_context_tier_max]
3067 properties:
3068 source_calendar_id: { type: string }
3069 connector_id: { type: string }
3070 display_name: { type: string }
3071 color: { type: string, nullable: true }
3072 user_group:
3073 type: string
3074 nullable: true
3075 enum: [personal, work, school, other, null]
3076 enabled_for_sync: { type: boolean }
3077 enabled_for_display: { type: boolean }
3078 enabled_for_agents: { type: boolean }
3079 agent_context_tier_max:
3080 type: integer
3081 minimum: 0
3082 maximum: 4
3083 provider: { type: string }
3084
3085 CalendarIcsImportRequest:
3086 type: object
3087 required: [ics_text]
3088 properties:
3089 ics_text: { type: string }
3090 display_name: { type: string }
3091 source_calendar_id: { type: string }
3092 connector_id: { type: string }
3093 default_timezone: { type: string }
3094
3095 CalendarIcsImportResult:
3096 type: object
3097 required: [schema, vault_id, source_calendar_id, connector_id, imported, updated]
3098 properties:
3099 schema:
3100 type: string
3101 enum: [knowtation.calendar_import/v0]
3102 vault_id: { type: string }
3103 source_calendar_id: { type: string }
3104 connector_id: { type: string }
3105 imported: { type: integer }
3106 updated: { type: integer }
3107
3108 SourceCalendarPatchRequest:
3109 type: object
3110 minProperties: 1
3111 properties:
3112 enabled_for_display: { type: boolean }
3113 enabled_for_agents: { type: boolean }
3114 agent_context_tier_max:
3115 type: integer
3116 minimum: 0
3117 maximum: 4
3118 user_group:
3119 type: string
3120 nullable: true
3121 enum: [personal, work, school, other, null]
3122
3123 SourceCalendarPatchResult:
3124 type: object
3125 required: [schema, vault_id, policy_agent_context_tier_max_cap, source_calendar]
3126 properties:
3127 schema:
3128 type: string
3129 enum: [knowtation.source_calendar_patch/v0]
3130 vault_id: { type: string }
3131 policy_agent_context_tier_max_cap:
3132 type: integer
3133 minimum: 0
3134 maximum: 4
3135 source_calendar: { $ref: '#/components/schemas/SourceCalendar' }
3136
3137 FlowListResponse:
3138 type: object
3139 required: [schema, vault_id, effective_scope, flows, truncated]
3140 properties:
3141 schema:
3142 type: string
3143 enum: [knowtation.flow_list/v0]
3144 vault_id: { type: string }
3145 effective_scope:
3146 type: string
3147 enum: [personal, project, org]
3148 flows:
3149 type: array
3150 maxItems: 200
3151 items: { $ref: '#/components/schemas/FlowSummary' }
3152 truncated: { type: boolean }
3153
3154 TaskListResponse:
3155 type: object
3156 required: [schema, vault_id, effective_scope, tasks, truncated]
3157 properties:
3158 schema:
3159 type: string
3160 enum: [knowtation.task_list/v0]
3161 vault_id: { type: string }
3162 effective_scope:
3163 type: string
3164 enum: [personal, project, org]
3165 tasks:
3166 type: array
3167 maxItems: 500
3168 items: { $ref: '#/components/schemas/TaskSummary' }
3169 truncated: { type: boolean }
3170
3171 LearningPathListResponse:
3172 type: object
3173 required: [schema, vault_id, effective_scope, paths, truncated]
3174 properties:
3175 schema:
3176 type: string
3177 enum: [knowtation.learning_path_list/v0]
3178 vault_id: { type: string }
3179 effective_scope:
3180 type: string
3181 enum: [personal, project, org]
3182 paths:
3183 type: array
3184 maxItems: 200
3185 items: { $ref: '#/components/schemas/LearningPathSummary' }
3186 truncated: { type: boolean }
3187
3188 LearningPathSummary:
3189 type: object
3190 required: [schema, path_id, scope, status, title, goal, current_step_index, step_count, next_step_title, active_decisions, workspace_id, updated]
3191 properties:
3192 schema:
3193 type: string
3194 enum: [knowtation.learning_path/v0]
3195 path_id: { type: string }
3196 scope:
3197 type: string
3198 enum: [personal, project, org]
3199 status:
3200 type: string
3201 enum: [active, paused, archived]
3202 title: { type: string }
3203 goal: { type: string }
3204 current_step_index: { type: integer }
3205 step_count: { type: integer }
3206 next_step_title: { type: string }
3207 active_decisions: { type: string }
3208 workspace_id: { type: string }
3209 updated: { type: string, format: date-time }
3210
3211 LearningPathGetResponse:
3212 type: object
3213 required: [schema, vault_id, effective_scope, path]
3214 properties:
3215 schema:
3216 type: string
3217 enum: [knowtation.learning_path_get/v0]
3218 vault_id: { type: string }
3219 effective_scope:
3220 type: string
3221 enum: [personal, project, org]
3222 path: { $ref: '#/components/schemas/LearningPathRecord' }
3223
3224 LearningPathRecord:
3225 type: object
3226 required: [schema, path_id, scope, status, title, summary, goal, steps, current_step_index, step_count, next_step_title, active_decisions, workspace_id, note_path, created, updated]
3227 properties:
3228 schema:
3229 type: string
3230 enum: [knowtation.learning_path/v0]
3231 path_id: { type: string }
3232 scope:
3233 type: string
3234 enum: [personal, project, org]
3235 status:
3236 type: string
3237 enum: [active, paused, archived]
3238 title: { type: string }
3239 summary: { type: string }
3240 goal: { type: string }
3241 steps:
3242 type: array
3243 minItems: 1
3244 maxItems: 20
3245 items:
3246 type: object
3247 required: [title, objective, source_document_ids]
3248 properties:
3249 title: { type: string }
3250 objective: { type: string }
3251 source_document_ids:
3252 type: array
3253 items: { type: string }
3254 current_step_index: { type: integer }
3255 step_count: { type: integer }
3256 next_step_title: { type: string }
3257 active_decisions: { type: string }
3258 workspace_id: { type: string }
3259 note_path:
3260 type: string
3261 nullable: true
3262 created: { type: string, format: date-time }
3263 updated: { type: string, format: date-time }
3264
3265 LearningPathProposalRequest:
3266 type: object
3267 properties:
3268 proposal_kind:
3269 type: string
3270 enum: [path_create, path_update, path_archive]
3271 title: { type: string }
3272 summary: { type: string }
3273 goal: { type: string }
3274 steps: { type: array, items: { type: object } }
3275 path_id: { type: string }
3276 intent: { type: string }
3277
3278 LearningPathProposalResponse:
3279 type: object
3280 required: [schema, proposal_id, proposal_kind, path_id, status, review_queue]
3281 properties:
3282 schema:
3283 type: string
3284 enum: [knowtation.learning_path_proposal/v0]
3285 proposal_id: { type: string }
3286 proposal_kind:
3287 type: string
3288 enum: [path_create, path_update, path_archive]
3289 path_id: { type: string }
3290 scope:
3291 type: string
3292 enum: [personal, project, org]
3293 auto_approvable: { type: boolean }
3294 status: { type: string }
3295 review_queue:
3296 type: string
3297 enum: [learning-path]
3298
3299 TaskSummary:
3300 type: object
3301 required: [schema, task_id, kind, scope, status, title, workspace_id, due_at, run_ref, truncated]
3302 properties:
3303 schema:
3304 type: string
3305 enum: [knowtation.task/v0]
3306 task_id: { type: string }
3307 kind:
3308 type: string
3309 enum: [personal, assignment, mentor_checkin, org_work_job]
3310 scope:
3311 type: string
3312 enum: [personal, project, org]
3313 status:
3314 type: string
3315 enum: [pending, in_progress, blocked, done, cancelled]
3316 title: { type: string }
3317 workspace_id: { type: string }
3318 due_at:
3319 type: string
3320 nullable: true
3321 run_ref:
3322 type: string
3323 nullable: true
3324 truncated: { type: boolean }
3325
3326 TaskGetResponse:
3327 type: object
3328 required: [schema, vault_id, effective_scope, task]
3329 properties:
3330 schema:
3331 type: string
3332 enum: [knowtation.task_get/v0]
3333 vault_id: { type: string }
3334 effective_scope:
3335 type: string
3336 enum: [personal, project, org]
3337 task: { $ref: '#/components/schemas/TaskRecord' }
3338
3339 TaskRecord:
3340 type: object
3341 required:
3342 - schema
3343 - task_id
3344 - kind
3345 - scope
3346 - status
3347 - title
3348 - workspace_id
3349 - due_at
3350 - artifact_links
3351 - created
3352 - updated
3353 - truncated
3354 properties:
3355 schema:
3356 type: string
3357 enum: [knowtation.task/v0]
3358 task_id: { type: string }
3359 kind:
3360 type: string
3361 enum: [personal, assignment, mentor_checkin, org_work_job]
3362 scope:
3363 type: string
3364 enum: [personal, project, org]
3365 status:
3366 type: string
3367 enum: [pending, in_progress, blocked, done, cancelled]
3368 title: { type: string }
3369 workspace_id: { type: string }
3370 due_at:
3371 type: string
3372 nullable: true
3373 assignee_ref:
3374 type: string
3375 nullable: true
3376 assigner_ref:
3377 type: string
3378 nullable: true
3379 run_ref:
3380 type: string
3381 nullable: true
3382 artifact_links:
3383 type: array
3384 maxItems: 32
3385 items:
3386 type: object
3387 required: [kind, ref]
3388 properties:
3389 kind:
3390 type: string
3391 enum: [note, media, review_item]
3392 ref: { type: string }
3393 created: { type: string }
3394 updated: { type: string }
3395 truncated: { type: boolean }
3396
3397 AttachmentListResponse:
3398 type: object
3399 required: [schema, vault_id, effective_scope, attachments, truncated]
3400 properties:
3401 schema:
3402 type: string
3403 enum: [knowtation.attachment_list/v0]
3404 vault_id: { type: string }
3405 effective_scope:
3406 type: string
3407 enum: [personal, project, org]
3408 attachments:
3409 type: array
3410 maxItems: 500
3411 items: { $ref: '#/components/schemas/AttachmentSummary' }
3412 truncated: { type: boolean }
3413
3414 AttachmentSummary:
3415 type: object
3416 required:
3417 - schema
3418 - attachment_id
3419 - source
3420 - storage_kind
3421 - mime_class
3422 - scope
3423 - display_label
3424 - created
3425 - truncated
3426 properties:
3427 schema:
3428 type: string
3429 enum: [knowtation.attachment/v0]
3430 attachment_id: { type: string }
3431 source:
3432 type: string
3433 enum: [vault_file, mist_blob, embedded_url]
3434 storage_kind:
3435 type: string
3436 enum: [vault_blob, external_link]
3437 mime_class:
3438 type: string
3439 enum: [image, video, audio, document, unknown]
3440 scope:
3441 type: string
3442 enum: [personal, project, org]
3443 display_label: { type: string }
3444 created: { type: string }
3445 truncated: { type: boolean }
3446
3447 AttachmentGetResponse:
3448 type: object
3449 required: [schema, vault_id, effective_scope, attachment]
3450 properties:
3451 schema:
3452 type: string
3453 enum: [knowtation.attachment_get/v0]
3454 vault_id: { type: string }
3455 effective_scope:
3456 type: string
3457 enum: [personal, project, org]
3458 attachment: { $ref: '#/components/schemas/AttachmentRecord' }
3459
3460 MediaProposalResponse:
3461 type: object
3462 required: [schema, proposal_id, proposal_kind, attachment_id, scope, auto_approvable, status]
3463 properties:
3464 schema:
3465 type: string
3466 enum: [knowtation.media_proposal/v0]
3467 proposal_id: { type: string }
3468 proposal_kind:
3469 type: string
3470 enum: [media_external_link, media_attach]
3471 attachment_id:
3472 type: string
3473 pattern: '^att_(file|mist|url|link)_[a-f0-9]{32}$'
3474 note_ref: { type: [string, 'null'] }
3475 connector_id: { type: [string, 'null'] }
3476 scope:
3477 type: string
3478 enum: [personal, project, org]
3479 base_state_id: { type: string }
3480 external_ref: { type: [string, 'null'] }
3481 auto_approvable:
3482 type: boolean
3483 enum: [false]
3484 status:
3485 type: string
3486 enum: [proposed]
3487 review_queue:
3488 type: string
3489 enum: [media-writes]
3490
3491 AttachmentRecord:
3492 type: object
3493 required:
3494 - schema
3495 - attachment_id
3496 - source
3497 - storage_kind
3498 - mime_class
3499 - mime_type
3500 - scope
3501 - display_label
3502 - byte_size
3503 - linked_note_refs
3504 - agent_visible
3505 - created
3506 - updated
3507 - truncated
3508 properties:
3509 schema:
3510 type: string
3511 enum: [knowtation.attachment/v0]
3512 attachment_id: { type: string }
3513 source:
3514 type: string
3515 enum: [vault_file, mist_blob, embedded_url]
3516 storage_kind:
3517 type: string
3518 enum: [vault_blob, external_link]
3519 mime_class:
3520 type: string
3521 enum: [image, video, audio, document, unknown]
3522 mime_type:
3523 type: string
3524 nullable: true
3525 scope:
3526 type: string
3527 enum: [personal, project, org]
3528 display_label: { type: string }
3529 byte_size:
3530 type: integer
3531 nullable: true
3532 linked_note_refs:
3533 type: array
3534 items: { type: string }
3535 agent_visible: { type: boolean }
3536 created: { type: string }
3537 updated: { type: string }
3538 truncated: { type: boolean }
3539
3540 TaskWriteProposalRequest:
3541 type: object
3542 required: [intent]
3543 properties:
3544 proposal_kind:
3545 type: string
3546 enum: [task_create, task_status_update, task_assign, task_artifact_link]
3547 intent: { type: string, minLength: 1 }
3548 task: { $ref: '#/components/schemas/TaskRecord' }
3549 task_id: { type: string }
3550 base_state_id: { type: string }
3551 status:
3552 type: string
3553 enum: [pending, in_progress, blocked, done, cancelled]
3554 assignee_ref: { type: string, nullable: true }
3555 assigner_ref: { type: string, nullable: true }
3556 artifact_link:
3557 type: object
3558 required: [kind, ref]
3559 properties:
3560 kind: { type: string }
3561 ref: { type: string }
3562
3563 TaskLoopWriteProposalRequest:
3564 type: object
3565 required: [intent]
3566 properties:
3567 proposal_kind:
3568 type: string
3569 enum: [task_loop_create, task_loop_pause, task_loop_cancel]
3570 intent: { type: string, minLength: 1 }
3571 loop: { type: object }
3572 loop_id: { type: string }
3573 base_state_id: { type: string }
3574
3575 TaskInstanceMaterializeRequest:
3576 type: object
3577 required: [intent]
3578 properties:
3579 intent: { type: string, minLength: 1 }
3580 occurrence_key: { type: string }
3581 occurrence_at: { type: string }
3582 due_at: { type: string }
3583 title_override: { type: string }
3584 base_state_id: { type: string }
3585
3586 TaskProposalResponse:
3587 type: object
3588 required:
3589 - schema
3590 - proposal_id
3591 - proposal_kind
3592 - auto_approvable
3593 - status
3594 - review_queue
3595 properties:
3596 schema:
3597 type: string
3598 enum: [knowtation.task_proposal/v0]
3599 proposal_id: { type: string }
3600 proposal_kind: { type: string }
3601 task_id: { type: string, nullable: true }
3602 loop_id: { type: string, nullable: true }
3603 base_state_id: { type: string, nullable: true }
3604 scope:
3605 type: string
3606 enum: [personal, project, org]
3607 auto_approvable: { type: boolean }
3608 status: { type: string }
3609 review_queue: { type: string }
3610
3611 TaskInstanceProposalResponse:
3612 allOf:
3613 - $ref: '#/components/schemas/TaskProposalResponse'
3614 - type: object
3615 required: [occurrence_key]
3616 properties:
3617 schema:
3618 type: string
3619 enum: [knowtation.task_instance_proposal/v0]
3620 occurrence_key: { type: string }
3621
3622 FlowSummary:
3623 type: object
3624 required: [schema, flow_id, title, version, scope, summary, tags, step_count, updated, truncated]
3625 properties:
3626 schema:
3627 type: string
3628 enum: [knowtation.flow/v0]
3629 flow_id: { type: string }
3630 title: { type: string }
3631 version: { type: string }
3632 scope:
3633 type: string
3634 enum: [personal, project, org]
3635 summary: { type: string }
3636 tags:
3637 type: array
3638 maxItems: 32
3639 items: { type: string }
3640 step_count: { type: integer, minimum: 0 }
3641 updated: { type: string }
3642 truncated: { type: boolean }
3643
3644 FlowGetResponse:
3645 type: object
3646 required: [schema, vault_id, flow, steps]
3647 properties:
3648 schema:
3649 type: string
3650 enum: [knowtation.flow_get/v0]
3651 vault_id: { type: string }
3652 flow: { $ref: '#/components/schemas/Flow' }
3653 steps:
3654 type: array
3655 maxItems: 100
3656 items: { $ref: '#/components/schemas/FlowStep' }
3657
3658 FlowRun:
3659 type: object
3660 required:
3661 [schema, run_id, run_ref, flow_id, flow_version, scope, status, step_states, started, provenance]
3662 description: knowtation.flow_run/v0 — canonical run state (pointer-only).
3663 properties:
3664 schema:
3665 type: string
3666 enum: [knowtation.flow_run/v0]
3667 run_id: { type: string }
3668 run_ref:
3669 type: string
3670 description: Portable cross-system pointer (flow_run:…); resolves get/list lookups.
3671 flow_id: { type: string }
3672 flow_version: { type: string }
3673 scope:
3674 type: string
3675 enum: [personal, project, org]
3676 status:
3677 type: string
3678 enum: [pending, in_progress, blocked, done, abandoned]
3679 step_states:
3680 type: array
3681 maxItems: 200
3682 items:
3683 type: object
3684 required: [step_id, status, verified]
3685 properties:
3686 step_id: { type: string }
3687 status:
3688 type: string
3689 enum: [pending, in_progress, blocked, done, skipped]
3690 evidence_ref: { type: string, nullable: true }
3691 verified: { type: boolean }
3692 started: { type: string, format: date-time }
3693 provenance:
3694 type: object
3695 required: [actor, harness]
3696 properties:
3697 actor: { type: string, description: Hashed actor id only }
3698 harness: { type: string }
3699 task_ref: { type: string, nullable: true }
3700 external_ref: { type: string, nullable: true }
3701
3702 FlowRunGetResponse:
3703 type: object
3704 required: [schema, vault_id, run]
3705 properties:
3706 schema:
3707 type: string
3708 enum: [knowtation.flow_run_get/v0]
3709 vault_id: { type: string }
3710 run: { $ref: '#/components/schemas/FlowRun' }
3711
3712 FlowRunResponse:
3713 allOf:
3714 - $ref: '#/components/schemas/FlowRunGetResponse'
3715
3716 FlowRunListResponse:
3717 type: object
3718 required: [schema, vault_id, effective_scope, runs, truncated]
3719 properties:
3720 schema:
3721 type: string
3722 enum: [knowtation.flow_run_list/v0]
3723 vault_id: { type: string }
3724 effective_scope:
3725 type: string
3726 enum: [personal, project, org]
3727 runs:
3728 type: array
3729 maxItems: 200
3730 items: { $ref: '#/components/schemas/FlowRun' }
3731 truncated: { type: boolean }
3732
3733 FlowRunStartResponse:
3734 type: object
3735 required: [schema, run]
3736 properties:
3737 schema:
3738 type: string
3739 enum: [knowtation.flow_run_start/v0]
3740 run: { $ref: '#/components/schemas/FlowRun' }
3741
3742 FlowRunSubmitReviewResponse:
3743 type: object
3744 required: [schema, run, proposal_id]
3745 properties:
3746 schema:
3747 type: string
3748 enum: [knowtation.flow_run_submit_review/v0]
3749 run: { $ref: '#/components/schemas/FlowRun' }
3750 proposal_id: { type: string }
3751
3752 FlowProposeRequest:
3753 type: object
3754 required: [flow, steps, intent]
3755 description: Propose a new Flow. intent is untrusted and recorded verbatim.
3756 properties:
3757 flow: { $ref: '#/components/schemas/Flow' }
3758 steps:
3759 type: array
3760 maxItems: 100
3761 items: { $ref: '#/components/schemas/FlowStep' }
3762 intent: { type: string, minLength: 1 }
3763
3764 FlowProposeEditRequest:
3765 type: object
3766 required: [flow, steps, intent, base_version, base_state_id]
3767 description: >
3768 Propose an edit. base_version + base_state_id (flowst1_ token) gate
3769 optimistic concurrency; flow.version must exceed base_version.
3770 properties:
3771 flow: { $ref: '#/components/schemas/Flow' }
3772 steps:
3773 type: array
3774 maxItems: 100
3775 items: { $ref: '#/components/schemas/FlowStep' }
3776 intent: { type: string, minLength: 1 }
3777 base_version: { type: string }
3778 base_state_id: { type: string }
3779
3780 FlowImportRequest:
3781 type: object
3782 required: [bundle, intent]
3783 description: Import a portable bundle through the same scope-checked propose path.
3784 properties:
3785 bundle:
3786 type: object
3787 required: [flow, steps]
3788 properties:
3789 flow: { $ref: '#/components/schemas/Flow' }
3790 steps:
3791 type: array
3792 maxItems: 100
3793 items: { $ref: '#/components/schemas/FlowStep' }
3794 intent: { type: string, minLength: 1 }
3795 external_ref: { type: string }
3796 source_vault_hint: { type: string }
3797
3798 FlowProposalResponse:
3799 type: object
3800 required: [schema, proposal_id, flow_id, scope, auto_approvable, status, review_queue]
3801 description: >
3802 knowtation.flow_proposal/v0 envelope — pointers/labels only, never a
3803 rendered Flow body or secret. base_version/base_state_id are null for new.
3804 properties:
3805 schema:
3806 type: string
3807 enum: [knowtation.flow_proposal/v0]
3808 proposal_id: { type: string }
3809 flow_id: { type: string }
3810 base_version: { type: string, nullable: true }
3811 base_state_id: { type: string, nullable: true }
3812 scope:
3813 type: string
3814 enum: [personal, project, org]
3815 auto_approvable: { type: boolean }
3816 status:
3817 type: string
3818 enum: [proposed]
3819 review_queue: { type: string }
3820
3821 FlowExternalGrantMintRequest:
3822 type: object
3823 required: [flow_version, requested_tools]
3824 properties:
3825 flow_version: { type: string }
3826 requested_tools:
3827 type: array
3828 minItems: 1
3829 items: { type: string }
3830 ttl_seconds: { type: integer, minimum: 1 }
3831 actor_label: { type: string }
3832
3833 FlowExternalGrant:
3834 type: object
3835 required:
3836 - schema
3837 - grant_id
3838 - vault_id
3839 - scope
3840 - flow_id
3841 - flow_version
3842 - allowed_tools
3843 - allowed_harnesses
3844 - expires_at
3845 - issued_at
3846 - revoked_at
3847 - actor_hash
3848 - invocation_count
3849 properties:
3850 schema:
3851 type: string
3852 enum: [knowtation.flow_external_grant/v0]
3853 grant_id: { type: string }
3854 vault_id: { type: string }
3855 scope:
3856 type: string
3857 enum: [personal, project, org]
3858 flow_id: { type: string }
3859 flow_version: { type: string }
3860 allowed_tools:
3861 type: array
3862 items: { type: string }
3863 allowed_harnesses:
3864 type: array
3865 items: { type: string }
3866 expires_at: { type: string, format: date-time }
3867 issued_at: { type: string, format: date-time }
3868 revoked_at: { type: string, format: date-time, nullable: true }
3869 actor_hash: { type: string }
3870 max_invocations: { type: integer }
3871 invocation_count: { type: integer }
3872
3873 FlowExternalGrantMintResponse:
3874 type: object
3875 required: [schema, grant, bearer, expires_at]
3876 properties:
3877 schema:
3878 type: string
3879 enum: [knowtation.flow_external_grant_mint/v0]
3880 grant: { $ref: '#/components/schemas/FlowExternalGrant' }
3881 bearer: { type: string }
3882 expires_at: { type: string, format: date-time }
3883
3884 FlowExternalGrantListResponse:
3885 type: object
3886 required: [schema, vault_id, grants]
3887 properties:
3888 schema:
3889 type: string
3890 enum: [knowtation.flow_external_grant_list/v0]
3891 vault_id: { type: string }
3892 grants:
3893 type: array
3894 items: { $ref: '#/components/schemas/FlowExternalGrant' }
3895
3896 AgentIdentityRegisterRequest:
3897 type: object
3898 required: [kind]
3899 properties:
3900 kind:
3901 type: string
3902 enum: [user_owned, org_owned, delegate]
3903 agent_id: { type: string }
3904 label: { type: string }
3905 scope_ceiling:
3906 type: string
3907 enum: [personal, project, org]
3908
3909 DelegationProposalResponse:
3910 type: object
3911 required: [schema, proposal_id, intent]
3912 properties:
3913 schema:
3914 type: string
3915 enum: [knowtation.delegation_proposal/v0]
3916 proposal_id: { type: string }
3917 intent: { type: string }
3918 agent_id: { type: string }
3919 consent_id: { type: string }
3920
3921 AgentIdentity:
3922 type: object
3923 required:
3924 - schema
3925 - agent_id
3926 - kind
3927 - owner_ref
3928 - vault_id
3929 - scope_ceiling
3930 - status
3931 - created
3932 - updated
3933 properties:
3934 schema:
3935 type: string
3936 enum: [knowtation.agent_identity/v0]
3937 agent_id: { type: string }
3938 kind:
3939 type: string
3940 enum: [user_owned, org_owned, delegate]
3941 owner_ref: { type: string }
3942 vault_id: { type: string }
3943 scope_ceiling:
3944 type: string
3945 enum: [personal, project, org]
3946 label: { type: string }
3947 status:
3948 type: string
3949 enum: [active, suspended, revoked]
3950 created: { type: string, format: date-time }
3951 updated: { type: string, format: date-time }
3952
3953 AgentIdentityListResponse:
3954 type: object
3955 required: [schema, vault_id, identities]
3956 properties:
3957 schema:
3958 type: string
3959 enum: [knowtation.agent_identity_list/v0]
3960 vault_id: { type: string }
3961 identities:
3962 type: array
3963 items: { $ref: '#/components/schemas/AgentIdentity' }
3964
3965 DelegationConsentProposeRequest:
3966 type: object
3967 required: [delegate_agent_id, scope]
3968 properties:
3969 delegate_agent_id: { type: string }
3970 scope:
3971 type: string
3972 enum: [personal, project, org]
3973 workspace_id: { type: string }
3974 allowed_flow_ids:
3975 type: array
3976 items: { type: string }
3977 allowed_task_kinds:
3978 type: array
3979 items: { type: string }
3980 allowed_task_ids:
3981 type: array
3982 items: { type: string }
3983 expires_at: { type: string, format: date-time }
3984
3985 DelegationConsentProposeResponse:
3986 type: object
3987 required: [schema, proposal_id, intent, consent_id]
3988 properties:
3989 schema:
3990 type: string
3991 enum: [knowtation.delegation_proposal/v0]
3992 proposal_id: { type: string }
3993 intent: { type: string }
3994 consent_id: { type: string }
3995 consent_preview: { $ref: '#/components/schemas/DelegationConsent' }
3996
3997 DelegationConsent:
3998 type: object
3999 required:
4000 - schema
4001 - consent_id
4002 - principal_ref
4003 - delegate_agent_id
4004 - scope
4005 - revoked_at
4006 - evidence_ref
4007 - created
4008 properties:
4009 schema:
4010 type: string
4011 enum: [knowtation.delegation_consent/v0]
4012 consent_id: { type: string }
4013 principal_ref: { type: string }
4014 delegate_agent_id: { type: string }
4015 scope:
4016 type: string
4017 enum: [personal, project, org]
4018 workspace_id: { type: string }
4019 allowed_flow_ids:
4020 type: array
4021 items: { type: string }
4022 allowed_task_kinds:
4023 type: array
4024 items: { type: string }
4025 allowed_task_ids:
4026 type: array
4027 items: { type: string }
4028 expires_at: { type: string, format: date-time }
4029 revoked_at: { type: string, format: date-time, nullable: true }
4030 evidence_ref: { type: string }
4031 created: { type: string, format: date-time }
4032
4033 DelegationGrantMintRequest:
4034 type: object
4035 required: [consent_id, actor_agent_id]
4036 properties:
4037 consent_id: { type: string }
4038 actor_agent_id: { type: string }
4039 task_ref: { type: string }
4040 run_ref: { type: string }
4041 flow_id: { type: string }
4042 flow_version: { type: string }
4043 ttl_seconds: { type: integer, minimum: 1 }
4044
4045 DelegationGrant:
4046 type: object
4047 required:
4048 - schema
4049 - grant_id
4050 - consent_id
4051 - actor_agent_id
4052 - principal_ref
4053 - scope
4054 - expires_at
4055 - revoked_at
4056 - action_count
4057 - issued_at
4058 properties:
4059 schema:
4060 type: string
4061 enum: [knowtation.delegation_grant/v0]
4062 grant_id: { type: string }
4063 consent_id: { type: string }
4064 actor_agent_id: { type: string }
4065 principal_ref: { type: string }
4066 scope:
4067 type: string
4068 enum: [personal, project, org]
4069 workspace_id: { type: string }
4070 task_ref: { type: string }
4071 run_ref: { type: string }
4072 flow_id: { type: string }
4073 flow_version: { type: string }
4074 expires_at: { type: string, format: date-time }
4075 revoked_at: { type: string, format: date-time, nullable: true }
4076 max_actions: { type: integer }
4077 action_count: { type: integer }
4078 issued_at: { type: string, format: date-time }
4079
4080 DelegationGrantMintResponse:
4081 type: object
4082 required: [schema, grant, bearer, expires_at]
4083 properties:
4084 schema:
4085 type: string
4086 enum: [knowtation.delegation_grant_mint/v0]
4087 grant: { $ref: '#/components/schemas/DelegationGrant' }
4088 bearer: { type: string }
4089 expires_at: { type: string, format: date-time }
4090
4091 DelegationGrantListResponse:
4092 type: object
4093 required: [schema, vault_id, grants]
4094 properties:
4095 schema:
4096 type: string
4097 enum: [knowtation.delegation_grant_list/v0]
4098 vault_id: { type: string }
4099 grants:
4100 type: array
4101 items: { $ref: '#/components/schemas/DelegationGrant' }
4102
4103 DelegationAuditAppendRequest:
4104 type: object
4105 required: [grant_id, actor_agent_id, action, evidence_refs]
4106 properties:
4107 grant_id: { type: string }
4108 actor_agent_id: { type: string }
4109 principal_ref: { type: string }
4110 action:
4111 type: string
4112 enum: [advance_step, complete_task, propose_outcome, invoke_tool, mint_subgrant]
4113 evidence_refs:
4114 type: array
4115 minItems: 1
4116 items: { type: string }
4117 task_ref: { type: string }
4118 run_ref: { type: string }
4119 flow_id: { type: string }
4120 flow_version: { type: string }
4121 step_id: { type: string }
4122 execution_location:
4123 type: string
4124 enum: [local, hosted, hybrid]
4125
4126 DelegationAudit:
4127 type: object
4128 required:
4129 - schema
4130 - audit_id
4131 - grant_id
4132 - actor_agent_id
4133 - principal_ref
4134 - action
4135 - evidence_refs
4136 - occurred_at
4137 properties:
4138 schema:
4139 type: string
4140 enum: [knowtation.delegation_audit/v0]
4141 audit_id: { type: string }
4142 grant_id: { type: string }
4143 actor_agent_id: { type: string }
4144 principal_ref: { type: string }
4145 task_ref: { type: string }
4146 run_ref: { type: string }
4147 flow_id: { type: string }
4148 flow_version: { type: string }
4149 step_id: { type: string }
4150 action:
4151 type: string
4152 enum: [advance_step, complete_task, propose_outcome, invoke_tool, mint_subgrant]
4153 evidence_refs:
4154 type: array
4155 items: { type: string }
4156 occurred_at: { type: string, format: date-time }
4157 execution_location:
4158 type: string
4159 enum: [local, hosted, hybrid]
4160
4161 FlowProjectResponse:
4162 type: object
4163 required: [schema, vault_id, projection, staleness, generator]
4164 properties:
4165 schema:
4166 type: string
4167 enum: [knowtation.flow_project/v0]
4168 vault_id: { type: string }
4169 projection: { $ref: '#/components/schemas/FlowProjection' }
4170 staleness: { $ref: '#/components/schemas/FlowProjectionStaleness' }
4171 generator: { $ref: '#/components/schemas/FlowProjectionGenerator' }
4172
4173 FlowProjection:
4174 type: object
4175 required: [schema, flow_id, flow_version, harness, rendered, generated_from_canonical, editable]
4176 properties:
4177 schema:
4178 type: string
4179 enum: [knowtation.flow_projection/v0]
4180 flow_id: { type: string }
4181 flow_version: { type: string }
4182 harness:
4183 type: string
4184 enum: [cursor_rule, cursor_skill, mcp_prompt, cli_runbook, agent_bundle]
4185 rendered:
4186 type: string
4187 maxLength: 65536
4188 generated_from_canonical:
4189 type: boolean
4190 enum: [true]
4191 editable:
4192 type: boolean
4193 enum: [false]
4194 fidelity:
4195 type: object
4196 required: [dropped_fields]
4197 properties:
4198 dropped_fields:
4199 type: array
4200 items: { type: string }
4201 notes: { type: string }
4202
4203 FlowProjectionStaleness:
4204 type: object
4205 required: [stale, projection_version, latest_version]
4206 properties:
4207 stale: { type: boolean }
4208 projection_version: { type: string }
4209 latest_version: { type: string }
4210
4211 FlowProjectionGenerator:
4212 type: object
4213 required: [generator_version, content_hash, generated_at]
4214 properties:
4215 generator_version: { type: string }
4216 content_hash: { type: string }
4217 generated_at: { type: string }
4218
4219 Flow:
4220 type: object
4221 required: [schema, flow_id, title, version, scope, summary, steps, updated, truncated]
4222 properties:
4223 schema:
4224 type: string
4225 enum: [knowtation.flow/v0]
4226 flow_id: { type: string }
4227 title: { type: string }
4228 version: { type: string }
4229 scope:
4230 type: string
4231 enum: [personal, project, org]
4232 summary: { type: string }
4233 tags:
4234 type: array
4235 maxItems: 32
4236 items: { type: string }
4237 steps:
4238 type: array
4239 maxItems: 100
4240 items: { type: string }
4241 inputs:
4242 type: array
4243 items:
4244 type: object
4245 required: [name, type, required]
4246 properties:
4247 name: { type: string }
4248 type: { type: string }
4249 required: { type: boolean }
4250 vault_mirror_path: { type: string, nullable: true }
4251 updated: { type: string }
4252 truncated: { type: boolean }
4253
4254 FlowStep:
4255 type: object
4256 required: [schema, step_id, flow_id, ordinal, owned_job, instruction, trigger, when_not_to_run, boundaries, output_shape, verification, automatable]
4257 properties:
4258 schema:
4259 type: string
4260 enum: [knowtation.flow_step/v0]
4261 step_id: { type: string }
4262 flow_id: { type: string }
4263 ordinal: { type: integer, minimum: 1 }
4264 owned_job: { type: string }
4265 instruction: { type: string }
4266 trigger: { type: string }
4267 when_not_to_run: { type: string }
4268 requires:
4269 type: array
4270 items:
4271 type: object
4272 required: [kind, id]
4273 properties:
4274 kind:
4275 type: string
4276 enum: [vault_scope, tool, file, artifact]
4277 id: { type: string }
4278 boundaries:
4279 type: array
4280 items: { type: string }
4281 skill_refs:
4282 type: array
4283 items:
4284 type: object
4285 required: [kind, id]
4286 properties:
4287 kind:
4288 type: string
4289 enum: [mcp_prompt, skill_pack, cli, external_tool]
4290 id: { type: string }
4291 inputs:
4292 type: array
4293 items:
4294 type: object
4295 required: [name, from]
4296 properties:
4297 name: { type: string }
4298 from: { type: string }
4299 outputs:
4300 type: array
4301 items:
4302 type: object
4303 required: [name, type]
4304 properties:
4305 name: { type: string }
4306 type: { type: string }
4307 output_shape: { type: string }
4308 verification:
4309 type: object
4310 required: [kind, evidence_required, description]
4311 properties:
4312 kind:
4313 type: string
4314 enum: [human_review, artifact_exists, value_match, test_pass, agent_check]
4315 evidence_required: { type: boolean }
4316 description: { type: string }
4317 automatable:
4318 type: string
4319 enum: [manual, agent_assisted, automatable]
File History 8 commits
sha256:49f768e5fb72e8d17321410817422fc5cab8f0a1b66a1e1da8bdd4cd251c4f7e Merge 'feat/ourware-landing-rebrand' into 'main' — proposal… Human 18 days ago
sha256:e4c529f14a0bb908c1caaaeb3f95f3623a1a82e636e7e3722ca2cd3dc9821263 security: npm audit fix pre-bridge 2026-07-29 Human 41 days ago
sha256:b5f647cb9c409f563d4671fe3fc05ddea01fabfed9b41fc11cb923588e1c1baf mirror: GitHub Phase A durable MCP OAuth (#270) Human minor 57 days ago
sha256:873e30b7fafe601346295f8f4289f388f21d8f715f28584d5481899ba2b714fc Merge pull request #249 from aaronrene/muse-mirror Agent 74 days ago
sha256:d8c648b20a4d53b2673c5c082ee7edfa7b2fc9b11080832da1f38807b6bf940b fix(7C-L1b): route hosted delegation proposals through cani… Human minor 77 days ago
sha256:0d530f9ef27b8b75547d1db7701a74bc77b77aa8f3d7fa3a8672cf2af36e63bb reconcile: import GitHub-direct RBAC/OAuth/companion and ho… Human minor 90 days ago
sha256:2827ba9e7632a4b141c50caf1e8f7d77abbc3515be20e7465f2bccb0ac4edf91 fix: repair endpoint now sets has_active_subscription when … Human minor 97 days ago