@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/{agent_runner-DijNVjaF.d.ts → agent_runner-Cgle_zVX.d.ts} +2 -2
- package/dist/src/fs.d.ts +15 -176
- package/dist/src/fs.js +605 -2931
- package/dist/src/fs.js.map +1 -1
- package/dist/src/github.d.ts +115 -115
- package/dist/src/github.js +1594 -1596
- package/dist/src/github.js.map +1 -1
- package/dist/src/index.d.ts +775 -1221
- package/dist/src/index.js +815 -1196
- package/dist/src/index.js.map +1 -1
- package/dist/src/memory.d.ts +1 -1
- package/dist/src/prisma.d.ts +3 -1
- package/dist/src/prisma.js +7 -2
- package/dist/src/prisma.js.map +1 -1
- package/dist/src/{record_projection.types-D9NkQbL_.d.ts → record_projection.types-CFsl44em.d.ts} +139 -166
- package/dist/src/{sync_state-C2a2RuBQ.d.ts → sync_state-B8X4NDKF.d.ts} +8 -4
- package/package.json +1 -1
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
|
|
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
|
|
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
|
|
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
|
|
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
|
|
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:
|
|
904
|
-
|
|
905
|
-
|
|
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: "
|
|
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: "
|
|
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: "
|
|
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
|
-
|
|
975
|
-
|
|
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
|
|
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',
|
|
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
|
-
|
|
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: "
|
|
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:
|
|
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: "
|
|
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:
|
|
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: "
|
|
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:
|
|
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.
|
|
1221
|
-
type: "
|
|
1222
|
-
payloadChecksum: "
|
|
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: "
|
|
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: "
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
"
|
|
1240
|
-
"
|
|
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.
|
|
1142
|
+
version: "1.1",
|
|
1247
1143
|
type: "execution",
|
|
1248
|
-
payloadChecksum: "
|
|
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.
|
|
1277
|
-
type: "
|
|
1278
|
-
|
|
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: "
|
|
1179
|
+
keyId: "agent:deploy-bot",
|
|
1282
1180
|
role: "author",
|
|
1283
|
-
notes: "
|
|
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
|
-
|
|
1298
|
-
|
|
1299
|
-
|
|
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
|
|
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
|
|
1222
|
+
description: "ID of the parent task this execution belongs to."
|
|
1340
1223
|
},
|
|
1341
1224
|
type: {
|
|
1342
1225
|
type: "string",
|
|
1343
|
-
|
|
1344
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
|
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
|
|
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
|
|
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
|
-
"
|
|
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-
|
|
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
|
-
"
|
|
1596
|
-
"
|
|
1597
|
-
"
|
|
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
|
-
|
|
1601
|
-
type: "
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1607
|
-
|
|
1608
|
-
|
|
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
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
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
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1622
|
-
|
|
1623
|
-
|
|
1624
|
-
|
|
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
|
-
|
|
1628
|
-
|
|
1629
|
-
|
|
1630
|
-
|
|
1631
|
-
|
|
1632
|
-
|
|
1633
|
-
|
|
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
|
-
|
|
1637
|
-
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
|
|
1641
|
-
{
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
|
|
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: "
|
|
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: "
|
|
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: "
|
|
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: "
|
|
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
|
|
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:
|
|
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: "
|
|
1743
|
+
$id: "workflow_record_schema.json",
|
|
1872
1744
|
title: "WorkflowRecord",
|
|
1873
|
-
description: "
|
|
1745
|
+
description: "Schema for workflow methodology configuration that defines named state transitions, signatures, and custom rules.",
|
|
1874
1746
|
type: "object",
|
|
1875
1747
|
required: [
|
|
1876
|
-
"
|
|
1748
|
+
"id",
|
|
1877
1749
|
"name",
|
|
1878
1750
|
"state_transitions"
|
|
1879
1751
|
],
|
|
1880
1752
|
additionalProperties: false,
|
|
1881
1753
|
properties: {
|
|
1882
|
-
|
|
1883
|
-
type: "string",
|
|
1884
|
-
description: "JSON Schema reference"
|
|
1885
|
-
},
|
|
1886
|
-
version: {
|
|
1754
|
+
id: {
|
|
1887
1755
|
type: "string",
|
|
1888
|
-
pattern: "^\\d
|
|
1889
|
-
|
|
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: "
|
|
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
|
|
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:
|
|
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'
|
|
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
|
|
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: "
|
|
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
|
|
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
|
|
1956
|
+
description: "Required capability roles (matches any agent with these roles)"
|
|
2079
1957
|
},
|
|
2080
1958
|
triggers: {
|
|
2081
1959
|
type: "array",
|
|
2082
|
-
description: "
|
|
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
|
-
|
|
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
|
-
|
|
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", "
|
|
3490
|
-
throw new Error("InvalidEntityTypeError: entityType must be task, execution,
|
|
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
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
5569
|
+
archive: {
|
|
6160
5570
|
from: [
|
|
6161
5571
|
"done"
|
|
6162
5572
|
],
|
|
5573
|
+
to: "archived",
|
|
6163
5574
|
requires: {
|
|
6164
|
-
|
|
5575
|
+
command: "gitgov task archive"
|
|
6165
5576
|
}
|
|
6166
5577
|
},
|
|
6167
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
5692
|
+
archive: {
|
|
6276
5693
|
from: [
|
|
6277
5694
|
"done"
|
|
6278
5695
|
],
|
|
5696
|
+
to: "archived",
|
|
6279
5697
|
requires: {
|
|
6280
|
-
|
|
5698
|
+
command: "gitgov task archive"
|
|
6281
5699
|
}
|
|
6282
5700
|
},
|
|
6283
|
-
|
|
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
|
|
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 =
|
|
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
|
|
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:
|
|
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 [
|
|
6688
|
-
if (!validStates.includes(
|
|
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.${
|
|
6691
|
-
message: `Invalid target state: ${
|
|
6692
|
-
value:
|
|
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.${
|
|
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.${
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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
|
-
|
|
6258
|
+
archive: {
|
|
6833
6259
|
from: ["done"],
|
|
6260
|
+
to: "archived",
|
|
6834
6261
|
requires: {
|
|
6835
|
-
|
|
6262
|
+
command: "gitgov task archive"
|
|
6836
6263
|
}
|
|
6837
6264
|
},
|
|
6838
|
-
|
|
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(
|
|
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
|
-
|
|
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
|
|
11504
|
-
(
|
|
11121
|
+
const relatedReleases = relatedRecords.executions.filter(
|
|
11122
|
+
(e) => e.payload.taskId === taskPayload.id && e.payload.type === "custom:release"
|
|
11505
11123
|
);
|
|
11506
|
-
for (const
|
|
11507
|
-
const
|
|
11508
|
-
if (
|
|
11509
|
-
lastUpdated =
|
|
11510
|
-
lastActivityType = "
|
|
11511
|
-
recentActivity = `
|
|
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
|
|
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
|
|
11584
|
-
(
|
|
11201
|
+
const releaseExecutions = relatedRecords.executions.filter(
|
|
11202
|
+
(e) => e.payload.taskId === task.payload.id && e.payload.type === "custom:release"
|
|
11585
11203
|
);
|
|
11586
|
-
const isReleased =
|
|
11587
|
-
const
|
|
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,
|
|
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
|