@gitgov/core 2.7.2 → 2.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/src/index.js CHANGED
@@ -20,7 +20,6 @@ var adapters_exports = {};
20
20
  __export(adapters_exports, {
21
21
  AgentAdapter: () => AgentAdapter,
22
22
  BacklogAdapter: () => BacklogAdapter,
23
- ChangelogAdapter: () => ChangelogAdapter,
24
23
  ExecutionAdapter: () => ExecutionAdapter,
25
24
  FeedbackAdapter: () => FeedbackAdapter,
26
25
  IdentityAdapter: () => IdentityAdapter,
@@ -29,6 +28,25 @@ __export(adapters_exports, {
29
28
  });
30
29
 
31
30
  // src/record_types/common.types.ts
31
+ var RECORD_TYPES = [
32
+ "actor",
33
+ "agent",
34
+ "cycle",
35
+ "task",
36
+ "execution",
37
+ "feedback"
38
+ ];
39
+ var DIR_TO_TYPE = {
40
+ "tasks": "task",
41
+ "cycles": "cycle",
42
+ "executions": "execution",
43
+ "feedbacks": "feedback",
44
+ "actors": "actor",
45
+ "agents": "agent"
46
+ };
47
+ var TYPE_TO_DIR = Object.fromEntries(
48
+ Object.entries(DIR_TO_TYPE).map(([dir, type]) => [type, dir])
49
+ );
32
50
  var GitGovError = class extends Error {
33
51
  constructor(message, code) {
34
52
  super(message);
@@ -74,7 +92,7 @@ var actor_record_schema_default = {
74
92
  $schema: "http://json-schema.org/draft-07/schema#",
75
93
  $id: "actor_record_schema.json",
76
94
  title: "ActorRecord",
77
- description: "Canonical schema for actor records as defined in actor_protocol.md",
95
+ description: "Canonical schema for actor records as defined in 02_actor.md",
78
96
  additionalProperties: false,
79
97
  type: "object",
80
98
  required: [
@@ -169,8 +187,9 @@ var agent_record_schema_default = {
169
187
  $schema: "http://json-schema.org/draft-07/schema#",
170
188
  $id: "agent_record_schema.json",
171
189
  title: "AgentRecord",
172
- description: "Canonical schema for agent operational manifests.",
190
+ description: "Canonical schema for agent operational manifests \u2014 the work contract that defines how an agent is invoked.",
173
191
  type: "object",
192
+ additionalProperties: false,
174
193
  required: [
175
194
  "id",
176
195
  "engine"
@@ -178,8 +197,13 @@ var agent_record_schema_default = {
178
197
  properties: {
179
198
  id: {
180
199
  type: "string",
181
- pattern: "^agent:[a-z0-9:-]+$",
182
- description: "Unique identifier for the agent, linking to an ActorRecord."
200
+ pattern: "^agent(:[a-z0-9-]+)+$",
201
+ description: "Unique identifier for the agent, linking 1:1 to an ActorRecord of type agent.",
202
+ examples: [
203
+ "agent:scribe",
204
+ "agent:aion",
205
+ "agent:camilo:cursor"
206
+ ]
183
207
  },
184
208
  status: {
185
209
  type: "string",
@@ -187,63 +211,12 @@ var agent_record_schema_default = {
187
211
  "active",
188
212
  "archived"
189
213
  ],
190
- default: "active"
191
- },
192
- triggers: {
193
- type: "array",
194
- default: [],
195
- description: "Optional list of triggers that activate the agent.\nAdditional fields are allowed and depend on trigger type:\n- webhook triggers: 'event' (event identifier), 'filter' (condition)\n- scheduled triggers: 'cron' (cron expression)\n- manual triggers: 'command' (example CLI command)\n",
196
- items: {
197
- type: "object",
198
- properties: {
199
- type: {
200
- type: "string",
201
- enum: [
202
- "manual",
203
- "webhook",
204
- "scheduled"
205
- ],
206
- description: "Type of trigger that activates the agent"
207
- }
208
- },
209
- required: [
210
- "type"
211
- ],
212
- additionalProperties: true
213
- }
214
- },
215
- knowledge_dependencies: {
216
- type: "array",
217
- default: [],
218
- items: {
219
- type: "string",
220
- description: "Glob patterns for blueprint files this agent needs access to"
221
- }
222
- },
223
- prompt_engine_requirements: {
224
- type: "object",
225
- properties: {
226
- roles: {
227
- type: "array",
228
- items: {
229
- type: "string"
230
- }
231
- },
232
- skills: {
233
- type: "array",
234
- items: {
235
- type: "string"
236
- }
237
- }
238
- }
239
- },
240
- metadata: {
241
- type: "object",
242
- description: "Optional framework-specific or deployment-specific metadata for agent extensions.\nCommon use cases: framework identification (langchain, google-adk), deployment info (provider, image, region),\ncost tracking (cost_per_invocation, currency), tool capabilities, maintainer info.\nThis field does NOT affect agent execution - it is purely informational.\n",
243
- additionalProperties: true
214
+ default: "active",
215
+ description: "Operational status. An archived agent cannot be invoked."
244
216
  },
245
217
  engine: {
246
218
  type: "object",
219
+ description: "Invocation specification \u2014 defines how the agent is executed. Uses oneOf with 4 variants: local, api, mcp, custom.",
247
220
  oneOf: [
248
221
  {
249
222
  required: [
@@ -290,7 +263,8 @@ var agent_record_schema_default = {
290
263
  "GET",
291
264
  "PUT"
292
265
  ],
293
- default: "POST"
266
+ default: "POST",
267
+ description: "HTTP method"
294
268
  },
295
269
  auth: {
296
270
  type: "object",
@@ -336,7 +310,7 @@ var agent_record_schema_default = {
336
310
  },
337
311
  tool: {
338
312
  type: "string",
339
- description: "Name of the MCP tool to invoke. If not specified, defaults to agentId without 'agent:' prefix."
313
+ description: "Name of the MCP tool to invoke. If omitted, the agent has access to all tools on the server."
340
314
  },
341
315
  auth: {
342
316
  type: "object",
@@ -385,6 +359,60 @@ var agent_record_schema_default = {
385
359
  }
386
360
  }
387
361
  ]
362
+ },
363
+ triggers: {
364
+ type: "array",
365
+ default: [],
366
+ description: "Optional list of triggers that activate the agent.\nAdditional fields are allowed and depend on trigger type:\n- manual: 'command' (example CLI command)\n- webhook: 'event' (event identifier), 'filter' (condition)\n- scheduled: 'cron' (cron expression)\n",
367
+ items: {
368
+ type: "object",
369
+ properties: {
370
+ type: {
371
+ type: "string",
372
+ enum: [
373
+ "manual",
374
+ "webhook",
375
+ "scheduled"
376
+ ],
377
+ description: "Type of trigger that activates the agent"
378
+ }
379
+ },
380
+ required: [
381
+ "type"
382
+ ],
383
+ additionalProperties: true
384
+ }
385
+ },
386
+ knowledge_dependencies: {
387
+ type: "array",
388
+ default: [],
389
+ items: {
390
+ type: "string",
391
+ description: "Glob patterns for files this agent needs access to"
392
+ }
393
+ },
394
+ prompt_engine_requirements: {
395
+ type: "object",
396
+ description: "Requirements for prompt composition \u2014 roles and skills the agent needs.",
397
+ properties: {
398
+ roles: {
399
+ type: "array",
400
+ items: {
401
+ type: "string"
402
+ }
403
+ },
404
+ skills: {
405
+ type: "array",
406
+ items: {
407
+ type: "string"
408
+ }
409
+ }
410
+ }
411
+ },
412
+ metadata: {
413
+ type: "object",
414
+ description: "Optional framework-specific or deployment-specific metadata.\nCommon use cases: framework identification (langchain, google-adk), deployment info,\ncost tracking, tool capabilities, maintainer info.\nThis field does NOT affect agent execution \u2014 it is purely informational.\n",
415
+ additionalProperties: true
388
416
  }
389
417
  },
390
418
  examples: [
@@ -615,193 +643,12 @@ var agent_record_schema_default = {
615
643
  ]
616
644
  };
617
645
 
618
- // src/record_schemas/generated/changelog_record_schema.json
619
- var changelog_record_schema_default = {
620
- $schema: "http://json-schema.org/draft-07/schema#",
621
- $id: "changelog_record_schema.json",
622
- title: "ChangelogRecord",
623
- description: "Canonical schema for changelog records - aggregates N tasks into 1 release note",
624
- additionalProperties: false,
625
- type: "object",
626
- required: [
627
- "id",
628
- "title",
629
- "description",
630
- "relatedTasks",
631
- "completedAt"
632
- ],
633
- properties: {
634
- id: {
635
- type: "string",
636
- pattern: "^\\d{10}-changelog-[a-z0-9-]{1,50}$",
637
- maxLength: 71,
638
- description: "Unique identifier for the changelog entry",
639
- examples: [
640
- "1752707800-changelog-sistema-autenticacion-v1",
641
- "1752707800-changelog-sprint-24-api-performance"
642
- ]
643
- },
644
- title: {
645
- type: "string",
646
- minLength: 10,
647
- maxLength: 150,
648
- description: "Executive title of the deliverable",
649
- examples: [
650
- "Sistema de Autenticaci\xF3n Completo v1.0",
651
- "Sprint 24 - Performance Optimizations"
652
- ]
653
- },
654
- description: {
655
- type: "string",
656
- minLength: 20,
657
- maxLength: 5e3,
658
- description: "Detailed description of the value delivered, including key decisions and impact"
659
- },
660
- relatedTasks: {
661
- type: "array",
662
- items: {
663
- type: "string",
664
- pattern: "^\\d{10}-task-[a-z0-9-]{1,50}$"
665
- },
666
- minItems: 1,
667
- description: "IDs of tasks that compose this deliverable (minimum 1 required)"
668
- },
669
- completedAt: {
670
- type: "number",
671
- minimum: 0,
672
- description: "Unix timestamp in seconds when the deliverable was completed"
673
- },
674
- relatedCycles: {
675
- type: "array",
676
- items: {
677
- type: "string",
678
- pattern: "^\\d{10}-cycle-[a-z0-9-]{1,50}$"
679
- },
680
- default: [],
681
- description: "Optional IDs of cycles related to this deliverable"
682
- },
683
- relatedExecutions: {
684
- type: "array",
685
- items: {
686
- type: "string",
687
- pattern: "^\\d{10}-exec-[a-z0-9-]{1,50}$"
688
- },
689
- default: [],
690
- description: "Optional IDs of key execution records related to this work"
691
- },
692
- version: {
693
- type: "string",
694
- minLength: 1,
695
- maxLength: 50,
696
- description: "Optional version or release identifier (e.g., 'v1.0.0', 'sprint-24')",
697
- examples: [
698
- "v1.0.0",
699
- "v2.1.3",
700
- "sprint-24"
701
- ]
702
- },
703
- tags: {
704
- type: "array",
705
- items: {
706
- type: "string",
707
- pattern: "^[a-z0-9-]+(:[a-z0-9-]+)*$"
708
- },
709
- default: [],
710
- description: "Optional tags for categorization (e.g., 'feature:auth', 'bugfix', 'security')"
711
- },
712
- commits: {
713
- type: "array",
714
- items: {
715
- type: "string",
716
- maxLength: 100
717
- },
718
- default: [],
719
- description: "Optional list of git commit hashes related to this deliverable"
720
- },
721
- files: {
722
- type: "array",
723
- items: {
724
- type: "string",
725
- maxLength: 500
726
- },
727
- default: [],
728
- description: "Optional list of main files that were created or modified"
729
- },
730
- notes: {
731
- type: "string",
732
- maxLength: 3e3,
733
- description: "Optional additional context, decisions, or learnings"
734
- }
735
- },
736
- examples: [
737
- {
738
- id: "1752707800-changelog-sistema-autenticacion-v1",
739
- title: "Sistema de Autenticaci\xF3n Completo v1.0",
740
- description: "Implementaci\xF3n completa del sistema de autenticaci\xF3n con OAuth2, 2FA via TOTP, recuperaci\xF3n de contrase\xF1a, y UI responsive. Incluye tests E2E completos (95% coverage) y documentaci\xF3n t\xE9cnica actualizada.",
741
- relatedTasks: [
742
- "1752274500-task-crear-ui-login",
743
- "1752274600-task-integrar-oauth2-backend",
744
- "1752274700-task-implementar-2fa-totp",
745
- "1752274800-task-tests-e2e-auth",
746
- "1752274900-task-documentar-flujo-auth"
747
- ],
748
- completedAt: 1752707800,
749
- relatedCycles: [
750
- "1752200000-cycle-q1-auth-milestone"
751
- ],
752
- relatedExecutions: [
753
- "1752274550-exec-analisis-auth-providers",
754
- "1752707750-exec-final-integration-test"
755
- ],
756
- version: "v1.0.0",
757
- tags: [
758
- "feature:auth",
759
- "security",
760
- "frontend",
761
- "backend"
762
- ],
763
- commits: [
764
- "abc123def",
765
- "456ghi789",
766
- "jkl012mno"
767
- ],
768
- files: [
769
- "src/pages/Login.tsx",
770
- "src/services/auth.ts",
771
- "src/components/TwoFactorSetup.tsx",
772
- "e2e/auth.spec.ts"
773
- ],
774
- notes: "Decisi\xF3n t\xE9cnica: Usamos NextAuth.js despu\xE9s de evaluar Passport.js. El 2FA se implement\xF3 con TOTP (Google Authenticator compatible) en lugar de SMS por seguridad y costo."
775
- },
776
- {
777
- id: "1752707900-changelog-hotfix-payment-timeout",
778
- title: "Hotfix: Critical Payment Timeout Fix",
779
- description: "Fixed critical payment timeout issue affecting 15% of transactions. Increased timeout from 5s to 30s and added circuit breaker pattern for third-party API calls.",
780
- relatedTasks: [
781
- "1752707850-task-fix-payment-timeout",
782
- "1752707870-task-add-circuit-breaker"
783
- ],
784
- completedAt: 1752707900,
785
- version: "v1.2.1",
786
- tags: [
787
- "hotfix",
788
- "critical",
789
- "payment"
790
- ],
791
- commits: [
792
- "xyz789abc"
793
- ],
794
- notes: "Emergency response to production incident. Deployed to production within 2 hours."
795
- }
796
- ]
797
- };
798
-
799
646
  // src/record_schemas/generated/cycle_record_schema.json
800
647
  var cycle_record_schema_default = {
801
648
  $schema: "http://json-schema.org/draft-07/schema#",
802
649
  $id: "cycle_record_schema.json",
803
650
  title: "CycleRecord",
804
- description: "Canonical schema for cycle records - strategic grouping of work",
651
+ description: "Canonical schema for cycle records \u2014 strategic grouping of work into sprints, milestones, or roadmaps.",
805
652
  additionalProperties: false,
806
653
  type: "object",
807
654
  required: [
@@ -814,7 +661,7 @@ var cycle_record_schema_default = {
814
661
  type: "string",
815
662
  pattern: "^\\d{10}-cycle-[a-z0-9-]{1,50}$",
816
663
  maxLength: 67,
817
- description: "Unique identifier for the cycle (10 timestamp + 1 dash + 5 'cycle' + 1 dash + max 50 slug = 67 max)",
664
+ description: "Unique identifier for the cycle (10 timestamp + 1 dash + 5 'cycle' + 1 dash + max 50 slug = 67 max).",
818
665
  examples: [
819
666
  "1754400000-cycle-sprint-24-api-performance",
820
667
  "1754500000-cycle-auth-system-v2",
@@ -825,7 +672,7 @@ var cycle_record_schema_default = {
825
672
  type: "string",
826
673
  minLength: 1,
827
674
  maxLength: 256,
828
- description: "Human-readable title for the cycle (e.g., 'Sprint 24', 'Auth v2.0', 'Q4 2025')",
675
+ description: "Human-readable title for the cycle (e.g., 'Sprint 24', 'Auth v2.0', 'Q4 2025').",
829
676
  examples: [
830
677
  "Sprint 24 - API Performance",
831
678
  "Authentication System v2.0",
@@ -840,7 +687,7 @@ var cycle_record_schema_default = {
840
687
  "completed",
841
688
  "archived"
842
689
  ],
843
- description: "The lifecycle status of the cycle"
690
+ description: "The lifecycle status of the cycle."
844
691
  },
845
692
  taskIds: {
846
693
  type: "array",
@@ -850,7 +697,7 @@ var cycle_record_schema_default = {
850
697
  maxLength: 66
851
698
  },
852
699
  default: [],
853
- description: "Optional array of Task IDs that belong to this cycle. Can be empty for cycles that only contain child cycles. (10 timestamp + 1 dash + 4 'task' + 1 dash + max 50 slug = 66 max)",
700
+ description: "Optional array of Task IDs that belong to this cycle. Bidirectional with TaskRecord.cycleIds. Can be empty for container cycles.",
854
701
  examples: [
855
702
  [
856
703
  "1752274500-task-optimizar-endpoint-search",
@@ -866,7 +713,7 @@ var cycle_record_schema_default = {
866
713
  maxLength: 67
867
714
  },
868
715
  default: [],
869
- description: "Optional array of Cycle IDs that are children of this cycle, allowing for hierarchies (e.g., Q1 containing Sprint 1, Sprint 2, Sprint 3). (10 timestamp + 1 dash + 5 'cycle' + 1 dash + max 50 slug = 67 max)",
716
+ description: "Optional array of child Cycle IDs for hierarchical composition (e.g., Q1 containing Sprint 1, Sprint 2, Sprint 3).",
870
717
  examples: [
871
718
  [
872
719
  "1754400000-cycle-sprint-24",
@@ -900,9 +747,29 @@ var cycle_record_schema_default = {
900
747
  },
901
748
  notes: {
902
749
  type: "string",
903
- minLength: 0,
904
- maxLength: 1e4,
905
- description: "Optional description of the cycle's goals, objectives, and context"
750
+ minLength: 1,
751
+ description: "Optional description of the cycle's goals, objectives, and context."
752
+ },
753
+ metadata: {
754
+ type: "object",
755
+ additionalProperties: true,
756
+ description: "Optional structured data for machine consumption.\nUse this field for domain-specific data that needs to be programmatically processed.\nExtends the strategic grouping with structured, queryable attributes.\nCommon use cases: epic lifecycle, sprint configuration, OKR tracking, budget allocation.\n",
757
+ examples: [
758
+ {
759
+ epic: true,
760
+ phase: "active",
761
+ files: {
762
+ overview: "overview.md",
763
+ roadmap: "roadmap.md",
764
+ plan: "implementation_plan.md"
765
+ }
766
+ },
767
+ {
768
+ sprint: 24,
769
+ velocity: 42,
770
+ team: "backend"
771
+ }
772
+ ]
906
773
  }
907
774
  },
908
775
  examples: [
@@ -920,7 +787,7 @@ var cycle_record_schema_default = {
920
787
  "team:backend",
921
788
  "focus:performance"
922
789
  ],
923
- notes: "Objetivo: Reducir la latencia p95 de la API por debajo de 200ms y preparar infraestructura para Black Friday."
790
+ notes: "Objective: Reduce API p95 latency below 200ms and prepare infrastructure for Black Friday."
924
791
  },
925
792
  {
926
793
  id: "1754500000-cycle-auth-system-v2",
@@ -937,7 +804,7 @@ var cycle_record_schema_default = {
937
804
  "security",
938
805
  "feature:auth"
939
806
  ],
940
- notes: "Milestone mayor: Sistema completo de autenticaci\xF3n con OAuth2, 2FA, y gesti\xF3n avanzada de sesiones. Cr\xEDtico para lanzamiento Q4."
807
+ notes: "Major milestone: Complete authentication system with OAuth2, 2FA, and advanced session management. Critical for Q4 launch."
941
808
  },
942
809
  {
943
810
  id: "1754600000-cycle-q4-2025-growth",
@@ -953,7 +820,7 @@ var cycle_record_schema_default = {
953
820
  "strategy:growth",
954
821
  "okr:scale-to-1m-users"
955
822
  ],
956
- notes: "Objetivo trimestral: Escalar a 1M usuarios activos. Incluye mejoras de performance, nuevo sistema de auth, y lanzamiento de app m\xF3vil."
823
+ notes: "Quarterly objective: Scale to 1M active users. Includes performance improvements, new auth system, and mobile app launch."
957
824
  }
958
825
  ]
959
826
  };
@@ -971,10 +838,8 @@ var embedded_metadata_schema_default = {
971
838
  properties: {
972
839
  version: {
973
840
  type: "string",
974
- enum: [
975
- "1.0"
976
- ],
977
- description: "Version of the embedded metadata format."
841
+ pattern: "^\\d+\\.\\d+$",
842
+ description: 'Protocol version in MAJOR.MINOR format (e.g. "1.1", "2.0").'
978
843
  },
979
844
  type: {
980
845
  type: "string",
@@ -983,12 +848,23 @@ var embedded_metadata_schema_default = {
983
848
  "agent",
984
849
  "task",
985
850
  "execution",
986
- "changelog",
987
851
  "feedback",
988
- "cycle"
852
+ "cycle",
853
+ "workflow",
854
+ "custom"
989
855
  ],
990
856
  description: "The type of the record contained in the payload."
991
857
  },
858
+ schemaUrl: {
859
+ type: "string",
860
+ format: "uri",
861
+ description: "URL to a custom schema for the payload. Required when type is 'custom'."
862
+ },
863
+ schemaChecksum: {
864
+ type: "string",
865
+ pattern: "^[a-fA-F0-9]{64}$",
866
+ description: "SHA-256 checksum of the custom schema. Required when type is 'custom'."
867
+ },
992
868
  payloadChecksum: {
993
869
  type: "string",
994
870
  pattern: "^[a-fA-F0-9]{64}$",
@@ -1003,14 +879,14 @@ var embedded_metadata_schema_default = {
1003
879
  keyId: {
1004
880
  type: "string",
1005
881
  pattern: "^(human|agent)(:[a-z0-9-]+)+$",
1006
- description: "The Actor ID of the signer (must match ActorRecord.id pattern)."
882
+ description: "The Actor ID of the signer. Supports scoped identifiers (e.g. agent:camilo:cursor)."
1007
883
  },
1008
884
  role: {
1009
885
  type: "string",
1010
886
  pattern: "^([a-z-]+|custom:[a-z0-9-]+)$",
1011
887
  minLength: 1,
1012
888
  maxLength: 50,
1013
- description: "The context role of the signature (e.g., 'author', 'reviewer', 'auditor', or 'custom:*')."
889
+ description: "The context role of the signature (e.g., 'author', 'reviewer', or 'custom:*')."
1014
890
  },
1015
891
  notes: {
1016
892
  type: "string",
@@ -1025,6 +901,7 @@ var embedded_metadata_schema_default = {
1025
901
  },
1026
902
  timestamp: {
1027
903
  type: "integer",
904
+ minimum: 16e8,
1028
905
  description: "Unix timestamp of the signature."
1029
906
  }
1030
907
  },
@@ -1058,7 +935,32 @@ var embedded_metadata_schema_default = {
1058
935
  "payload"
1059
936
  ],
1060
937
  additionalProperties: false,
1061
- oneOf: [
938
+ allOf: [
939
+ {
940
+ if: {
941
+ properties: {
942
+ header: {
943
+ type: "object",
944
+ properties: {
945
+ type: {
946
+ const: "custom"
947
+ }
948
+ }
949
+ }
950
+ }
951
+ },
952
+ then: {
953
+ properties: {
954
+ header: {
955
+ type: "object",
956
+ required: [
957
+ "schemaUrl",
958
+ "schemaChecksum"
959
+ ]
960
+ }
961
+ }
962
+ }
963
+ },
1062
964
  {
1063
965
  if: {
1064
966
  properties: {
@@ -1078,8 +980,7 @@ var embedded_metadata_schema_default = {
1078
980
  $ref: "ref:actor_record_schema"
1079
981
  }
1080
982
  }
1081
- },
1082
- else: false
983
+ }
1083
984
  },
1084
985
  {
1085
986
  if: {
@@ -1100,8 +1001,7 @@ var embedded_metadata_schema_default = {
1100
1001
  $ref: "ref:agent_record_schema"
1101
1002
  }
1102
1003
  }
1103
- },
1104
- else: false
1004
+ }
1105
1005
  },
1106
1006
  {
1107
1007
  if: {
@@ -1122,8 +1022,7 @@ var embedded_metadata_schema_default = {
1122
1022
  $ref: "ref:task_record_schema"
1123
1023
  }
1124
1024
  }
1125
- },
1126
- else: false
1025
+ }
1127
1026
  },
1128
1027
  {
1129
1028
  if: {
@@ -1144,8 +1043,7 @@ var embedded_metadata_schema_default = {
1144
1043
  $ref: "ref:execution_record_schema"
1145
1044
  }
1146
1045
  }
1147
- },
1148
- else: false
1046
+ }
1149
1047
  },
1150
1048
  {
1151
1049
  if: {
@@ -1154,7 +1052,7 @@ var embedded_metadata_schema_default = {
1154
1052
  type: "object",
1155
1053
  properties: {
1156
1054
  type: {
1157
- const: "changelog"
1055
+ const: "feedback"
1158
1056
  }
1159
1057
  }
1160
1058
  }
@@ -1163,11 +1061,10 @@ var embedded_metadata_schema_default = {
1163
1061
  then: {
1164
1062
  properties: {
1165
1063
  payload: {
1166
- $ref: "ref:changelog_record_schema"
1064
+ $ref: "ref:feedback_record_schema"
1167
1065
  }
1168
1066
  }
1169
- },
1170
- else: false
1067
+ }
1171
1068
  },
1172
1069
  {
1173
1070
  if: {
@@ -1176,7 +1073,7 @@ var embedded_metadata_schema_default = {
1176
1073
  type: "object",
1177
1074
  properties: {
1178
1075
  type: {
1179
- const: "feedback"
1076
+ const: "cycle"
1180
1077
  }
1181
1078
  }
1182
1079
  }
@@ -1185,11 +1082,10 @@ var embedded_metadata_schema_default = {
1185
1082
  then: {
1186
1083
  properties: {
1187
1084
  payload: {
1188
- $ref: "ref:feedback_record_schema"
1085
+ $ref: "ref:cycle_record_schema"
1189
1086
  }
1190
1087
  }
1191
- },
1192
- else: false
1088
+ }
1193
1089
  },
1194
1090
  {
1195
1091
  if: {
@@ -1198,7 +1094,7 @@ var embedded_metadata_schema_default = {
1198
1094
  type: "object",
1199
1095
  properties: {
1200
1096
  type: {
1201
- const: "cycle"
1097
+ const: "workflow"
1202
1098
  }
1203
1099
  }
1204
1100
  }
@@ -1207,58 +1103,58 @@ var embedded_metadata_schema_default = {
1207
1103
  then: {
1208
1104
  properties: {
1209
1105
  payload: {
1210
- $ref: "ref:cycle_record_schema"
1106
+ $ref: "ref:workflow_record_schema"
1211
1107
  }
1212
1108
  }
1213
- },
1214
- else: false
1109
+ }
1215
1110
  }
1216
1111
  ],
1217
1112
  examples: [
1218
1113
  {
1219
1114
  header: {
1220
- version: "1.0",
1221
- type: "task",
1222
- payloadChecksum: "a1b2c3d4e5f6...",
1115
+ version: "1.1",
1116
+ type: "actor",
1117
+ payloadChecksum: "063d4ba3505e4d2d3852f6063cbd0b98a8728b2afb4a26a323c5c5c512137398",
1223
1118
  signatures: [
1224
1119
  {
1225
1120
  keyId: "human:lead-dev",
1226
1121
  role: "author",
1227
- notes: "Initial task creation for OAuth 2.0 implementation",
1228
- signature: "...",
1122
+ notes: "Self-registration of lead developer account",
1123
+ signature: "yEtlWOGAek8ukP8fycqYZOyogQBudO5XUf4v4BUGaOTogDH4wraanhLvutaJBM7rdilFUS2VvmxZmIy0KjTZAg==",
1229
1124
  timestamp: 1752274500
1230
1125
  }
1231
1126
  ]
1232
1127
  },
1233
1128
  payload: {
1234
- id: "1752274500-task-implementar-auth",
1235
- status: "pending",
1236
- priority: "high",
1237
- description: "Implementar autenticaci\xF3n OAuth 2.0.",
1238
- tags: [
1239
- "skill:go",
1240
- "area:backend"
1241
- ]
1129
+ id: "human:lead-dev",
1130
+ type: "human",
1131
+ displayName: "Lead Developer",
1132
+ publicKey: "0yyrCETtVql51Id+nRKGmpbfsxNxOz+eCYLpWDoutV0=",
1133
+ roles: [
1134
+ "developer",
1135
+ "reviewer"
1136
+ ],
1137
+ status: "active"
1242
1138
  }
1243
1139
  },
1244
1140
  {
1245
1141
  header: {
1246
- version: "1.0",
1142
+ version: "1.1",
1247
1143
  type: "execution",
1248
- payloadChecksum: "b2c3d4e5f6a1...",
1144
+ payloadChecksum: "bd667ddc8698a50594592ac15d0761e62a9f05cc3ba10a9a853ef0819e5fb2ad",
1249
1145
  signatures: [
1250
1146
  {
1251
- keyId: "agent:cursor",
1147
+ keyId: "agent:camilo:cursor",
1252
1148
  role: "author",
1253
1149
  notes: "OAuth 2.0 flow completed with GitHub provider integration",
1254
- signature: "...",
1150
+ signature: "8d9LWTtMlK/Ct4+QWGFpH4iFdZb9T/hlFThAAGKqz8UOPe9qDwPFcv3b4qz9G+NQXh1/PgB1pl8YiQCe6fnjAQ==",
1255
1151
  timestamp: 1752274600
1256
1152
  },
1257
1153
  {
1258
1154
  keyId: "human:camilo",
1259
1155
  role: "reviewer",
1260
1156
  notes: "Reviewed and tested locally. LGTM.",
1261
- signature: "...",
1157
+ signature: "17xsA75W0zzNZI3DXa8iHmxS5NwedfCwu9DoXwk/vArk9yaHcFsY6EgJHNPUtIX+XeKSVF/lOg6CvVIkcXjjAA==",
1262
1158
  timestamp: 1752274650
1263
1159
  }
1264
1160
  ]
@@ -1268,39 +1164,30 @@ var embedded_metadata_schema_default = {
1268
1164
  taskId: "1752274500-task-implement-oauth",
1269
1165
  type: "progress",
1270
1166
  title: "OAuth 2.0 flow implemented",
1271
- result: "Completed the OAuth 2.0 authentication flow..."
1167
+ result: "Completed the OAuth 2.0 authentication flow with GitHub provider. Token refresh and session management included."
1272
1168
  }
1273
1169
  },
1274
1170
  {
1275
1171
  header: {
1276
- version: "1.0",
1277
- type: "actor",
1278
- payloadChecksum: "c3d4e5f6a1b2...",
1172
+ version: "1.1",
1173
+ type: "custom",
1174
+ schemaUrl: "https://example.com/schemas/deployment-record-v1.json",
1175
+ schemaChecksum: "d4e5f6a1b2c3789012345678901234567890123456789012345678901234abcd",
1176
+ payloadChecksum: "1f9598081fcfcf34732de647de25c8445e68e9320e0c10d3a4bd911c7274a1b3",
1279
1177
  signatures: [
1280
1178
  {
1281
- keyId: "human:admin",
1179
+ keyId: "agent:deploy-bot",
1282
1180
  role: "author",
1283
- notes: "New developer onboarded to team",
1284
- signature: "...",
1181
+ notes: "Production deployment of v2.1.0",
1182
+ signature: "W3cSLJnEp+OmKVOwFqjuLTL1S55/OlQyFDzmmxg+vUfETIiQWNr7aDH06/rHUM11g2BLEGRfXZPQPFry6FJeAw==",
1285
1183
  timestamp: 1752274700
1286
- },
1287
- {
1288
- keyId: "agent:aion",
1289
- role: "auditor",
1290
- notes: "Actor verification: 10/10. Credentials validated.",
1291
- signature: "...",
1292
- timestamp: 1752274705
1293
1184
  }
1294
1185
  ]
1295
1186
  },
1296
1187
  payload: {
1297
- id: "human:new-developer",
1298
- type: "human",
1299
- displayName: "New Developer",
1300
- publicKey: "...",
1301
- roles: [
1302
- "developer"
1303
- ]
1188
+ deploymentId: "deploy-2025-07-12-v2.1.0",
1189
+ environment: "production",
1190
+ status: "success"
1304
1191
  }
1305
1192
  }
1306
1193
  ]
@@ -1311,7 +1198,7 @@ var execution_record_schema_default = {
1311
1198
  $schema: "http://json-schema.org/draft-07/schema#",
1312
1199
  $id: "execution_record_schema.json",
1313
1200
  title: "ExecutionRecord",
1314
- description: "Canonical schema for execution log records - the universal event stream",
1201
+ description: "Canonical schema for execution log records - the universal event stream.",
1315
1202
  additionalProperties: false,
1316
1203
  type: "object",
1317
1204
  required: [
@@ -1326,209 +1213,50 @@ var execution_record_schema_default = {
1326
1213
  type: "string",
1327
1214
  pattern: "^\\d{10}-exec-[a-z0-9-]{1,50}$",
1328
1215
  maxLength: 66,
1329
- description: "Unique identifier for the execution log entry (10 timestamp + 1 dash + 4 'exec' + 1 dash + max 50 slug = 66 max)",
1330
- examples: [
1331
- "1752275000-exec-refactor-queries",
1332
- "1752361200-exec-api-externa-caida"
1333
- ]
1216
+ description: "Unique identifier for the execution log entry."
1334
1217
  },
1335
1218
  taskId: {
1336
1219
  type: "string",
1337
1220
  pattern: "^\\d{10}-task-[a-z0-9-]{1,50}$",
1338
1221
  maxLength: 66,
1339
- description: "ID of the parent task this execution belongs to (10 timestamp + 1 dash + 4 'task' + 1 dash + max 50 slug = 66 max)"
1222
+ description: "ID of the parent task this execution belongs to."
1340
1223
  },
1341
1224
  type: {
1342
1225
  type: "string",
1343
- enum: [
1344
- "analysis",
1345
- "progress",
1346
- "blocker",
1347
- "completion",
1348
- "info",
1349
- "correction"
1350
- ],
1351
- description: "Semantic classification of the execution event",
1352
- examples: [
1353
- "progress",
1354
- "analysis",
1355
- "blocker",
1356
- "completion"
1357
- ]
1226
+ pattern: "^(analysis|decision|progress|blocker|completion|correction|info|custom:[a-z0-9-]+(:[a-z0-9-]+)*)$",
1227
+ description: "Classifies what happened in this execution event. Primitive types cover the fundamental kinds of events that occur during any collaborative work. Extend with 'custom:' for your domain.\nPrimitive types:\n - analysis: Investigation, research, or evaluation before acting.\n - decision: A choice that changes the direction of work.\n - progress: Incremental advancement of work.\n - blocker: An impediment preventing further progress.\n - completion: Work on the task is finished.\n - correction: A fix to something previously done incorrectly.\n - info: Informational note or status update.\n\nCustom types use the 'custom:' prefix for industry-specific extensions. Software development examples:\n - custom:review (code review, design review, QA)\n - custom:deployment (deploy to staging/production)\n - custom:rollback (revert a deployment or change)\n - custom:release (version release, PR merge to main)\n - custom:hotfix (emergency fix in production)\nImplementations that encounter an unrecognized custom type MUST treat it as 'info' for display purposes.\n"
1358
1228
  },
1359
1229
  title: {
1360
1230
  type: "string",
1361
1231
  minLength: 1,
1362
1232
  maxLength: 256,
1363
- description: "Human-readable title for the execution (used to generate ID)",
1364
- examples: [
1365
- "Refactor de queries N+1",
1366
- "API Externa Ca\xEDda",
1367
- "Plan de implementaci\xF3n OAuth2"
1368
- ]
1233
+ description: "Human-readable title for the execution (used to generate ID slug)."
1369
1234
  },
1370
1235
  result: {
1371
1236
  type: "string",
1372
1237
  minLength: 10,
1373
- maxLength: 22e3,
1374
- description: 'The tangible, verifiable output or result of the execution. \nThis is the "WHAT" - evidence of work or event summary.\n'
1238
+ description: 'The tangible, verifiable output or result of the execution. This is the "WHAT" - evidence of work or event summary.\n'
1375
1239
  },
1376
1240
  notes: {
1377
1241
  type: "string",
1378
- maxLength: 6500,
1379
- description: 'Optional narrative, context and decisions behind the execution.\nThis is the "HOW" and "WHY" - the story behind the result.\n'
1242
+ description: 'Optional narrative, context and decisions behind the execution. This is the "HOW" and "WHY" - the story behind the result.\n'
1380
1243
  },
1381
1244
  references: {
1382
1245
  type: "array",
1383
1246
  items: {
1384
1247
  type: "string",
1248
+ minLength: 1,
1385
1249
  maxLength: 500
1386
1250
  },
1387
1251
  default: [],
1388
- description: "Optional list of typed references to relevant commits, files, PRs, or external documents.\nShould use typed prefixes for clarity and trazabilidad (see execution_protocol_appendix.md):\n- commit: Git commit SHA\n- pr: Pull Request number\n- file: File path (relative to repo root)\n- url: External URL\n- issue: GitHub Issue number\n- task: TaskRecord ID\n- exec: ExecutionRecord ID (for corrections or dependencies)\n- changelog: ChangelogRecord ID\n"
1252
+ description: "Optional list of typed references to relevant commits, files, PRs, or external documents. Standard prefixes: commit:, pr:, issue:, file:, url:, task:, exec:.\n"
1389
1253
  },
1390
1254
  metadata: {
1391
1255
  type: "object",
1392
1256
  additionalProperties: true,
1393
- description: "Optional structured data for machine consumption.\nUse this field for data that needs to be programmatically processed (e.g., audit findings,\nperformance metrics, scan results). This complements result (human-readable WHAT) and\nnotes (narrative HOW/WHY) by providing structured, queryable data.\nCommon use cases: audit findings arrays, performance metrics, tool outputs, scan summaries.\n",
1394
- examples: [
1395
- {
1396
- findings: [
1397
- {
1398
- type: "PII",
1399
- file: "src/user.ts",
1400
- line: 42
1401
- }
1402
- ],
1403
- scannedFiles: 245
1404
- },
1405
- {
1406
- metrics: {
1407
- duration_ms: 1250,
1408
- memory_mb: 512
1409
- }
1410
- }
1411
- ]
1412
- }
1413
- },
1414
- examples: [
1415
- {
1416
- id: "1752275500-exec-refactor-queries",
1417
- taskId: "1752274500-task-optimizar-api",
1418
- type: "progress",
1419
- title: "Refactor de queries N+1",
1420
- result: "Refactorizados 3 queries N+1 a un solo JOIN optimizado. Performance mejor\xF3 de 2.5s a 200ms.",
1421
- notes: "Identificados 3 N+1 queries en el endpoint /api/search. Aplicado eager loading y caching de relaciones.",
1422
- references: [
1423
- "commit:b2c3d4e",
1424
- "file:src/api/search.ts"
1425
- ]
1426
- },
1427
- {
1428
- id: "1752361200-exec-api-externa-caida",
1429
- taskId: "1752274500-task-optimizar-api",
1430
- type: "blocker",
1431
- title: "API Externa Ca\xEDda",
1432
- result: "No se puede continuar con testing de integraci\xF3n. API de pagos devuelve 503.",
1433
- notes: "La API de pagos de terceros (api.payments.com) est\xE1 devolviendo errores 503. Contactado soporte del proveedor. ETA de resoluci\xF3n: 2-3 horas.",
1434
- references: [
1435
- "url:https://status.payments.com"
1436
- ]
1437
- },
1438
- {
1439
- id: "1752188000-exec-plan-oauth-implementation",
1440
- taskId: "1752274500-task-oauth-implementation",
1441
- type: "analysis",
1442
- title: "Plan de implementaci\xF3n OAuth2",
1443
- result: "Documento de dise\xF1o t\xE9cnico completado. 5 sub-tareas identificadas con estimaciones de complejidad.",
1444
- notes: "Evaluadas 3 opciones: NextAuth.js (elegida), Passport.js, custom implementation. NextAuth.js por madurez y soporte de m\xFAltiples providers.",
1445
- references: [
1446
- "file:docs/oauth-design.md"
1447
- ]
1448
- },
1449
- {
1450
- id: "1752707800-exec-oauth-completed",
1451
- taskId: "1752274500-task-oauth-implementation",
1452
- type: "completion",
1453
- title: "OAuth Implementation Completed",
1454
- result: "Sistema OAuth2 completamente implementado, testeado y deployado a staging. 95% test coverage. Todos los acceptance criteria cumplidos.",
1455
- notes: "Implementaci\xF3n finalizada. Code review aprobado. Tests E2E passing. Ready para changelog y deploy a producci\xF3n.",
1456
- references: [
1457
- "pr:456",
1458
- "commit:def789abc",
1459
- "url:https://staging.app.com/login"
1460
- ]
1461
- },
1462
- {
1463
- id: "1752275600-exec-cambio-estrategia-redis",
1464
- taskId: "1752274500-task-oauth-implementation",
1465
- type: "info",
1466
- title: "Cambio de estrategia: Usar Redis para sessions",
1467
- result: "Decisi\xF3n: Migrar de JWT stateless a sessions en Redis por requisito de revocaci\xF3n inmediata.",
1468
- notes: "Durante code review se identific\xF3 requisito cr\xEDtico: revocar sesiones inmediatamente (ej: compromiso de cuenta). JWT stateless no permite esto sin lista negra compleja. Redis sessions permite revocaci\xF3n instant\xE1nea.",
1469
- references: [
1470
- "issue:567",
1471
- "url:https://redis.io/docs/manual/keyspace-notifications/"
1472
- ]
1473
- },
1474
- {
1475
- id: "1752275700-exec-correccion-metricas",
1476
- taskId: "1752274500-task-optimizar-api",
1477
- type: "correction",
1478
- title: "Correcci\xF3n: M\xE9tricas de performance",
1479
- result: "Correcci\xF3n de execution 1752275500-exec-refactor-queries: El performance fue 200ms, no 50ms como se report\xF3.",
1480
- notes: "Error de tipeo en execution original. La mejora real fue de 2.5s a 200ms (no 50ms). Sigue siendo significativa (92% mejora) pero n\xFAmeros correctos son importantes para m\xE9tricas.",
1481
- references: [
1482
- "exec:1752275500-exec-refactor-queries"
1483
- ]
1484
- },
1485
- {
1486
- id: "1752276000-exec-source-audit-scan",
1487
- taskId: "1752274500-task-audit-compliance",
1488
- type: "analysis",
1489
- title: "Source Audit Scan - 2025-01-15",
1490
- result: "Escaneados 245 archivos. Encontrados 10 findings (3 critical, 4 high, 3 medium). Ver metadata para detalles estructurados.",
1491
- notes: "Scan ejecutado con RegexDetector + HeuristicDetector. LLM calls: 0 (tier free).",
1492
- references: [
1493
- "file:src/config/db.ts",
1494
- "file:src/auth/keys.ts"
1495
- ],
1496
- metadata: {
1497
- scannedFiles: 245,
1498
- scannedLines: 18420,
1499
- duration_ms: 1250,
1500
- findings: [
1501
- {
1502
- id: "SEC-001",
1503
- severity: "critical",
1504
- file: "src/config/db.ts",
1505
- line: 5,
1506
- type: "api_key"
1507
- },
1508
- {
1509
- id: "SEC-003",
1510
- severity: "critical",
1511
- file: "src/auth/keys.ts",
1512
- line: 2,
1513
- type: "private_key"
1514
- },
1515
- {
1516
- id: "PII-003",
1517
- severity: "critical",
1518
- file: "src/payments/stripe.ts",
1519
- line: 8,
1520
- type: "credit_card"
1521
- }
1522
- ],
1523
- summary: {
1524
- critical: 3,
1525
- high: 4,
1526
- medium: 3,
1527
- low: 0
1528
- }
1529
- }
1257
+ description: "Optional structured data for machine consumption. Use this field for data that needs to be programmatically processed (e.g., audit findings, performance metrics, scan results). Complements result (WHAT) and notes (HOW/WHY) with structured, queryable data.\n"
1530
1258
  }
1531
- ]
1259
+ }
1532
1260
  };
1533
1261
 
1534
1262
  // src/record_schemas/generated/feedback_record_schema.json
@@ -1536,7 +1264,7 @@ var feedback_record_schema_default = {
1536
1264
  $schema: "http://json-schema.org/draft-07/schema#",
1537
1265
  $id: "feedback_record_schema.json",
1538
1266
  title: "FeedbackRecord",
1539
- description: "Canonical schema for feedback records - structured conversation about work",
1267
+ description: "Canonical schema for feedback records \u2014 the structured conversation about work.",
1540
1268
  additionalProperties: false,
1541
1269
  type: "object",
1542
1270
  required: [
@@ -1552,32 +1280,35 @@ var feedback_record_schema_default = {
1552
1280
  type: "string",
1553
1281
  pattern: "^\\d{10}-feedback-[a-z0-9-]{1,50}$",
1554
1282
  maxLength: 70,
1555
- description: "Unique identifier for the feedback entry",
1283
+ description: "Unique identifier for the feedback entry (10 timestamp + 1 dash + 8 'feedback' + 1 dash + max 50 slug = 70 max)",
1556
1284
  examples: [
1557
1285
  "1752788100-feedback-blocking-rest-api",
1558
- "1752788200-feedback-question-test-coverage"
1286
+ "1752788400-feedback-question-test-coverage"
1559
1287
  ]
1560
1288
  },
1561
1289
  entityType: {
1562
1290
  type: "string",
1563
1291
  enum: [
1292
+ "actor",
1293
+ "agent",
1564
1294
  "task",
1565
1295
  "execution",
1566
- "changelog",
1567
1296
  "feedback",
1568
- "cycle"
1297
+ "cycle",
1298
+ "workflow"
1569
1299
  ],
1570
- description: "The type of entity this feedback refers to"
1300
+ description: "The type of entity this feedback refers to."
1571
1301
  },
1572
1302
  entityId: {
1573
1303
  type: "string",
1574
1304
  minLength: 1,
1575
1305
  maxLength: 256,
1576
- description: "The ID of the entity this feedback refers to.\nMust match the pattern for its entityType:\n- task: ^\\d{10}-task-[a-z0-9-]{1,50}$\n- execution: ^\\d{10}-exec-[a-z0-9-]{1,50}$\n- changelog: ^\\d{10}-changelog-[a-z0-9-]{1,50}$\n- feedback: ^\\d{10}-feedback-[a-z0-9-]{1,50}$\n- cycle: ^\\d{10}-cycle-[a-z0-9-]{1,50}$\n",
1306
+ description: "The ID of the entity this feedback refers to.\nMust match the ID pattern for its entityType:\n- actor: ^(human|agent)(:[a-z0-9-]+)+$\n- agent: ^agent(:[a-z0-9-]+)+$\n- task: ^\\d{10}-task-[a-z0-9-]{1,50}$\n- execution: ^\\d{10}-exec-[a-z0-9-]{1,50}$\n- feedback: ^\\d{10}-feedback-[a-z0-9-]{1,50}$\n- cycle: ^\\d{10}-cycle-[a-z0-9-]{1,50}$\n- workflow: ^\\d{10}-workflow-[a-z0-9-]{1,50}$\n",
1577
1307
  examples: [
1578
1308
  "1752274500-task-implementar-oauth",
1579
1309
  "1752642000-exec-subtarea-9-4",
1580
- "1752788100-feedback-blocking-rest-api"
1310
+ "1752788100-feedback-blocking-rest-api",
1311
+ "human:camilo"
1581
1312
  ]
1582
1313
  },
1583
1314
  type: {
@@ -1590,64 +1321,191 @@ var feedback_record_schema_default = {
1590
1321
  "clarification",
1591
1322
  "assignment"
1592
1323
  ],
1593
- description: "The semantic intent of the feedback",
1324
+ description: "The semantic intent of the feedback."
1325
+ },
1326
+ status: {
1327
+ type: "string",
1328
+ enum: [
1329
+ "open",
1330
+ "acknowledged",
1331
+ "resolved",
1332
+ "wontfix"
1333
+ ],
1334
+ description: 'The lifecycle status of the feedback.\nFeedbackRecords are immutable. To change status, create a new FeedbackRecord\nthat references this one using entityType: "feedback" and resolvesFeedbackId.\n'
1335
+ },
1336
+ content: {
1337
+ type: "string",
1338
+ minLength: 1,
1339
+ description: "The content of the feedback."
1340
+ },
1341
+ assignee: {
1342
+ type: "string",
1343
+ pattern: "^(human|agent)(:[a-z0-9-]+)+$",
1344
+ maxLength: 256,
1345
+ description: "Optional. The Actor ID responsible for addressing the feedback (e.g., 'human:maria', 'agent:camilo:cursor').",
1594
1346
  examples: [
1595
- "blocking",
1596
- "question",
1597
- "approval"
1347
+ "human:maria",
1348
+ "agent:code-reviewer",
1349
+ "agent:camilo:cursor"
1350
+ ]
1351
+ },
1352
+ resolvesFeedbackId: {
1353
+ type: "string",
1354
+ pattern: "^\\d{10}-feedback-[a-z0-9-]{1,50}$",
1355
+ maxLength: 70,
1356
+ description: "Optional. The ID of another FeedbackRecord that this one resolves or responds to.",
1357
+ examples: [
1358
+ "1752788100-feedback-blocking-rest-api"
1598
1359
  ]
1599
1360
  },
1600
- status: {
1601
- type: "string",
1602
- enum: [
1603
- "open",
1604
- "acknowledged",
1605
- "resolved",
1606
- "wontfix"
1607
- ],
1608
- description: 'The lifecycle status of the feedback. \nNote: FeedbackRecords are immutable. To change status, create a new feedback \nthat references this one using entityType: "feedback" and resolvesFeedbackId.\n'
1361
+ metadata: {
1362
+ type: "object",
1363
+ additionalProperties: true,
1364
+ description: "Optional structured data for machine consumption.\nUse this field for domain-specific data that needs to be programmatically processed.\nCommon use cases: waiver details (fingerprint, ruleId, file, line), approval context, assignment metadata.\n"
1365
+ }
1366
+ },
1367
+ allOf: [
1368
+ {
1369
+ if: {
1370
+ required: [
1371
+ "entityType"
1372
+ ],
1373
+ properties: {
1374
+ entityType: {
1375
+ const: "actor"
1376
+ }
1377
+ }
1378
+ },
1379
+ then: {
1380
+ properties: {
1381
+ entityId: {
1382
+ type: "string",
1383
+ pattern: "^(human|agent)(:[a-z0-9-]+)+$"
1384
+ }
1385
+ }
1386
+ }
1387
+ },
1388
+ {
1389
+ if: {
1390
+ required: [
1391
+ "entityType"
1392
+ ],
1393
+ properties: {
1394
+ entityType: {
1395
+ const: "agent"
1396
+ }
1397
+ }
1398
+ },
1399
+ then: {
1400
+ properties: {
1401
+ entityId: {
1402
+ type: "string",
1403
+ pattern: "^agent(:[a-z0-9-]+)+$"
1404
+ }
1405
+ }
1406
+ }
1407
+ },
1408
+ {
1409
+ if: {
1410
+ required: [
1411
+ "entityType"
1412
+ ],
1413
+ properties: {
1414
+ entityType: {
1415
+ const: "task"
1416
+ }
1417
+ }
1418
+ },
1419
+ then: {
1420
+ properties: {
1421
+ entityId: {
1422
+ type: "string",
1423
+ pattern: "^\\d{10}-task-[a-z0-9-]{1,50}$"
1424
+ }
1425
+ }
1426
+ }
1609
1427
  },
1610
- content: {
1611
- type: "string",
1612
- minLength: 1,
1613
- maxLength: 5e3,
1614
- description: "The content of the feedback. Reduced from 10000 to 5000 chars for practical use."
1428
+ {
1429
+ if: {
1430
+ required: [
1431
+ "entityType"
1432
+ ],
1433
+ properties: {
1434
+ entityType: {
1435
+ const: "execution"
1436
+ }
1437
+ }
1438
+ },
1439
+ then: {
1440
+ properties: {
1441
+ entityId: {
1442
+ type: "string",
1443
+ pattern: "^\\d{10}-exec-[a-z0-9-]{1,50}$"
1444
+ }
1445
+ }
1446
+ }
1615
1447
  },
1616
- assignee: {
1617
- type: "string",
1618
- pattern: "^(human|agent)(:[a-z0-9-]+)+$",
1619
- maxLength: 256,
1620
- description: "Optional. The Actor ID responsible for addressing the feedback (e.g., 'human:maria', 'agent:camilo:cursor')",
1621
- examples: [
1622
- "human:maria",
1623
- "agent:code-reviewer",
1624
- "agent:camilo:cursor"
1625
- ]
1448
+ {
1449
+ if: {
1450
+ required: [
1451
+ "entityType"
1452
+ ],
1453
+ properties: {
1454
+ entityType: {
1455
+ const: "feedback"
1456
+ }
1457
+ }
1458
+ },
1459
+ then: {
1460
+ properties: {
1461
+ entityId: {
1462
+ type: "string",
1463
+ pattern: "^\\d{10}-feedback-[a-z0-9-]{1,50}$"
1464
+ }
1465
+ }
1466
+ }
1626
1467
  },
1627
- resolvesFeedbackId: {
1628
- type: "string",
1629
- pattern: "^\\d{10}-feedback-[a-z0-9-]{1,50}$",
1630
- maxLength: 70,
1631
- description: "Optional. The ID of another feedback record that this one resolves or responds to",
1632
- examples: [
1633
- "1752788100-feedback-blocking-rest-api"
1634
- ]
1468
+ {
1469
+ if: {
1470
+ required: [
1471
+ "entityType"
1472
+ ],
1473
+ properties: {
1474
+ entityType: {
1475
+ const: "cycle"
1476
+ }
1477
+ }
1478
+ },
1479
+ then: {
1480
+ properties: {
1481
+ entityId: {
1482
+ type: "string",
1483
+ pattern: "^\\d{10}-cycle-[a-z0-9-]{1,50}$"
1484
+ }
1485
+ }
1486
+ }
1635
1487
  },
1636
- metadata: {
1637
- type: "object",
1638
- additionalProperties: true,
1639
- description: "Optional structured data for machine consumption.\nUse this field for domain-specific data that needs to be programmatically processed.\nCommon use cases: waiver details (fingerprint, ruleId, file, line), approval context, assignment metadata.\n",
1640
- examples: [
1641
- {
1642
- fingerprint: "abc123def456",
1643
- ruleId: "PII-001",
1644
- file: "src/user.ts",
1645
- line: 42,
1646
- expiresAt: "2025-12-31T23:59:59Z"
1488
+ {
1489
+ if: {
1490
+ required: [
1491
+ "entityType"
1492
+ ],
1493
+ properties: {
1494
+ entityType: {
1495
+ const: "workflow"
1496
+ }
1647
1497
  }
1648
- ]
1498
+ },
1499
+ then: {
1500
+ properties: {
1501
+ entityId: {
1502
+ type: "string",
1503
+ pattern: "^\\d{10}-workflow-[a-z0-9-]{1,50}$"
1504
+ }
1505
+ }
1506
+ }
1649
1507
  }
1650
- },
1508
+ ],
1651
1509
  examples: [
1652
1510
  {
1653
1511
  id: "1752788100-feedback-blocking-rest-api",
@@ -1655,7 +1513,7 @@ var feedback_record_schema_default = {
1655
1513
  entityId: "1752642000-exec-subtarea-9-4",
1656
1514
  type: "blocking",
1657
1515
  status: "open",
1658
- content: "Esta implementaci\xF3n no cumple el est\xE1ndar de rutas REST. Los endpoints deben seguir el patr\xF3n /api/v1/{resource}/{id}. Actualmente usa /get-user?id=X que no es RESTful."
1516
+ content: "This implementation does not comply with the REST endpoint standard. Endpoints must follow the /api/v1/{resource}/{id} pattern. Currently uses /get-user?id=X which is not RESTful."
1659
1517
  },
1660
1518
  {
1661
1519
  id: "1752788200-feedback-rest-api-fixed",
@@ -1663,7 +1521,7 @@ var feedback_record_schema_default = {
1663
1521
  entityId: "1752788100-feedback-blocking-rest-api",
1664
1522
  type: "clarification",
1665
1523
  status: "resolved",
1666
- content: "Implementada la correcci\xF3n. Ahora todos los endpoints siguen el est\xE1ndar REST: GET /api/v1/users/:id, POST /api/v1/users, etc. Tests actualizados y passing.",
1524
+ content: "Fix implemented. All endpoints now follow REST standard: GET /api/v1/users/:id, POST /api/v1/users, etc. Tests updated and passing.",
1667
1525
  resolvesFeedbackId: "1752788100-feedback-blocking-rest-api"
1668
1526
  },
1669
1527
  {
@@ -1672,7 +1530,7 @@ var feedback_record_schema_default = {
1672
1530
  entityId: "1752274500-task-implementar-oauth",
1673
1531
  type: "assignment",
1674
1532
  status: "open",
1675
- content: "Asignando esta tarea a Mar\xEDa por su experiencia con OAuth2. Prioridad alta para el sprint actual.",
1533
+ content: "Assigning this task to Maria for her experience with OAuth2. High priority for the current sprint.",
1676
1534
  assignee: "human:maria"
1677
1535
  },
1678
1536
  {
@@ -1681,7 +1539,7 @@ var feedback_record_schema_default = {
1681
1539
  entityId: "1752274500-task-implementar-oauth",
1682
1540
  type: "question",
1683
1541
  status: "open",
1684
- content: "\xBFCu\xE1l es el nivel de test coverage esperado para esta feature? El spec no lo menciona expl\xEDcitamente. \xBFDebemos apuntar a 80% como el resto del proyecto?"
1542
+ content: "What level of test coverage is expected for this feature? The spec does not mention it explicitly. Should we aim for 80% like the rest of the project?"
1685
1543
  }
1686
1544
  ]
1687
1545
  };
@@ -1691,7 +1549,7 @@ var task_record_schema_default = {
1691
1549
  $schema: "http://json-schema.org/draft-07/schema#",
1692
1550
  $id: "task_record_schema.json",
1693
1551
  title: "TaskRecord",
1694
- description: "Canonical schema for task records as defined in task_protocol.md",
1552
+ description: "Canonical schema for task records as defined in 04_task.md",
1695
1553
  additionalProperties: false,
1696
1554
  type: "object",
1697
1555
  required: [
@@ -1741,7 +1599,6 @@ var task_record_schema_default = {
1741
1599
  "paused",
1742
1600
  "discarded"
1743
1601
  ],
1744
- maxLength: 40,
1745
1602
  description: "Current state of the task in the institutional flow"
1746
1603
  },
1747
1604
  priority: {
@@ -1752,13 +1609,11 @@ var task_record_schema_default = {
1752
1609
  "high",
1753
1610
  "critical"
1754
1611
  ],
1755
- maxLength: 40,
1756
1612
  description: "Strategic or tactical priority level"
1757
1613
  },
1758
1614
  description: {
1759
1615
  type: "string",
1760
1616
  minLength: 10,
1761
- maxLength: 22e3,
1762
1617
  description: "Functional, technical or strategic summary of the objective"
1763
1618
  },
1764
1619
  tags: {
@@ -1766,7 +1621,7 @@ var task_record_schema_default = {
1766
1621
  items: {
1767
1622
  type: "string",
1768
1623
  minLength: 1,
1769
- pattern: "^[a-z0-9-]+(:[a-z0-9-:]+)*$"
1624
+ pattern: "^[a-z0-9-]+(:[a-z0-9-]+)*$"
1770
1625
  },
1771
1626
  default: [],
1772
1627
  description: "Optional. List of key:value tags for categorization and role suggestion (e.g., 'skill:react', 'role:agent:developer')."
@@ -1783,9 +1638,26 @@ var task_record_schema_default = {
1783
1638
  },
1784
1639
  notes: {
1785
1640
  type: "string",
1786
- minLength: 0,
1787
- maxLength: 3e3,
1641
+ minLength: 1,
1788
1642
  description: "Additional comments, decisions made or added context"
1643
+ },
1644
+ metadata: {
1645
+ type: "object",
1646
+ additionalProperties: true,
1647
+ description: "Optional structured data for machine consumption.\nUse this field for domain-specific data that needs to be programmatically processed.\nComplements tags (classification) and notes (free text) with structured, queryable data.\nCommon use cases: epic metadata, external tool references, agent metrics, compliance tags.\n",
1648
+ examples: [
1649
+ {
1650
+ epic: true,
1651
+ phase: "implementation",
1652
+ files: {
1653
+ overview: "overview.md"
1654
+ }
1655
+ },
1656
+ {
1657
+ jira: "AUTH-42",
1658
+ storyPoints: 5
1659
+ }
1660
+ ]
1789
1661
  }
1790
1662
  },
1791
1663
  examples: [
@@ -1868,25 +1740,22 @@ var task_record_schema_default = {
1868
1740
  // src/record_schemas/generated/workflow_record_schema.json
1869
1741
  var workflow_record_schema_default = {
1870
1742
  $schema: "http://json-schema.org/draft-07/schema#",
1871
- $id: "workflow_schema.json",
1743
+ $id: "workflow_record_schema.json",
1872
1744
  title: "WorkflowRecord",
1873
- description: "Complete schema for workflow methodology configuration files that define state transitions, signatures, and custom rules",
1745
+ description: "Schema for workflow methodology configuration that defines named state transitions, signatures, and custom rules.",
1874
1746
  type: "object",
1875
1747
  required: [
1876
- "version",
1748
+ "id",
1877
1749
  "name",
1878
1750
  "state_transitions"
1879
1751
  ],
1880
1752
  additionalProperties: false,
1881
1753
  properties: {
1882
- $schema: {
1883
- type: "string",
1884
- description: "JSON Schema reference"
1885
- },
1886
- version: {
1754
+ id: {
1887
1755
  type: "string",
1888
- pattern: "^\\d+\\.\\d+\\.\\d+$",
1889
- description: "Semantic version of the methodology configuration"
1756
+ pattern: "^\\d{10}-workflow-[a-z0-9-]{1,50}$",
1757
+ maxLength: 70,
1758
+ description: "Unique identifier for the workflow record (10 timestamp + 1 dash + 8 'workflow' + 1 dash + max 50 slug = 70 max)"
1890
1759
  },
1891
1760
  name: {
1892
1761
  type: "string",
@@ -1901,11 +1770,15 @@ var workflow_record_schema_default = {
1901
1770
  },
1902
1771
  state_transitions: {
1903
1772
  type: "object",
1904
- description: "Defines valid state transitions and their requirements",
1773
+ description: "Map of named transitions to their rules. Keys are transition names (e.g., submit, approve, activate, resume), not target states.",
1774
+ propertyNames: {
1775
+ pattern: "^[a-z][a-z0-9_]{0,49}$"
1776
+ },
1905
1777
  additionalProperties: {
1906
1778
  type: "object",
1907
1779
  required: [
1908
1780
  "from",
1781
+ "to",
1909
1782
  "requires"
1910
1783
  ],
1911
1784
  additionalProperties: false,
@@ -1919,21 +1792,26 @@ var workflow_record_schema_default = {
1919
1792
  minItems: 1,
1920
1793
  description: "Valid source states for this transition"
1921
1794
  },
1795
+ to: {
1796
+ type: "string",
1797
+ pattern: "^[a-z][a-z0-9_]{0,49}$",
1798
+ description: "Target state for this transition"
1799
+ },
1922
1800
  requires: {
1923
1801
  type: "object",
1924
1802
  additionalProperties: false,
1925
1803
  properties: {
1926
1804
  command: {
1927
1805
  type: "string",
1928
- description: "CLI command that triggers this transition"
1806
+ description: "CLI command that triggers this transition (Command Gate)"
1929
1807
  },
1930
1808
  event: {
1931
1809
  type: "string",
1932
- description: "System event that triggers this transition"
1810
+ description: "System event that triggers this transition (Event Gate)"
1933
1811
  },
1934
1812
  signatures: {
1935
1813
  type: "object",
1936
- description: "Signature requirements keyed by role (e.g., 'approver:quality', 'developer:backend')",
1814
+ description: "Signature group requirements (Signature Gate)",
1937
1815
  additionalProperties: {
1938
1816
  type: "object",
1939
1817
  required: [
@@ -1973,7 +1851,7 @@ var workflow_record_schema_default = {
1973
1851
  items: {
1974
1852
  type: "string"
1975
1853
  },
1976
- description: "Optional: specific actors that can sign"
1854
+ description: "Optional: restrict to specific actor IDs"
1977
1855
  }
1978
1856
  }
1979
1857
  }
@@ -2022,7 +1900,7 @@ var workflow_record_schema_default = {
2022
1900
  },
2023
1901
  expression: {
2024
1902
  type: "string",
2025
- description: "Inline validation expression for 'custom' validation type. Implementation determines the runtime and language. Must return boolean or Promise<boolean>."
1903
+ description: "Inline validation expression for 'custom' type. Must return boolean."
2026
1904
  },
2027
1905
  module_path: {
2028
1906
  type: "string",
@@ -2033,7 +1911,7 @@ var workflow_record_schema_default = {
2033
1911
  },
2034
1912
  agent_integration: {
2035
1913
  type: "object",
2036
- description: "Optional agent automation configuration for methodology",
1914
+ description: "Optional agent automation configuration",
2037
1915
  additionalProperties: false,
2038
1916
  properties: {
2039
1917
  description: {
@@ -2043,7 +1921,7 @@ var workflow_record_schema_default = {
2043
1921
  },
2044
1922
  required_agents: {
2045
1923
  type: "array",
2046
- description: "References to agents required for this methodology. Agent details (engine, knowledge, etc.) live in their AgentRecord.",
1924
+ description: "Agents required for this methodology",
2047
1925
  items: {
2048
1926
  type: "object",
2049
1927
  required: [
@@ -2065,8 +1943,8 @@ var workflow_record_schema_default = {
2065
1943
  properties: {
2066
1944
  id: {
2067
1945
  type: "string",
2068
- pattern: "^agent:[a-z0-9:-]+$",
2069
- description: "Specific agent ID. References an existing AgentRecord."
1946
+ pattern: "^agent(:[a-z0-9-]+)+$",
1947
+ description: "Specific agent ID (references an AgentRecord)"
2070
1948
  },
2071
1949
  required_roles: {
2072
1950
  type: "array",
@@ -2075,11 +1953,11 @@ var workflow_record_schema_default = {
2075
1953
  pattern: "^[a-z0-9-]+(:[a-z0-9-]+)*$"
2076
1954
  },
2077
1955
  minItems: 1,
2078
- description: "Required capability roles. Matches any agent with these roles (from ActorRecord)."
1956
+ description: "Required capability roles (matches any agent with these roles)"
2079
1957
  },
2080
1958
  triggers: {
2081
1959
  type: "array",
2082
- description: "When this agent activates within this methodology",
1960
+ description: "Events that activate this agent",
2083
1961
  items: {
2084
1962
  type: "object",
2085
1963
  required: [
@@ -2108,190 +1986,13 @@ var workflow_record_schema_default = {
2108
1986
  }
2109
1987
  }
2110
1988
  }
2111
- },
2112
- examples: [
2113
- {
2114
- version: "1.0.0",
2115
- name: "Simple Kanban",
2116
- description: "Basic workflow for small teams",
2117
- state_transitions: {
2118
- review: {
2119
- from: [
2120
- "draft"
2121
- ],
2122
- requires: {
2123
- command: "gitgov task submit"
2124
- }
2125
- },
2126
- ready: {
2127
- from: [
2128
- "review"
2129
- ],
2130
- requires: {
2131
- command: "gitgov task approve",
2132
- signatures: {
2133
- __default__: {
2134
- role: "approver",
2135
- capability_roles: [
2136
- "approver:product"
2137
- ],
2138
- min_approvals: 1
2139
- }
2140
- }
2141
- }
2142
- },
2143
- active: {
2144
- from: [
2145
- "ready"
2146
- ],
2147
- requires: {
2148
- event: "first_execution_record_created"
2149
- }
2150
- },
2151
- done: {
2152
- from: [
2153
- "active"
2154
- ],
2155
- requires: {
2156
- command: "gitgov task complete"
2157
- }
2158
- }
2159
- }
2160
- },
2161
- {
2162
- version: "1.0.0",
2163
- name: "GitGovernance Default Methodology",
2164
- description: "Standard GitGovernance workflow with quality gates and agent collaboration",
2165
- state_transitions: {
2166
- review: {
2167
- from: [
2168
- "draft"
2169
- ],
2170
- requires: {
2171
- command: "gitgov task submit",
2172
- signatures: {
2173
- __default__: {
2174
- role: "submitter",
2175
- capability_roles: [
2176
- "author"
2177
- ],
2178
- min_approvals: 1
2179
- }
2180
- }
2181
- }
2182
- },
2183
- ready: {
2184
- from: [
2185
- "review"
2186
- ],
2187
- requires: {
2188
- command: "gitgov task approve",
2189
- signatures: {
2190
- __default__: {
2191
- role: "approver",
2192
- capability_roles: [
2193
- "approver:product"
2194
- ],
2195
- min_approvals: 1
2196
- },
2197
- design: {
2198
- role: "approver",
2199
- capability_roles: [
2200
- "approver:design"
2201
- ],
2202
- min_approvals: 1
2203
- },
2204
- quality: {
2205
- role: "approver",
2206
- capability_roles: [
2207
- "approver:quality"
2208
- ],
2209
- min_approvals: 1
2210
- }
2211
- }
2212
- }
2213
- },
2214
- active: {
2215
- from: [
2216
- "ready",
2217
- "paused"
2218
- ],
2219
- requires: {
2220
- event: "first_execution_record_created",
2221
- custom_rules: [
2222
- "task_must_have_valid_assignment_for_executor"
2223
- ]
2224
- }
2225
- },
2226
- done: {
2227
- from: [
2228
- "active"
2229
- ],
2230
- requires: {
2231
- command: "gitgov task complete",
2232
- signatures: {
2233
- __default__: {
2234
- role: "approver",
2235
- capability_roles: [
2236
- "approver:quality"
2237
- ],
2238
- min_approvals: 1
2239
- }
2240
- }
2241
- }
2242
- },
2243
- archived: {
2244
- from: [
2245
- "done"
2246
- ],
2247
- requires: {
2248
- event: "changelog_record_created"
2249
- }
2250
- },
2251
- paused: {
2252
- from: [
2253
- "active",
2254
- "review"
2255
- ],
2256
- requires: {
2257
- event: "feedback_blocking_created"
2258
- }
2259
- },
2260
- discarded: {
2261
- from: [
2262
- "ready",
2263
- "active"
2264
- ],
2265
- requires: {
2266
- command: "gitgov task cancel",
2267
- signatures: {
2268
- __default__: {
2269
- role: "canceller",
2270
- capability_roles: [
2271
- "approver:product",
2272
- "approver:quality"
2273
- ],
2274
- min_approvals: 1
2275
- }
2276
- }
2277
- }
2278
- }
2279
- },
2280
- custom_rules: {
2281
- task_must_have_valid_assignment_for_executor: {
2282
- description: "Task must have a valid assignment before execution can begin",
2283
- validation: "assignment_required"
2284
- }
2285
- }
2286
- }
2287
- ]
1989
+ }
2288
1990
  };
2289
1991
 
2290
1992
  // src/record_schemas/generated/index.ts
2291
1993
  var Schemas = {
2292
1994
  ActorRecord: actor_record_schema_default,
2293
1995
  AgentRecord: agent_record_schema_default,
2294
- ChangelogRecord: changelog_record_schema_default,
2295
1996
  CycleRecord: cycle_record_schema_default,
2296
1997
  EmbeddedMetadata: embedded_metadata_schema_default,
2297
1998
  ExecutionRecord: execution_record_schema_default,
@@ -2342,7 +2043,6 @@ var SchemaValidationCache = class {
2342
2043
  const schemaRefMap = {
2343
2044
  "ActorRecord": "ref:actor_record_schema",
2344
2045
  "AgentRecord": "ref:agent_record_schema",
2345
- "ChangelogRecord": "ref:changelog_record_schema",
2346
2046
  "CycleRecord": "ref:cycle_record_schema",
2347
2047
  "ExecutionRecord": "ref:execution_record_schema",
2348
2048
  "FeedbackRecord": "ref:feedback_record_schema",
@@ -2890,10 +2590,6 @@ function generateExecutionId(title, timestamp) {
2890
2590
  const slug = sanitizeForId(title);
2891
2591
  return `${timestamp}-exec-${slug}`;
2892
2592
  }
2893
- function generateChangelogId(title, timestamp) {
2894
- const slug = sanitizeForId(title);
2895
- return `${timestamp}-changelog-${slug}`;
2896
- }
2897
2593
  function generateFeedbackId(title, timestamp) {
2898
2594
  const slug = sanitizeForId(title);
2899
2595
  return `${timestamp}-feedback-${slug}`;
@@ -2912,7 +2608,7 @@ function createTaskRecord(payload) {
2912
2608
  cycleIds: payload.cycleIds,
2913
2609
  references: payload.references,
2914
2610
  notes: payload.notes,
2915
- ...payload
2611
+ metadata: payload.metadata
2916
2612
  };
2917
2613
  const validation = validateTaskRecordDetailed(task);
2918
2614
  if (!validation.isValid) {
@@ -2981,7 +2677,7 @@ function createCycleRecord(payload) {
2981
2677
  childCycleIds: payload.childCycleIds,
2982
2678
  tags: payload.tags,
2983
2679
  notes: payload.notes,
2984
- ...payload
2680
+ metadata: payload.metadata
2985
2681
  };
2986
2682
  const validation = validateCycleRecordDetailed(cycle);
2987
2683
  if (!validation.isValid) {
@@ -3486,8 +3182,8 @@ var FeedbackAdapter = class {
3486
3182
  if (!payloadWithEntityId.entityId) {
3487
3183
  throw new Error("RecordNotFoundError: entityId is required");
3488
3184
  }
3489
- if (payloadWithEntityId.entityType && !["task", "execution", "changelog", "feedback", "cycle"].includes(payloadWithEntityId.entityType)) {
3490
- throw new Error("InvalidEntityTypeError: entityType must be task, execution, changelog, feedback, or cycle");
3185
+ if (payloadWithEntityId.entityType && !["task", "execution", "feedback", "cycle"].includes(payloadWithEntityId.entityType)) {
3186
+ throw new Error("InvalidEntityTypeError: entityType must be task, execution, feedback, or cycle");
3491
3187
  }
3492
3188
  if (payload.type === "assignment" && payload.assignee) {
3493
3189
  const existingFeedbacks = await this.getFeedbackByEntity(payloadWithEntityId.entityId);
@@ -4314,10 +4010,6 @@ var BacklogAdapter = class {
4314
4010
  "execution.created",
4315
4011
  (event) => this.handleExecutionCreated(event)
4316
4012
  );
4317
- this.eventBus.subscribe(
4318
- "changelog.created",
4319
- (event) => this.handleChangelogCreated(event)
4320
- );
4321
4013
  this.eventBus.subscribe(
4322
4014
  "cycle.status.changed",
4323
4015
  (event) => this.handleCycleStatusChanged(event)
@@ -4895,73 +4587,33 @@ ${task.status === "review" ? "[REJECTED]" : "[CANCELLED]"} ${reason} (${(/* @__P
4895
4587
  }
4896
4588
  const actor = await this.getActor(event.payload.triggeredBy);
4897
4589
  const transitionRule = await this.workflowAdapter.getTransitionRule("ready", "active", {
4898
- task,
4899
- actor,
4900
- signatures: []
4901
- });
4902
- if (!transitionRule) {
4903
- console.warn(`Workflow rejected ready\u2192active transition for task ${task.id}`);
4904
- return;
4905
- }
4906
- const updatedTask = { ...task, status: "active" };
4907
- const taskRecord = await this.stores.tasks.get(task.id);
4908
- if (taskRecord) {
4909
- const updatedRecord = { ...taskRecord, payload: updatedTask };
4910
- await this.stores.tasks.put(updatedRecord.payload.id, updatedRecord);
4911
- this.eventBus.publish({
4912
- type: "task.status.changed",
4913
- timestamp: Date.now(),
4914
- source: "backlog_adapter",
4915
- payload: {
4916
- taskId: task.id,
4917
- oldStatus: "ready",
4918
- newStatus: "active",
4919
- actorId: event.payload.triggeredBy
4920
- }
4921
- });
4922
- }
4923
- } catch (error) {
4924
- console.error("Error in handleExecutionCreated:", error);
4925
- }
4926
- }
4927
- /**
4928
- * [EARS-37] Handles changelog created events - transitions done→archived
4929
- */
4930
- async handleChangelogCreated(event) {
4931
- try {
4932
- const changelogRecord = await this.stores.changelogs.get(event.payload.changelogId);
4933
- if (!changelogRecord) {
4934
- console.warn(`Changelog not found: ${event.payload.changelogId}`);
4935
- return;
4936
- }
4937
- if (!changelogRecord.payload.relatedTasks || changelogRecord.payload.relatedTasks.length === 0) {
4938
- return;
4939
- }
4940
- for (const taskId of changelogRecord.payload.relatedTasks) {
4941
- const task = await this.getTask(taskId);
4942
- if (!task || task.status !== "done") {
4943
- continue;
4944
- }
4945
- const updatedTask = { ...task, status: "archived" };
4946
- const taskRecord = await this.stores.tasks.get(task.id);
4947
- if (taskRecord) {
4948
- const updatedRecord = { ...taskRecord, payload: updatedTask };
4949
- await this.stores.tasks.put(updatedRecord.payload.id, updatedRecord);
4950
- this.eventBus.publish({
4951
- type: "task.status.changed",
4952
- timestamp: Date.now(),
4953
- source: "backlog_adapter",
4954
- payload: {
4955
- taskId: task.id,
4956
- oldStatus: "done",
4957
- newStatus: "archived",
4958
- actorId: "system"
4959
- }
4960
- });
4961
- }
4590
+ task,
4591
+ actor,
4592
+ signatures: []
4593
+ });
4594
+ if (!transitionRule) {
4595
+ console.warn(`Workflow rejected ready\u2192active transition for task ${task.id}`);
4596
+ return;
4597
+ }
4598
+ const updatedTask = { ...task, status: "active" };
4599
+ const taskRecord = await this.stores.tasks.get(task.id);
4600
+ if (taskRecord) {
4601
+ const updatedRecord = { ...taskRecord, payload: updatedTask };
4602
+ await this.stores.tasks.put(updatedRecord.payload.id, updatedRecord);
4603
+ this.eventBus.publish({
4604
+ type: "task.status.changed",
4605
+ timestamp: Date.now(),
4606
+ source: "backlog_adapter",
4607
+ payload: {
4608
+ taskId: task.id,
4609
+ oldStatus: "ready",
4610
+ newStatus: "active",
4611
+ actorId: event.payload.triggeredBy
4612
+ }
4613
+ });
4962
4614
  }
4963
4615
  } catch (error) {
4964
- console.error("Error in handleChangelogCreated:", error);
4616
+ console.error("Error in handleExecutionCreated:", error);
4965
4617
  }
4966
4618
  }
4967
4619
  /**
@@ -5365,252 +5017,6 @@ ${task.status === "review" ? "[REJECTED]" : "[CANCELLED]"} ${reason} (${(/* @__P
5365
5017
  }
5366
5018
  };
5367
5019
 
5368
- // src/adapters/changelog_adapter/index.ts
5369
- var changelog_adapter_exports = {};
5370
- __export(changelog_adapter_exports, {
5371
- ChangelogAdapter: () => ChangelogAdapter
5372
- });
5373
-
5374
- // src/record_validations/changelog_validator.ts
5375
- function validateChangelogRecordSchema(data) {
5376
- const validator = SchemaValidationCache.getValidatorFromSchema(Schemas.ChangelogRecord);
5377
- const isValid = validator(data);
5378
- return [isValid, validator.errors];
5379
- }
5380
- function isChangelogRecord(data) {
5381
- const [isValid] = validateChangelogRecordSchema(data);
5382
- return isValid;
5383
- }
5384
- function validateChangelogRecordDetailed(data) {
5385
- const [isValid, errors] = validateChangelogRecordSchema(data);
5386
- if (!isValid && errors) {
5387
- const formattedErrors = errors.map((error) => ({
5388
- field: error.instancePath?.replace("/", "") || error.params?.["missingProperty"] || "root",
5389
- message: error.message || "Unknown validation error",
5390
- value: error.data
5391
- }));
5392
- return {
5393
- isValid: false,
5394
- errors: formattedErrors
5395
- };
5396
- }
5397
- return {
5398
- isValid: true,
5399
- errors: []
5400
- };
5401
- }
5402
- async function validateFullChangelogRecord(record, getPublicKey) {
5403
- const [isValid, errors] = validateChangelogRecordSchema(record.payload);
5404
- if (!isValid) {
5405
- const formattedErrors = (errors || []).map((error) => ({
5406
- field: error.instancePath?.replace("/", "") || error.params?.["missingProperty"] || "root",
5407
- message: error.message || "Unknown validation error",
5408
- value: error.data
5409
- }));
5410
- throw new DetailedValidationError("ChangelogRecord", formattedErrors);
5411
- }
5412
- await validateFullEmbeddedMetadataRecord(record, getPublicKey);
5413
- }
5414
-
5415
- // src/record_factories/changelog_factory.ts
5416
- function createChangelogRecord(payload) {
5417
- const timestamp = Math.floor(Date.now() / 1e3);
5418
- const changelog = {
5419
- // Required fields
5420
- id: payload.id || "",
5421
- title: payload.title || "",
5422
- description: payload.description || "",
5423
- relatedTasks: payload.relatedTasks || [],
5424
- completedAt: payload.completedAt || timestamp,
5425
- // Optional fields (only include if provided)
5426
- ...payload.relatedCycles && { relatedCycles: payload.relatedCycles },
5427
- ...payload.relatedExecutions && { relatedExecutions: payload.relatedExecutions },
5428
- ...payload.version && { version: payload.version },
5429
- ...payload.tags && { tags: payload.tags },
5430
- ...payload.commits && { commits: payload.commits },
5431
- ...payload.files && { files: payload.files },
5432
- ...payload.notes && { notes: payload.notes }
5433
- };
5434
- const validation = validateChangelogRecordDetailed(changelog);
5435
- if (!validation.isValid) {
5436
- throw new DetailedValidationError("ChangelogRecord", validation.errors);
5437
- }
5438
- return changelog;
5439
- }
5440
- function loadChangelogRecord(data) {
5441
- const embeddedValidation = validateEmbeddedMetadataDetailed(data);
5442
- if (!embeddedValidation.isValid) {
5443
- throw new DetailedValidationError("GitGovRecord (ChangelogRecord)", embeddedValidation.errors);
5444
- }
5445
- const record = data;
5446
- const payloadValidation = validateChangelogRecordDetailed(record.payload);
5447
- if (!payloadValidation.isValid) {
5448
- throw new DetailedValidationError("ChangelogRecord payload", payloadValidation.errors);
5449
- }
5450
- return record;
5451
- }
5452
-
5453
- // src/adapters/changelog_adapter/changelog_adapter.ts
5454
- var ChangelogAdapter = class {
5455
- stores;
5456
- identity;
5457
- eventBus;
5458
- constructor(dependencies) {
5459
- this.stores = dependencies.stores;
5460
- this.identity = dependencies.identity;
5461
- this.eventBus = dependencies.eventBus;
5462
- }
5463
- /**
5464
- * [EARS-A1] Records a deliverable/release note.
5465
- *
5466
- * Description: Aggregates multiple tasks into a single deliverable/release note.
5467
- * Implementation: Validates required fields, builds record with factory, signs, persists and emits event.
5468
- * Usage: Invoked by `gitgov changelog add` to document deliverables.
5469
- * Returns: Complete and signed ChangelogRecord.
5470
- */
5471
- async create(payload, actorId) {
5472
- if (!payload.title || payload.title.length < 10) {
5473
- throw new Error("DetailedValidationError: title is required and must be at least 10 characters");
5474
- }
5475
- if (!payload.description || payload.description.length < 20) {
5476
- throw new Error("DetailedValidationError: description is required and must be at least 20 characters");
5477
- }
5478
- if (!payload.relatedTasks || payload.relatedTasks.length === 0) {
5479
- throw new Error("DetailedValidationError: relatedTasks is required and must contain at least one task ID");
5480
- }
5481
- if (payload.relatedTasks) {
5482
- for (const taskId of payload.relatedTasks) {
5483
- const taskExists = await this.stores.tasks.get(taskId);
5484
- if (!taskExists) {
5485
- throw new Error(`RecordNotFoundError: Task not found: ${taskId}`);
5486
- }
5487
- }
5488
- }
5489
- if (payload.relatedCycles) {
5490
- for (const cycleId of payload.relatedCycles) {
5491
- const cycleExists = await this.stores.cycles.get(cycleId);
5492
- if (!cycleExists) {
5493
- throw new Error(`RecordNotFoundError: Cycle not found: ${cycleId}`);
5494
- }
5495
- }
5496
- }
5497
- try {
5498
- const timestamp = payload.completedAt || Math.floor(Date.now() / 1e3);
5499
- if (!payload.id) {
5500
- payload.id = generateChangelogId(payload.title, timestamp);
5501
- }
5502
- const validatedPayload = createChangelogRecord(payload);
5503
- const unsignedRecord = {
5504
- header: {
5505
- version: "1.0",
5506
- type: "changelog",
5507
- payloadChecksum: "will-be-calculated-by-signRecord",
5508
- signatures: [{
5509
- keyId: actorId,
5510
- role: "author",
5511
- notes: "Changelog entry created",
5512
- signature: "placeholder",
5513
- timestamp: Date.now()
5514
- }]
5515
- },
5516
- payload: validatedPayload
5517
- };
5518
- const signedRecord = await this.identity.signRecord(unsignedRecord, actorId, "author", "Changelog record created");
5519
- await this.stores.changelogs.put(validatedPayload.id, signedRecord);
5520
- this.eventBus.publish({
5521
- type: "changelog.created",
5522
- timestamp: Date.now(),
5523
- source: "changelog_adapter",
5524
- payload: {
5525
- changelogId: validatedPayload.id,
5526
- relatedTasks: validatedPayload.relatedTasks,
5527
- title: validatedPayload.title,
5528
- version: validatedPayload.version
5529
- }
5530
- });
5531
- return validatedPayload;
5532
- } catch (error) {
5533
- if (error instanceof Error && error.message.includes("DetailedValidationError")) {
5534
- throw error;
5535
- }
5536
- throw error;
5537
- }
5538
- }
5539
- /**
5540
- * [EARS-B1] Gets a specific ChangelogRecord by its ID.
5541
- */
5542
- async getChangelog(changelogId) {
5543
- const record = await this.stores.changelogs.get(changelogId);
5544
- return record ? record.payload : null;
5545
- }
5546
- /**
5547
- * [EARS-C1] Gets all ChangelogRecords that include a specific task.
5548
- */
5549
- async getChangelogsByTask(taskId) {
5550
- const ids = await this.stores.changelogs.list();
5551
- const changelogs = [];
5552
- for (const id of ids) {
5553
- const record = await this.stores.changelogs.get(id);
5554
- if (record && record.payload.relatedTasks.includes(taskId)) {
5555
- changelogs.push(record.payload);
5556
- }
5557
- }
5558
- return changelogs;
5559
- }
5560
- /**
5561
- * [EARS-D1] Gets all ChangelogRecords with optional filtering and sorting.
5562
- */
5563
- async getAllChangelogs(options) {
5564
- const ids = await this.stores.changelogs.list();
5565
- let changelogs = [];
5566
- for (const id of ids) {
5567
- const record = await this.stores.changelogs.get(id);
5568
- if (record) {
5569
- changelogs.push(record.payload);
5570
- }
5571
- }
5572
- if (options?.tags && options.tags.length > 0) {
5573
- changelogs = changelogs.filter((changelog) => {
5574
- if (!changelog.tags) return false;
5575
- return options.tags.some((tag) => changelog.tags.includes(tag));
5576
- });
5577
- }
5578
- if (options?.version) {
5579
- changelogs = changelogs.filter((changelog) => changelog.version === options.version);
5580
- }
5581
- const sortBy = options?.sortBy || "completedAt";
5582
- const sortOrder = options?.sortOrder || "desc";
5583
- changelogs.sort((a, b) => {
5584
- let compareValue = 0;
5585
- if (sortBy === "completedAt") {
5586
- compareValue = a.completedAt - b.completedAt;
5587
- } else if (sortBy === "title") {
5588
- compareValue = a.title.localeCompare(b.title);
5589
- }
5590
- return sortOrder === "asc" ? compareValue : -compareValue;
5591
- });
5592
- if (options?.limit && options.limit > 0) {
5593
- changelogs = changelogs.slice(0, options.limit);
5594
- }
5595
- return changelogs;
5596
- }
5597
- /**
5598
- * [EARS-E1] Gets recent ChangelogRecords ordered by completedAt.
5599
- */
5600
- async getRecentChangelogs(limit) {
5601
- const allChangelogs = await this.getAllChangelogs();
5602
- const sortedChangelogs = allChangelogs.sort((a, b) => b.completedAt - a.completedAt);
5603
- return sortedChangelogs.slice(0, limit);
5604
- }
5605
- /**
5606
- * Legacy method for backwards compatibility - maps to getChangelogsByTask
5607
- * @deprecated Use getChangelogsByTask instead
5608
- */
5609
- async getChangelogsByEntity(entityId, _entityType) {
5610
- return this.getChangelogsByTask(entityId);
5611
- }
5612
- };
5613
-
5614
5020
  // src/adapters/execution_adapter/index.ts
5615
5021
  var execution_adapter_exports = {};
5616
5022
  __export(execution_adapter_exports, {
@@ -6075,14 +5481,15 @@ __export(workflow_adapter_exports, {
6075
5481
 
6076
5482
  // src/adapters/workflow_adapter/generated/kanban_workflow.json
6077
5483
  var kanban_workflow_default = {
6078
- version: "1.0.0",
5484
+ id: "1700000000-workflow-default-methodology",
6079
5485
  name: "GitGovernance Default Methodology",
6080
5486
  description: "Standard GitGovernance workflow with quality gates and agent collaboration",
6081
5487
  state_transitions: {
6082
- review: {
5488
+ submit: {
6083
5489
  from: [
6084
5490
  "draft"
6085
5491
  ],
5492
+ to: "review",
6086
5493
  requires: {
6087
5494
  command: "gitgov task submit",
6088
5495
  signatures: {
@@ -6096,10 +5503,11 @@ var kanban_workflow_default = {
6096
5503
  }
6097
5504
  }
6098
5505
  },
6099
- ready: {
5506
+ approve: {
6100
5507
  from: [
6101
5508
  "review"
6102
5509
  ],
5510
+ to: "ready",
6103
5511
  requires: {
6104
5512
  command: "gitgov task approve",
6105
5513
  signatures: {
@@ -6127,11 +5535,12 @@ var kanban_workflow_default = {
6127
5535
  }
6128
5536
  }
6129
5537
  },
6130
- active: {
5538
+ activate: {
6131
5539
  from: [
6132
5540
  "ready",
6133
5541
  "paused"
6134
5542
  ],
5543
+ to: "active",
6135
5544
  requires: {
6136
5545
  event: "first_execution_record_created",
6137
5546
  custom_rules: [
@@ -6139,10 +5548,11 @@ var kanban_workflow_default = {
6139
5548
  ]
6140
5549
  }
6141
5550
  },
6142
- done: {
5551
+ complete: {
6143
5552
  from: [
6144
5553
  "active"
6145
5554
  ],
5555
+ to: "done",
6146
5556
  requires: {
6147
5557
  command: "gitgov task complete",
6148
5558
  signatures: {
@@ -6156,28 +5566,31 @@ var kanban_workflow_default = {
6156
5566
  }
6157
5567
  }
6158
5568
  },
6159
- archived: {
5569
+ archive: {
6160
5570
  from: [
6161
5571
  "done"
6162
5572
  ],
5573
+ to: "archived",
6163
5574
  requires: {
6164
- event: "changelog_record_created"
5575
+ command: "gitgov task archive"
6165
5576
  }
6166
5577
  },
6167
- paused: {
5578
+ pause: {
6168
5579
  from: [
6169
5580
  "active",
6170
5581
  "review"
6171
5582
  ],
5583
+ to: "paused",
6172
5584
  requires: {
6173
5585
  event: "feedback_blocking_created"
6174
5586
  }
6175
5587
  },
6176
- discarded: {
5588
+ cancel: {
6177
5589
  from: [
6178
5590
  "ready",
6179
5591
  "active"
6180
5592
  ],
5593
+ to: "discarded",
6181
5594
  requires: {
6182
5595
  command: "gitgov task cancel",
6183
5596
  signatures: {
@@ -6211,14 +5624,15 @@ var kanban_workflow_default = {
6211
5624
 
6212
5625
  // src/adapters/workflow_adapter/generated/scrum_workflow.json
6213
5626
  var scrum_workflow_default = {
6214
- version: "1.0.0",
5627
+ id: "1700000000-workflow-scrum-framework",
6215
5628
  name: "Scrum Framework",
6216
5629
  description: "Agile Scrum methodology with sprint-based workflow and defined roles",
6217
5630
  state_transitions: {
6218
- review: {
5631
+ submit: {
6219
5632
  from: [
6220
5633
  "draft"
6221
5634
  ],
5635
+ to: "review",
6222
5636
  requires: {
6223
5637
  command: "gitgov task submit",
6224
5638
  signatures: {
@@ -6232,10 +5646,11 @@ var scrum_workflow_default = {
6232
5646
  }
6233
5647
  }
6234
5648
  },
6235
- ready: {
5649
+ approve: {
6236
5650
  from: [
6237
5651
  "review"
6238
5652
  ],
5653
+ to: "ready",
6239
5654
  requires: {
6240
5655
  command: "gitgov task approve",
6241
5656
  custom_rules: [
@@ -6243,11 +5658,12 @@ var scrum_workflow_default = {
6243
5658
  ]
6244
5659
  }
6245
5660
  },
6246
- active: {
5661
+ activate: {
6247
5662
  from: [
6248
5663
  "ready",
6249
5664
  "paused"
6250
5665
  ],
5666
+ to: "active",
6251
5667
  requires: {
6252
5668
  event: "sprint_started",
6253
5669
  custom_rules: [
@@ -6255,10 +5671,11 @@ var scrum_workflow_default = {
6255
5671
  ]
6256
5672
  }
6257
5673
  },
6258
- done: {
5674
+ complete: {
6259
5675
  from: [
6260
5676
  "active"
6261
5677
  ],
5678
+ to: "done",
6262
5679
  requires: {
6263
5680
  command: "gitgov task complete",
6264
5681
  signatures: {
@@ -6272,19 +5689,21 @@ var scrum_workflow_default = {
6272
5689
  }
6273
5690
  }
6274
5691
  },
6275
- archived: {
5692
+ archive: {
6276
5693
  from: [
6277
5694
  "done"
6278
5695
  ],
5696
+ to: "archived",
6279
5697
  requires: {
6280
- event: "changelog_record_created"
5698
+ command: "gitgov task archive"
6281
5699
  }
6282
5700
  },
6283
- paused: {
5701
+ pause: {
6284
5702
  from: [
6285
5703
  "active",
6286
5704
  "review"
6287
5705
  ],
5706
+ to: "paused",
6288
5707
  requires: {
6289
5708
  event: "feedback_blocking_created"
6290
5709
  }
@@ -6387,20 +5806,29 @@ var WorkflowAdapter = class _WorkflowAdapter {
6387
5806
  }
6388
5807
  return "__default__";
6389
5808
  }
5809
+ /**
5810
+ * Finds a transition config by matching from and to states.
5811
+ * Keys are transition names (e.g. submit, approve), target state is in transition.to.
5812
+ */
5813
+ findTransitionByStates(from, to) {
5814
+ const config = this.getConfig();
5815
+ for (const transitionConfig of Object.values(config.state_transitions ?? {})) {
5816
+ if (transitionConfig && transitionConfig.to === to && transitionConfig.from.includes(from)) {
5817
+ return transitionConfig;
5818
+ }
5819
+ }
5820
+ return null;
5821
+ }
6390
5822
  /**
6391
5823
  * Determines if a state transition is legal according to the methodology
6392
5824
  */
6393
5825
  async getTransitionRule(from, to, _context) {
6394
- const config = this.getConfig();
6395
- const transitionConfig = config.state_transitions?.[to];
5826
+ const transitionConfig = this.findTransitionByStates(from, to);
6396
5827
  if (!transitionConfig) {
6397
5828
  return null;
6398
5829
  }
6399
- if (!transitionConfig.from.includes(from)) {
6400
- return null;
6401
- }
6402
5830
  return {
6403
- to,
5831
+ to: transitionConfig.to,
6404
5832
  conditions: transitionConfig.requires
6405
5833
  };
6406
5834
  }
@@ -6408,7 +5836,6 @@ var WorkflowAdapter = class _WorkflowAdapter {
6408
5836
  * Validates if an actor's signature meets the requirements for a transition
6409
5837
  */
6410
5838
  async validateSignature(signature, context) {
6411
- const config = this.getConfig();
6412
5839
  if (!context.transitionTo) {
6413
5840
  throw new Error('ValidationContext must include "transitionTo" for signature validation.');
6414
5841
  }
@@ -6417,11 +5844,8 @@ var WorkflowAdapter = class _WorkflowAdapter {
6417
5844
  if (!actor) {
6418
5845
  return false;
6419
5846
  }
6420
- const transitionConfig = config.state_transitions?.[targetState];
5847
+ const transitionConfig = this.findTransitionByStates(context.task.status, targetState);
6421
5848
  if (!transitionConfig) return false;
6422
- if (!transitionConfig.from.includes(context.task.status)) {
6423
- return false;
6424
- }
6425
5849
  const signatureRules = transitionConfig.requires.signatures;
6426
5850
  if (!signatureRules) return true;
6427
5851
  const signatureGroup = this.getApplicableSignatureGroup(signatureRules, actor);
@@ -6503,11 +5927,10 @@ var WorkflowAdapter = class _WorkflowAdapter {
6503
5927
  return [];
6504
5928
  }
6505
5929
  const available = [];
6506
- for (const toState in config.state_transitions) {
6507
- const transitionConfig = config.state_transitions[toState];
5930
+ for (const transitionConfig of Object.values(config.state_transitions)) {
6508
5931
  if (transitionConfig && transitionConfig.from.includes(from)) {
6509
5932
  available.push({
6510
- to: toState,
5933
+ to: transitionConfig.to,
6511
5934
  conditions: transitionConfig.requires
6512
5935
  });
6513
5936
  }
@@ -6641,7 +6064,6 @@ var record_factories_exports = {};
6641
6064
  __export(record_factories_exports, {
6642
6065
  createActorRecord: () => createActorRecord,
6643
6066
  createAgentRecord: () => createAgentRecord,
6644
- createChangelogRecord: () => createChangelogRecord,
6645
6067
  createCycleRecord: () => createCycleRecord,
6646
6068
  createDefaultWorkflowConfig: () => createDefaultWorkflowConfig,
6647
6069
  createEmbeddedMetadataRecord: () => createEmbeddedMetadataRecord,
@@ -6652,7 +6074,6 @@ __export(record_factories_exports, {
6652
6074
  createWorkflowConfig: () => createWorkflowConfig,
6653
6075
  loadActorRecord: () => loadActorRecord,
6654
6076
  loadAgentRecord: () => loadAgentRecord,
6655
- loadChangelogRecord: () => loadChangelogRecord,
6656
6077
  loadCycleRecord: () => loadCycleRecord,
6657
6078
  loadExecutionRecord: () => loadExecutionRecord,
6658
6079
  loadFeedbackRecord: () => loadFeedbackRecord,
@@ -6684,19 +6105,19 @@ function validateWorkflowConfigDetailed(data) {
6684
6105
  function validateWorkflowConfigBusinessRules(config) {
6685
6106
  const errors = [];
6686
6107
  const validStates = ["draft", "review", "ready", "active", "done", "archived", "paused", "discarded"];
6687
- for (const [targetState, transition] of Object.entries(config.state_transitions)) {
6688
- if (!validStates.includes(targetState)) {
6108
+ for (const [transitionName, transition] of Object.entries(config.state_transitions)) {
6109
+ if (transition?.to && !validStates.includes(transition.to)) {
6689
6110
  errors.push({
6690
- field: `state_transitions.${targetState}`,
6691
- message: `Invalid target state: ${targetState}`,
6692
- value: targetState
6111
+ field: `state_transitions.${transitionName}.to`,
6112
+ message: `Invalid target state: ${transition.to}`,
6113
+ value: transition.to
6693
6114
  });
6694
6115
  }
6695
6116
  if (transition?.from) {
6696
6117
  for (const fromState of transition.from) {
6697
6118
  if (!validStates.includes(fromState)) {
6698
6119
  errors.push({
6699
- field: `state_transitions.${targetState}.from`,
6120
+ field: `state_transitions.${transitionName}.from`,
6700
6121
  message: `Invalid source state: ${fromState}`,
6701
6122
  value: fromState
6702
6123
  });
@@ -6707,7 +6128,7 @@ function validateWorkflowConfigBusinessRules(config) {
6707
6128
  for (const ruleId of transition.requires.custom_rules) {
6708
6129
  if (!config.custom_rules[ruleId]) {
6709
6130
  errors.push({
6710
- field: `state_transitions.${targetState}.requires.custom_rules`,
6131
+ field: `state_transitions.${transitionName}.requires.custom_rules`,
6711
6132
  message: `Custom rule '${ruleId}' not defined in custom_rules section`,
6712
6133
  value: ruleId
6713
6134
  });
@@ -6736,12 +6157,13 @@ function validateWorkflowConfigBusinessRules(config) {
6736
6157
  // src/record_factories/workflow_factory.ts
6737
6158
  function createWorkflowConfig(payload) {
6738
6159
  const config = {
6739
- version: payload.version || "1.0.0",
6160
+ id: payload.id || `${Math.floor(Date.now() / 1e3)}-workflow-custom`,
6740
6161
  name: payload.name || "Custom Methodology",
6741
6162
  description: payload.description,
6742
6163
  state_transitions: payload.state_transitions || {
6743
- review: {
6164
+ submit: {
6744
6165
  from: ["draft"],
6166
+ to: "review",
6745
6167
  requires: {
6746
6168
  command: "gitgov task submit",
6747
6169
  signatures: {
@@ -6769,12 +6191,13 @@ function createWorkflowConfig(payload) {
6769
6191
  }
6770
6192
  async function createDefaultWorkflowConfig() {
6771
6193
  return createWorkflowConfig({
6772
- version: "1.0.0",
6194
+ id: "1700000000-workflow-default-methodology",
6773
6195
  name: "GitGovernance Default Methodology",
6774
6196
  description: "Standard GitGovernance workflow with quality gates and agent collaboration",
6775
6197
  state_transitions: {
6776
- review: {
6198
+ submit: {
6777
6199
  from: ["draft"],
6200
+ to: "review",
6778
6201
  requires: {
6779
6202
  command: "gitgov task submit",
6780
6203
  signatures: {
@@ -6786,8 +6209,9 @@ async function createDefaultWorkflowConfig() {
6786
6209
  }
6787
6210
  }
6788
6211
  },
6789
- ready: {
6212
+ approve: {
6790
6213
  from: ["review"],
6214
+ to: "ready",
6791
6215
  requires: {
6792
6216
  command: "gitgov task approve",
6793
6217
  signatures: {
@@ -6809,15 +6233,17 @@ async function createDefaultWorkflowConfig() {
6809
6233
  }
6810
6234
  }
6811
6235
  },
6812
- active: {
6813
- from: ["ready"],
6236
+ activate: {
6237
+ from: ["ready", "paused"],
6238
+ to: "active",
6814
6239
  requires: {
6815
6240
  event: "first_execution_record_created",
6816
6241
  custom_rules: ["task_must_have_valid_assignment_for_executor"]
6817
6242
  }
6818
6243
  },
6819
- done: {
6244
+ complete: {
6820
6245
  from: ["active"],
6246
+ to: "done",
6821
6247
  requires: {
6822
6248
  command: "gitgov task complete",
6823
6249
  signatures: {
@@ -6829,17 +6255,33 @@ async function createDefaultWorkflowConfig() {
6829
6255
  }
6830
6256
  }
6831
6257
  },
6832
- archived: {
6258
+ archive: {
6833
6259
  from: ["done"],
6260
+ to: "archived",
6834
6261
  requires: {
6835
- event: "changelog_record_created"
6262
+ command: "gitgov task archive"
6836
6263
  }
6837
6264
  },
6838
- paused: {
6265
+ pause: {
6839
6266
  from: ["active", "review"],
6267
+ to: "paused",
6840
6268
  requires: {
6841
6269
  event: "feedback_blocking_created"
6842
6270
  }
6271
+ },
6272
+ cancel: {
6273
+ from: ["ready", "active"],
6274
+ to: "discarded",
6275
+ requires: {
6276
+ command: "gitgov task cancel",
6277
+ signatures: {
6278
+ "__default__": {
6279
+ role: "canceller",
6280
+ capability_roles: ["approver:product", "approver:quality"],
6281
+ min_approvals: 1
6282
+ }
6283
+ }
6284
+ }
6843
6285
  }
6844
6286
  },
6845
6287
  custom_rules: {
@@ -6874,7 +6316,6 @@ function createTestSignature(keyId = "human:test-user", role = "author", notes =
6874
6316
  function inferTypeFromPayload(payload) {
6875
6317
  if ("engine" in payload) return "agent";
6876
6318
  if ("taskId" in payload && "result" in payload) return "execution";
6877
- if ("relatedTasks" in payload && "completedAt" in payload) return "changelog";
6878
6319
  if ("entityType" in payload && "entityId" in payload) return "feedback";
6879
6320
  if ("status" in payload && "taskIds" in payload) return "cycle";
6880
6321
  if ("priority" in payload && "description" in payload) return "task";
@@ -7328,6 +6769,7 @@ var FsFileLister = class {
7328
6769
  );
7329
6770
  }
7330
6771
  }
6772
+ const normalized = patterns.map((p) => p.endsWith("/") ? `${p}**` : p);
7331
6773
  const fgOptions = {
7332
6774
  cwd: this.cwd,
7333
6775
  ignore: options?.ignore ?? [],
@@ -7338,7 +6780,7 @@ var FsFileLister = class {
7338
6780
  if (options?.maxDepth !== void 0) {
7339
6781
  fgOptions.deep = options.maxDepth;
7340
6782
  }
7341
- return fg(patterns, fgOptions);
6783
+ return fg(normalized, fgOptions);
7342
6784
  }
7343
6785
  /**
7344
6786
  * [EARS-FL02] Checks if a file exists.
@@ -7578,7 +7020,6 @@ var ENTITY_TO_SCHEMA = {
7578
7020
  agent: "AgentRecord",
7579
7021
  cycle: "CycleRecord",
7580
7022
  execution: "ExecutionRecord",
7581
- changelog: "ChangelogRecord",
7582
7023
  feedback: "FeedbackRecord"
7583
7024
  };
7584
7025
  var LintModule = class {
@@ -7695,8 +7136,7 @@ var LintModule = class {
7695
7136
  ["actor", this.stores.actors],
7696
7137
  ["agent", this.stores.agents],
7697
7138
  ["execution", this.stores.executions],
7698
- ["feedback", this.stores.feedbacks],
7699
- ["changelog", this.stores.changelogs]
7139
+ ["feedback", this.stores.feedbacks]
7700
7140
  ];
7701
7141
  const recordEntries = [];
7702
7142
  for (const [type, store] of storeMap) {
@@ -7822,9 +7262,6 @@ var LintModule = class {
7822
7262
  case "execution":
7823
7263
  loadExecutionRecord(rawRecord);
7824
7264
  break;
7825
- case "changelog":
7826
- loadChangelogRecord(rawRecord);
7827
- break;
7828
7265
  case "feedback":
7829
7266
  loadFeedbackRecord(rawRecord);
7830
7267
  break;
@@ -8647,12 +8084,225 @@ function isRebaseAlreadyInProgressError(error) {
8647
8084
  return error instanceof RebaseAlreadyInProgressError;
8648
8085
  }
8649
8086
 
8087
+ // src/hook_handler/index.ts
8088
+ var hook_handler_exports = {};
8089
+ __export(hook_handler_exports, {
8090
+ HookHandler: () => HookHandler,
8091
+ classifyCommand: () => classifyCommand
8092
+ });
8093
+
8094
+ // src/hook_handler/hook_handler.ts
8095
+ var HookHandler = class {
8096
+ executionAdapter;
8097
+ sessionManager;
8098
+ configManager;
8099
+ constructor(deps) {
8100
+ this.executionAdapter = deps.executionAdapter;
8101
+ this.sessionManager = deps.sessionManager;
8102
+ this.configManager = deps.configManager;
8103
+ }
8104
+ /**
8105
+ * Process a hook event and decide whether to create an ExecutionRecord.
8106
+ * Fail-silent: catches all errors and returns { action: 'skipped', reason }.
8107
+ */
8108
+ async handleEvent(event, options = {}) {
8109
+ const dryRun = options.dryRun ?? false;
8110
+ try {
8111
+ const config = await this.configManager.loadConfig();
8112
+ if (!config) {
8113
+ return { action: "skipped", reason: "no config" };
8114
+ }
8115
+ if (isFileChangedEvent(event)) {
8116
+ return { action: "skipped", reason: "file changes are not recorded" };
8117
+ }
8118
+ if (isTeammateIdleEvent(event)) {
8119
+ return { action: "skipped", reason: "activity logged" };
8120
+ }
8121
+ const actorId = await this.resolveActorId();
8122
+ const activeTaskId = actorId ? (await this.sessionManager.getActorState(actorId))?.activeTaskId ?? null : null;
8123
+ if (isSessionEndEvent(event)) {
8124
+ return await this.handleSessionEnd(event, actorId, activeTaskId, dryRun);
8125
+ }
8126
+ if (!activeTaskId) {
8127
+ return { action: "skipped", reason: "no active task" };
8128
+ }
8129
+ if (isCommandExecutedEvent(event)) {
8130
+ return await this.handleCommandExecuted(event, actorId, activeTaskId, dryRun);
8131
+ }
8132
+ if (isTaskCompletedEvent(event)) {
8133
+ return await this.handleTaskCompleted(event, actorId, activeTaskId, dryRun);
8134
+ }
8135
+ return { action: "skipped", reason: "unknown event type" };
8136
+ } catch (error) {
8137
+ const message = error instanceof Error ? error.message : String(error);
8138
+ return { action: "skipped", reason: message };
8139
+ }
8140
+ }
8141
+ // ─── Command Executed ──────────────────────────────────────
8142
+ async handleCommandExecuted(event, actorId, activeTaskId, dryRun = false) {
8143
+ if (event.exit_code !== 0) {
8144
+ return { action: "skipped", reason: "command failed" };
8145
+ }
8146
+ const classification = classifyCommand(event.tool_input.command, event.tool_output);
8147
+ if (classification.kind === "unknown") {
8148
+ return { action: "skipped", reason: "unrecognized command" };
8149
+ }
8150
+ const payload = this.buildCommandPayload(classification, activeTaskId);
8151
+ if (dryRun) {
8152
+ return { action: "recorded", executionId: "dry-run" };
8153
+ }
8154
+ const record = await this.executionAdapter.create(payload, actorId);
8155
+ return { action: "recorded", executionId: record.id };
8156
+ }
8157
+ buildCommandPayload(classification, activeTaskId) {
8158
+ switch (classification.kind) {
8159
+ // [EARS-B2]
8160
+ case "commit":
8161
+ return {
8162
+ taskId: activeTaskId,
8163
+ type: "completion",
8164
+ title: `Commit ${classification.hash}`,
8165
+ result: `Commit ${classification.hash}: ${classification.message} (${classification.filesChanged} files changed)`,
8166
+ references: [`commit:${classification.hash}`]
8167
+ };
8168
+ // [EARS-B3]
8169
+ case "pr":
8170
+ return {
8171
+ taskId: activeTaskId,
8172
+ type: "completion",
8173
+ title: `PR #${classification.number} created`,
8174
+ result: `PR #${classification.number} created`,
8175
+ references: [`pr:${classification.number}`]
8176
+ };
8177
+ // [EARS-B4]
8178
+ case "test":
8179
+ return {
8180
+ taskId: activeTaskId,
8181
+ type: "analysis",
8182
+ title: "Test run",
8183
+ result: `Tests: ${classification.passed}/${classification.total} passing, ${classification.failed} failed`,
8184
+ metadata: { tests: { passed: classification.passed, failed: classification.failed, total: classification.total } }
8185
+ };
8186
+ }
8187
+ }
8188
+ // ─── Task Completed ────────────────────────────────────────
8189
+ async handleTaskCompleted(event, actorId, activeTaskId, dryRun = false) {
8190
+ const payload = {
8191
+ taskId: activeTaskId,
8192
+ type: "completion",
8193
+ title: `Task completed: ${event.task.subject}`,
8194
+ result: `Task "${event.task.subject}" completed${event.task.owner ? ` by ${event.task.owner}` : ""}`,
8195
+ references: [`task:${event.task.id}`]
8196
+ };
8197
+ if (dryRun) {
8198
+ return { action: "recorded", executionId: "dry-run" };
8199
+ }
8200
+ const record = await this.executionAdapter.create(payload, actorId);
8201
+ return { action: "recorded", executionId: record.id };
8202
+ }
8203
+ // ─── Session End ───────────────────────────────────────────
8204
+ async handleSessionEnd(event, actorId, activeTaskId, dryRun = false) {
8205
+ if (!actorId) {
8206
+ return { action: "skipped", reason: "no actor" };
8207
+ }
8208
+ if (!activeTaskId) {
8209
+ return { action: "skipped", reason: "no active task" };
8210
+ }
8211
+ const taskId = activeTaskId;
8212
+ const payload = {
8213
+ taskId,
8214
+ type: "analysis",
8215
+ title: "Session ended",
8216
+ result: `Session ended${event.session_id ? ` (${event.session_id})` : ""}`
8217
+ };
8218
+ if (dryRun) {
8219
+ return { action: "recorded", executionId: "dry-run" };
8220
+ }
8221
+ const record = await this.executionAdapter.create(payload, actorId);
8222
+ return { action: "recorded", executionId: record.id };
8223
+ }
8224
+ // ─── Helpers ───────────────────────────────────────────────
8225
+ async resolveActorId() {
8226
+ const lastSession = await this.sessionManager.getLastSession();
8227
+ if (lastSession) return lastSession.actorId;
8228
+ const detectedId = await this.sessionManager.detectActorFromKeyFiles();
8229
+ return detectedId;
8230
+ }
8231
+ };
8232
+ function isCommandExecutedEvent(event) {
8233
+ return "tool_name" in event && event.tool_name === "Bash";
8234
+ }
8235
+ function isFileChangedEvent(event) {
8236
+ return "tool_name" in event && (event.tool_name === "Write" || event.tool_name === "Edit");
8237
+ }
8238
+ function isTaskCompletedEvent(event) {
8239
+ return "hook_type" in event && event.hook_type === "TaskCompleted";
8240
+ }
8241
+ function isTeammateIdleEvent(event) {
8242
+ return "hook_type" in event && event.hook_type === "TeammateIdle";
8243
+ }
8244
+ function isSessionEndEvent(event) {
8245
+ return "hook_type" in event && event.hook_type === "Stop";
8246
+ }
8247
+ function classifyCommand(command, output) {
8248
+ if (/git\s+commit/.test(command)) {
8249
+ return parseCommitOutput(output);
8250
+ }
8251
+ if (/gh\s+pr\s+create/.test(command)) {
8252
+ return parsePrOutput(output);
8253
+ }
8254
+ if (/(?:jest|vitest|pytest|npm\s+test|pnpm\s+test|npx\s+vitest|npx\s+jest)/.test(command)) {
8255
+ return parseTestOutput(output);
8256
+ }
8257
+ return { kind: "unknown" };
8258
+ }
8259
+ function parseCommitOutput(output) {
8260
+ if (!output) return { kind: "commit", hash: "unknown", message: "", filesChanged: 0 };
8261
+ const hashMatch = output.match(/\[[\w/.-]+\s+([a-f0-9]+)\]/);
8262
+ const hash = hashMatch?.[1] ?? "unknown";
8263
+ const messageMatch = output.match(/\]\s+(.+?)(?:\n|$)/);
8264
+ const message = messageMatch?.[1] ?? "";
8265
+ const filesMatch = output.match(/(\d+)\s+files?\s+changed/);
8266
+ const filesChanged = filesMatch?.[1] ? parseInt(filesMatch[1], 10) : 0;
8267
+ return { kind: "commit", hash, message, filesChanged };
8268
+ }
8269
+ function parsePrOutput(output) {
8270
+ if (!output) return { kind: "pr", number: "unknown" };
8271
+ const prMatch = output.match(/\/pull\/(\d+)/);
8272
+ if (prMatch?.[1]) return { kind: "pr", number: prMatch[1] };
8273
+ const numMatch = output.match(/#(\d+)/);
8274
+ return { kind: "pr", number: numMatch?.[1] ?? "unknown" };
8275
+ }
8276
+ function parseTestOutput(output) {
8277
+ if (!output) return { kind: "test", passed: 0, failed: 0, total: 0 };
8278
+ let passed = 0;
8279
+ let failed = 0;
8280
+ let total = 0;
8281
+ const vitestMatch = output.match(/Tests?\s+(\d+)\s+passed/);
8282
+ const failedMatch = output.match(/(\d+)\s+failed/);
8283
+ const totalMatch = output.match(/(\d+)\s+total/);
8284
+ if (vitestMatch?.[1]) passed = parseInt(vitestMatch[1], 10);
8285
+ if (failedMatch?.[1]) failed = parseInt(failedMatch[1], 10);
8286
+ if (totalMatch?.[1]) {
8287
+ total = parseInt(totalMatch[1], 10);
8288
+ } else {
8289
+ total = passed + failed;
8290
+ }
8291
+ if (!vitestMatch) {
8292
+ const pytestPassed = output.match(/(\d+)\s+passed/);
8293
+ const pytestFailed = output.match(/(\d+)\s+failed/);
8294
+ if (pytestPassed?.[1]) passed = parseInt(pytestPassed[1], 10);
8295
+ if (pytestFailed?.[1]) failed = parseInt(pytestFailed[1], 10);
8296
+ total = passed + failed;
8297
+ }
8298
+ return { kind: "test", passed, failed, total };
8299
+ }
8300
+
8650
8301
  // src/record_validations/index.ts
8651
8302
  var record_validations_exports = {};
8652
8303
  __export(record_validations_exports, {
8653
8304
  isActorRecord: () => isActorRecord,
8654
8305
  isAgentRecord: () => isAgentRecord,
8655
- isChangelogRecord: () => isChangelogRecord,
8656
8306
  isCycleRecord: () => isCycleRecord,
8657
8307
  isEmbeddedMetadataRecord: () => isEmbeddedMetadataRecord,
8658
8308
  isExecutionRecord: () => isExecutionRecord,
@@ -8664,8 +8314,6 @@ __export(record_validations_exports, {
8664
8314
  validateAgentActorRelationship: () => validateAgentActorRelationship,
8665
8315
  validateAgentRecordDetailed: () => validateAgentRecordDetailed,
8666
8316
  validateAgentRecordSchema: () => validateAgentRecordSchema,
8667
- validateChangelogRecordDetailed: () => validateChangelogRecordDetailed,
8668
- validateChangelogRecordSchema: () => validateChangelogRecordSchema,
8669
8317
  validateCycleRecordDetailed: () => validateCycleRecordDetailed,
8670
8318
  validateCycleRecordSchema: () => validateCycleRecordSchema,
8671
8319
  validateEmbeddedMetadataDetailed: () => validateEmbeddedMetadataDetailed,
@@ -8676,7 +8324,6 @@ __export(record_validations_exports, {
8676
8324
  validateFeedbackRecordSchema: () => validateFeedbackRecordSchema,
8677
8325
  validateFullActorRecord: () => validateFullActorRecord,
8678
8326
  validateFullAgentRecord: () => validateFullAgentRecord,
8679
- validateFullChangelogRecord: () => validateFullChangelogRecord,
8680
8327
  validateFullCycleRecord: () => validateFullCycleRecord,
8681
8328
  validateFullEmbeddedMetadataRecord: () => validateFullEmbeddedMetadataRecord,
8682
8329
  validateFullExecutionRecord: () => validateFullExecutionRecord,
@@ -8692,7 +8339,10 @@ __export(record_validations_exports, {
8692
8339
  // src/record_types/index.ts
8693
8340
  var record_types_exports = {};
8694
8341
  __export(record_types_exports, {
8695
- GitGovError: () => GitGovError
8342
+ DIR_TO_TYPE: () => DIR_TO_TYPE,
8343
+ GitGovError: () => GitGovError,
8344
+ RECORD_TYPES: () => RECORD_TYPES,
8345
+ TYPE_TO_DIR: () => TYPE_TO_DIR
8696
8346
  });
8697
8347
 
8698
8348
  // src/event_bus/index.ts
@@ -10894,7 +10544,6 @@ var RecordProjector = class {
10894
10544
  cycles,
10895
10545
  feedback: await this.readAllFeedback(),
10896
10546
  executions: await this.readAllExecutions(),
10897
- changelogs: await this.readAllChangelogs(),
10898
10547
  actors
10899
10548
  };
10900
10549
  const activityHistory = await this.calculateActivityHistory(allRecords);
@@ -10920,8 +10569,7 @@ var RecordProjector = class {
10920
10569
  cycles: cycles.length,
10921
10570
  actors: actors.length,
10922
10571
  feedback: allRecords.feedback.length,
10923
- executions: allRecords.executions.length,
10924
- changelogs: allRecords.changelogs.length
10572
+ executions: allRecords.executions.length
10925
10573
  },
10926
10574
  generationTime: 0
10927
10575
  // Will be set by caller if needed
@@ -11244,20 +10892,6 @@ var RecordProjector = class {
11244
10892
  }
11245
10893
  return executions;
11246
10894
  }
11247
- /**
11248
- * Reads all changelogs from stores.changelogs with full metadata.
11249
- */
11250
- async readAllChangelogs() {
11251
- const changelogIds = await this.stores.changelogs.list();
11252
- const changelogs = [];
11253
- for (const id of changelogIds) {
11254
- const record = await this.stores.changelogs.get(id);
11255
- if (record) {
11256
- changelogs.push(record);
11257
- }
11258
- }
11259
- return changelogs;
11260
- }
11261
10895
  /**
11262
10896
  * Persists IndexData to sink if available.
11263
10897
  * [EARS-U4] No-op when sink is undefined (writeTime=0).
@@ -11407,22 +11041,6 @@ var RecordProjector = class {
11407
11041
  events.push(event);
11408
11042
  }
11409
11043
  });
11410
- allRecords.changelogs.forEach((changelog) => {
11411
- const timestampPart = changelog.payload.id.split("-")[0];
11412
- if (timestampPart) {
11413
- const event = {
11414
- timestamp: parseInt(timestampPart),
11415
- type: "changelog_created",
11416
- entityId: changelog.payload.id,
11417
- entityTitle: changelog.payload.title || "Release notes",
11418
- actorId: changelog.header.signatures[0]?.keyId || "unknown"
11419
- };
11420
- if (changelog.payload.version) {
11421
- event.metadata = { version: changelog.payload.version };
11422
- }
11423
- events.push(event);
11424
- }
11425
- });
11426
11044
  allRecords.executions.forEach((execution) => {
11427
11045
  const timestampPart = execution.payload.id.split("-")[0];
11428
11046
  if (timestampPart) {
@@ -11500,15 +11118,15 @@ var RecordProjector = class {
11500
11118
  recentActivity = `Execution: ${execution.payload.title || "Work logged"}`;
11501
11119
  }
11502
11120
  }
11503
- const relatedChangelogs = relatedRecords.changelogs.filter(
11504
- (c) => c.payload.relatedTasks && c.payload.relatedTasks.includes(taskPayload.id) || c.payload.description?.includes(taskPayload.id)
11121
+ const relatedReleases = relatedRecords.executions.filter(
11122
+ (e) => e.payload.taskId === taskPayload.id && e.payload.type === "custom:release"
11505
11123
  );
11506
- for (const changelog of relatedChangelogs) {
11507
- const changelogTime = this.getTimestampFromId(changelog.payload.id) * 1e3;
11508
- if (changelogTime > lastUpdated) {
11509
- lastUpdated = changelogTime;
11510
- lastActivityType = "changelog_created";
11511
- recentActivity = `Changelog: ${changelog.payload.title}`;
11124
+ for (const release of relatedReleases) {
11125
+ const releaseTime = this.getTimestampFromId(release.payload.id) * 1e3;
11126
+ if (releaseTime > lastUpdated) {
11127
+ lastUpdated = releaseTime;
11128
+ lastActivityType = "execution_added";
11129
+ recentActivity = `Release: ${release.payload.title}`;
11512
11130
  }
11513
11131
  }
11514
11132
  return { lastUpdated, lastActivityType, recentActivity };
@@ -11537,7 +11155,7 @@ var RecordProjector = class {
11537
11155
  * 5. Cycles (all cycles as array with id+title)
11538
11156
  * 6. Metrics (executionCount, blockingFeedbackCount, openQuestionCount)
11539
11157
  * 7. Time to resolution (for done tasks)
11540
- * 8. Release info (isReleased, lastReleaseVersion from changelogs)
11158
+ * 8. Release info
11541
11159
  * 9. Derived states (EARS-43: REUTILIZA pre-calculated derivedStates con O(1) lookup)
11542
11160
  * 10. Health score (0-100 using multi-factor algorithm)
11543
11161
  * 11. Time in current stage (days)
@@ -11580,11 +11198,12 @@ var RecordProjector = class {
11580
11198
  (f) => f.payload.entityId === task.payload.id && f.payload.type === "question" && f.payload.status === "open"
11581
11199
  ).length;
11582
11200
  const timeToResolution = task.payload.status === "done" ? (lastUpdated - this.getTimestampFromId(task.payload.id) * 1e3) / (1e3 * 60 * 60) : void 0;
11583
- const releaseChangelogs = relatedRecords.changelogs.filter(
11584
- (cl) => cl.payload.relatedTasks.includes(task.payload.id)
11201
+ const releaseExecutions = relatedRecords.executions.filter(
11202
+ (e) => e.payload.taskId === task.payload.id && e.payload.type === "custom:release"
11585
11203
  );
11586
- const isReleased = releaseChangelogs.length > 0;
11587
- const lastReleaseVersion = isReleased ? releaseChangelogs[releaseChangelogs.length - 1]?.payload.version || void 0 : void 0;
11204
+ const isReleased = releaseExecutions.length > 0;
11205
+ const lastReleaseExec = releaseExecutions[releaseExecutions.length - 1];
11206
+ const lastReleaseVersion = isReleased ? lastReleaseExec?.payload.metadata?.["version"] : void 0;
11588
11207
  const taskId = task.payload.id;
11589
11208
  const isStalled = derivedStateSets.stalledTasks.has(taskId);
11590
11209
  const isAtRisk = derivedStateSets.atRiskTasks.has(taskId);
@@ -11670,6 +11289,6 @@ var RecordProjector = class {
11670
11289
  }
11671
11290
  };
11672
11291
 
11673
- export { adapters_exports as Adapters, backlog_adapter_exports as BacklogAdapter, changelog_adapter_exports as ChangelogAdapter, config_manager_exports as Config, crypto_exports as Crypto, diagram_generator_exports as DiagramGenerator, event_bus_exports as EventBus, execution_adapter_exports as ExecutionAdapter, record_factories_exports as Factories, feedback_adapter_exports as FeedbackAdapter, file_lister_exports as FileLister, finding_detector_exports as FindingDetector, git_exports as Git, identity_adapter_exports as IdentityAdapter, key_provider_exports as KeyProvider, lint_exports as Lint, logger_exports as Logger, project_adapter_exports as ProjectAdapter, project_initializer_exports as ProjectInitializer, record_metrics_exports as RecordMetrics, record_projection_exports as RecordProjection, record_types_exports as Records, agent_runner_exports as Runner, record_schemas_exports as Schemas, session_manager_exports as Session, source_auditor_exports as SourceAuditor, record_store_exports as Store, sync_state_exports as SyncState, record_validations_exports as Validation, workflow_adapter_exports as WorkflowAdapter };
11292
+ export { adapters_exports as Adapters, backlog_adapter_exports as BacklogAdapter, config_manager_exports as Config, crypto_exports as Crypto, diagram_generator_exports as DiagramGenerator, event_bus_exports as EventBus, execution_adapter_exports as ExecutionAdapter, record_factories_exports as Factories, feedback_adapter_exports as FeedbackAdapter, file_lister_exports as FileLister, finding_detector_exports as FindingDetector, git_exports as Git, hook_handler_exports as HookHandler, identity_adapter_exports as IdentityAdapter, key_provider_exports as KeyProvider, lint_exports as Lint, logger_exports as Logger, project_adapter_exports as ProjectAdapter, project_initializer_exports as ProjectInitializer, record_metrics_exports as RecordMetrics, record_projection_exports as RecordProjection, record_types_exports as Records, agent_runner_exports as Runner, record_schemas_exports as Schemas, session_manager_exports as Session, source_auditor_exports as SourceAuditor, record_store_exports as Store, sync_state_exports as SyncState, record_validations_exports as Validation, workflow_adapter_exports as WorkflowAdapter };
11674
11293
  //# sourceMappingURL=index.js.map
11675
11294
  //# sourceMappingURL=index.js.map