@xn-intenton-z2a/agentic-lib 7.4.14 → 7.4.16

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.
Files changed (55) hide show
  1. package/.github/agents/agent-apply-fix.md +30 -1
  2. package/.github/agents/agent-director.md +28 -7
  3. package/.github/agents/agent-discussion-bot.md +28 -0
  4. package/.github/agents/agent-implementation-review.md +21 -0
  5. package/.github/agents/agent-issue-resolution.md +32 -0
  6. package/.github/agents/agent-iterate.md +33 -0
  7. package/.github/agents/agent-maintain-features.md +34 -0
  8. package/.github/agents/agent-maintain-library.md +39 -0
  9. package/.github/agents/agent-ready-issue.md +21 -0
  10. package/.github/agents/agent-review-issue.md +16 -0
  11. package/.github/agents/agent-supervisor.md +60 -0
  12. package/.github/workflows/agentic-lib-init.yml +76 -11
  13. package/.github/workflows/agentic-lib-schedule.yml +58 -6
  14. package/.github/workflows/agentic-lib-test.yml +31 -3
  15. package/.github/workflows/agentic-lib-update.yml +20 -0
  16. package/.github/workflows/agentic-lib-workflow.yml +42 -7
  17. package/README.md +23 -12
  18. package/agentic-lib.toml +2 -2
  19. package/bin/agentic-lib.js +34 -4
  20. package/package.json +1 -1
  21. package/src/actions/agentic-step/index.js +35 -10
  22. package/src/actions/agentic-step/logging.js +5 -2
  23. package/src/actions/agentic-step/tasks/direct.js +50 -16
  24. package/src/actions/agentic-step/tasks/maintain-features.js +7 -0
  25. package/src/actions/agentic-step/tasks/maintain-library.js +10 -0
  26. package/src/actions/agentic-step/tasks/transform.js +37 -1
  27. package/src/actions/commit-if-changed/action.yml +2 -1
  28. package/src/copilot/config.js +2 -2
  29. package/src/copilot/github-tools.js +8 -2
  30. package/src/copilot/guards.js +4 -10
  31. package/src/copilot/state.js +214 -0
  32. package/src/copilot/telemetry.js +92 -10
  33. package/src/seeds/missions/1-dan-create-c64-emulator.md +13 -13
  34. package/src/seeds/missions/1-dan-create-planning-engine.md +82 -0
  35. package/src/seeds/missions/1-kyu-create-ray-tracer.md +31 -8
  36. package/src/seeds/missions/2-dan-create-self-hosted.md +67 -0
  37. package/src/seeds/missions/2-kyu-create-markdown-compiler.md +48 -0
  38. package/src/seeds/missions/2-kyu-create-plot-code-lib.md +35 -16
  39. package/src/seeds/missions/3-kyu-analyze-lunar-lander.md +13 -14
  40. package/src/seeds/missions/3-kyu-evaluate-time-series-lab.md +22 -28
  41. package/src/seeds/missions/4-kyu-analyze-json-schema-diff.md +46 -2
  42. package/src/seeds/missions/4-kyu-apply-cron-engine.md +16 -18
  43. package/src/seeds/missions/4-kyu-apply-dense-encoding.md +14 -11
  44. package/src/seeds/missions/4-kyu-apply-owl-ontology.md +47 -0
  45. package/src/seeds/missions/5-kyu-apply-ascii-face.md +40 -0
  46. package/src/seeds/missions/5-kyu-apply-string-utils.md +17 -17
  47. package/src/seeds/missions/6-kyu-understand-hamming-distance.md +12 -12
  48. package/src/seeds/missions/6-kyu-understand-roman-numerals.md +12 -12
  49. package/src/seeds/missions/8-kyu-remember-hello-world.md +10 -0
  50. package/src/seeds/zero-MISSION.md +12 -12
  51. package/src/seeds/zero-package.json +1 -1
  52. package/src/seeds/missions/2-dan-create-agi.md +0 -22
  53. package/src/seeds/missions/2-kyu-evaluate-markdown-compiler.md +0 -33
  54. package/src/seeds/missions/3-kyu-evaluate-owl-ontology.md +0 -34
  55. package/src/seeds/missions/5-kyu-create-ascii-face.md +0 -4
@@ -79,7 +79,26 @@ permissions:
79
79
  contents: write
80
80
 
81
81
  jobs:
82
+ params:
83
+ runs-on: ubuntu-latest
84
+ outputs:
85
+ frequency: ${{ steps.resolve.outputs.frequency }}
86
+ model: ${{ steps.resolve.outputs.model }}
87
+ profile: ${{ steps.resolve.outputs.profile }}
88
+ maintenance: ${{ steps.resolve.outputs.maintenance }}
89
+ steps:
90
+ - id: resolve
91
+ uses: actions/github-script@v8
92
+ with:
93
+ script: |
94
+ const frequency = context.payload.inputs?.['frequency'] || 'off';
95
+ core.setOutput('frequency', frequency);
96
+ core.setOutput('model', context.payload.inputs?.['model'] || '');
97
+ core.setOutput('profile', context.payload.inputs?.['profile'] || '');
98
+ core.setOutput('maintenance', frequency === 'maintenance' ? 'true' : 'false');
99
+
82
100
  update-schedule:
101
+ needs: [params]
83
102
  runs-on: ubuntu-latest
84
103
  steps:
85
104
  - uses: actions/checkout@v6
@@ -112,8 +131,10 @@ jobs:
112
131
  const isMaintenance = frequency === 'maintenance';
113
132
  const effectiveFrequency = isMaintenance ? 'weekly' : frequency;
114
133
 
134
+ // Problem 4 fix: Use a "never fires" cron for off instead of removing the block.
135
+ // Keeping the schedule: block permanently avoids GitHub cron de-registration issues.
115
136
  const SCHEDULE_MAP = {
116
- off: null,
137
+ off: '0 0 31 2 *',
117
138
  weekly: '25 6 * * 1',
118
139
  daily: '25 6 * * *',
119
140
  hourly: '25 * * * *',
@@ -147,11 +168,12 @@ jobs:
147
168
  }
148
169
  }
149
170
 
150
- // Remove any existing schedule block
151
- content = content.replace(/\n schedule:\n - cron: "[^"]*"\n/g, '\n');
152
-
153
- if (cron) {
154
- // Insert schedule block after the 'on:' line
171
+ // Replace existing schedule cron or insert a new block
172
+ const cronRegexReplace = /- cron: "[^"]*"/;
173
+ if (cronRegexReplace.test(content)) {
174
+ content = content.replace(cronRegexReplace, `- cron: "${cron}"`);
175
+ } else {
176
+ // No schedule block exists — insert one after 'on:'
155
177
  const scheduleBlock = `\n schedule:\n - cron: "${cron}"\n`;
156
178
  content = content.replace(
157
179
  /\non:\n/,
@@ -261,3 +283,33 @@ jobs:
261
283
  exit 1
262
284
  fi
263
285
  done
286
+
287
+ - name: "Problem 2 fix: Verify schedule registered with GitHub"
288
+ if: github.repository != 'xn-intenton-z2a/agentic-lib' && inputs.dry-run != 'true' && inputs.dry-run != true
289
+ env:
290
+ GH_TOKEN: ${{ secrets.WORKFLOW_TOKEN }}
291
+ run: |
292
+ echo "Waiting 10s for GitHub to process the push..."
293
+ sleep 10
294
+ WORKFLOW_STATE=$(gh api "repos/${{ github.repository }}/actions/workflows/agentic-lib-workflow.yml" --jq '.state' 2>/dev/null || echo "unknown")
295
+ echo "Workflow state: ${WORKFLOW_STATE}"
296
+ if [ "$WORKFLOW_STATE" != "active" ]; then
297
+ echo "::warning::Workflow state is '${WORKFLOW_STATE}', attempting to enable..."
298
+ gh api "repos/${{ github.repository }}/actions/workflows/agentic-lib-workflow.yml/enable" -X PUT 2>/dev/null || true
299
+ WORKFLOW_STATE=$(gh api "repos/${{ github.repository }}/actions/workflows/agentic-lib-workflow.yml" --jq '.state' 2>/dev/null || echo "unknown")
300
+ echo "Workflow state after enable: ${WORKFLOW_STATE}"
301
+ fi
302
+ # Verify the cron was registered by checking the workflow definition
303
+ FREQUENCY="${{ inputs.frequency }}"
304
+ if [ "$FREQUENCY" != "off" ]; then
305
+ echo "Verifying cron schedule is active..."
306
+ gh api "repos/${{ github.repository }}/actions/workflows" --jq '.workflows[] | select(.name == "agentic-lib-workflow") | "state=\(.state)"' 2>/dev/null || true
307
+ fi
308
+
309
+ - name: Job Summary
310
+ if: always()
311
+ uses: actions/github-script@v8
312
+ with:
313
+ script: |
314
+ const summary = `## Job: update-schedule\n| Key | Value |\n|-----|-------|\n| Status | ${context.job.status || 'completed'} |\n| Frequency | ${{ inputs.frequency }} |\n| Model | ${{ inputs.model || 'default' }} |\n| Profile | ${{ inputs.profile || 'default' }} |`;
315
+ core.summary.addRaw(summary).write();
@@ -58,7 +58,19 @@ permissions:
58
58
  issues: write
59
59
 
60
60
  jobs:
61
+ params:
62
+ runs-on: ubuntu-latest
63
+ outputs:
64
+ dry-run: ${{ steps.resolve.outputs.dry-run }}
65
+ steps:
66
+ - id: resolve
67
+ uses: actions/github-script@v8
68
+ with:
69
+ script: |
70
+ core.setOutput('dry-run', context.payload.inputs?.['dry-run'] || 'false');
71
+
61
72
  test:
73
+ needs: [params]
62
74
  runs-on: ubuntu-latest
63
75
  steps:
64
76
  - uses: actions/checkout@v6
@@ -86,6 +98,14 @@ jobs:
86
98
  - name: Run tests
87
99
  run: ${{ steps.config.outputs.test-command }}
88
100
 
101
+ - name: Job Summary
102
+ if: always()
103
+ uses: actions/github-script@v8
104
+ with:
105
+ script: |
106
+ const summary = `## Job: test\n| Key | Value |\n|-----|-------|\n| Status | ${context.job.status || 'completed'} |`;
107
+ core.summary.addRaw(summary).write();
108
+
89
109
  behaviour:
90
110
  if: github.repository != 'xn-intenton-z2a/agentic-lib'
91
111
  continue-on-error: true
@@ -139,9 +159,17 @@ jobs:
139
159
  LOG_BRANCH: ${{ inputs.log-branch || 'agentic-lib-logs' }}
140
160
  run: bash .github/agentic-lib/scripts/push-to-logs.sh "${SCREENSHOT_FILE:-SCREENSHOT_INDEX.png}"
141
161
 
162
+ - name: Job Summary
163
+ if: always()
164
+ uses: actions/github-script@v8
165
+ with:
166
+ script: |
167
+ const summary = `## Job: behaviour\n| Key | Value |\n|-----|-------|\n| Status | ${context.job.status || 'completed'} |\n| Tests Failed | ${{ steps.result.outputs.tests-failed }} |`;
168
+ core.summary.addRaw(summary).write();
169
+
142
170
  # ─── Dispatch fix workflow when unit tests fail on main ─────────────
143
171
  dispatch-fix:
144
- needs: [test]
172
+ needs: [params, test]
145
173
  if: >-
146
174
  !cancelled()
147
175
  && github.ref == 'refs/heads/main'
@@ -183,7 +211,7 @@ jobs:
183
211
 
184
212
  # ─── Report instability: install or unit test failure → automated + instability ──
185
213
  report-instability:
186
- needs: [test]
214
+ needs: [params, test]
187
215
  if: >-
188
216
  !cancelled()
189
217
  && github.ref == 'refs/heads/main'
@@ -293,7 +321,7 @@ jobs:
293
321
 
294
322
  # ─── Report behaviour failure: behaviour test failure → automated only ──
295
323
  report-behaviour:
296
- needs: [behaviour]
324
+ needs: [params, behaviour]
297
325
  if: >-
298
326
  !cancelled()
299
327
  && github.ref == 'refs/heads/main'
@@ -37,7 +37,19 @@ on:
37
37
  permissions: write-all
38
38
 
39
39
  jobs:
40
+ params:
41
+ runs-on: ubuntu-latest
42
+ outputs:
43
+ dry-run: ${{ steps.resolve.outputs.dry-run }}
44
+ steps:
45
+ - id: resolve
46
+ uses: actions/github-script@v8
47
+ with:
48
+ script: |
49
+ core.setOutput('dry-run', context.payload.inputs?.['dry-run'] || 'false');
50
+
40
51
  update:
52
+ needs: [params]
41
53
  runs-on: ubuntu-latest
42
54
  steps:
43
55
  - uses: actions/checkout@v6
@@ -109,3 +121,11 @@ jobs:
109
121
  exit 1
110
122
  fi
111
123
  done
124
+
125
+ - name: Job Summary
126
+ if: always()
127
+ uses: actions/github-script@v8
128
+ with:
129
+ script: |
130
+ const summary = `## Job: update\n| Key | Value |\n|-----|-------|\n| Status | ${context.job.status || 'completed'} |\n| Dry Run | ${{ inputs.dry-run }} |`;
131
+ core.summary.addRaw(summary).write();
@@ -590,7 +590,9 @@ jobs:
590
590
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
591
591
  SCREENSHOT_FILE: ${{ needs.params.outputs.screenshot-file }}
592
592
  run: |
593
+ git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
593
594
  git show "origin/${LOG_BRANCH}:${SCREENSHOT_FILE}" > "${SCREENSHOT_FILE}" 2>/dev/null || true
595
+ git show "origin/${LOG_BRANCH}:agentic-lib-state.toml" > "agentic-lib-state.toml" 2>/dev/null || true
594
596
 
595
597
  - name: Check mission-complete signal
596
598
  id: mission-check
@@ -700,7 +702,7 @@ jobs:
700
702
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && needs.params.outputs.dry-run != 'true'
701
703
  env:
702
704
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
703
- run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md
705
+ run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md agentic-lib-state.toml
704
706
 
705
707
  # ─── Implementation Review: traces mission elements through code/tests/website ──
706
708
  implementation-review:
@@ -724,9 +726,10 @@ jobs:
724
726
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
725
727
  SCREENSHOT_FILE: ${{ needs.params.outputs.screenshot-file }}
726
728
  run: |
729
+ git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
727
730
  git show "origin/${LOG_BRANCH}:${SCREENSHOT_FILE}" > "${SCREENSHOT_FILE}" 2>/dev/null || true
731
+ git show "origin/${LOG_BRANCH}:agentic-lib-state.toml" > "agentic-lib-state.toml" 2>/dev/null || true
728
732
  mkdir -p .agent-logs
729
- git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
730
733
  for f in $(git ls-tree --name-only "origin/${LOG_BRANCH}" 2>/dev/null | grep '^agent-log-' || true); do
731
734
  git show "origin/${LOG_BRANCH}:${f}" > ".agent-logs/${f}" 2>/dev/null || true
732
735
  done
@@ -765,7 +768,7 @@ jobs:
765
768
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && needs.params.outputs.dry-run != 'true'
766
769
  env:
767
770
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
768
- run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md
771
+ run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md agentic-lib-state.toml
769
772
 
770
773
  # ─── Director: LLM evaluates mission status (complete/failed/in-progress) ──
771
774
  director:
@@ -789,7 +792,9 @@ jobs:
789
792
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
790
793
  SCREENSHOT_FILE: ${{ needs.params.outputs.screenshot-file }}
791
794
  run: |
795
+ git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
792
796
  git show "origin/${LOG_BRANCH}:${SCREENSHOT_FILE}" > "${SCREENSHOT_FILE}" 2>/dev/null || true
797
+ git show "origin/${LOG_BRANCH}:agentic-lib-state.toml" > "agentic-lib-state.toml" 2>/dev/null || true
793
798
 
794
799
  - uses: actions/setup-node@v6
795
800
  with:
@@ -826,7 +831,7 @@ jobs:
826
831
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && needs.params.outputs.dry-run != 'true'
827
832
  env:
828
833
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
829
- run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md
834
+ run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md agentic-lib-state.toml
830
835
 
831
836
  # ─── Supervisor: LLM decides what to do (after director evaluates) ──
832
837
  supervisor:
@@ -838,20 +843,48 @@ jobs:
838
843
  needs.director.outputs.decision != 'mission-complete' &&
839
844
  needs.director.outputs.decision != 'mission-failed'
840
845
  runs-on: ubuntu-latest
846
+ outputs:
847
+ backoff-skip: ${{ steps.backoff.outputs.skip }}
841
848
  steps:
842
849
  - uses: actions/checkout@v6
843
850
  with:
844
851
  fetch-depth: 0
845
852
  ref: ${{ needs.maintain.outputs.commit-sha || github.sha }}
846
853
 
847
- - name: Fetch log and screenshot from log branch
854
+ - name: Fetch log, screenshot and state from log branch
848
855
  env:
849
856
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
850
857
  SCREENSHOT_FILE: ${{ needs.params.outputs.screenshot-file }}
851
858
  run: |
859
+ git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
852
860
  git show "origin/${LOG_BRANCH}:${SCREENSHOT_FILE}" > "${SCREENSHOT_FILE}" 2>/dev/null || true
861
+ git show "origin/${LOG_BRANCH}:agentic-lib-state.toml" > "agentic-lib-state.toml" 2>/dev/null || true
862
+
863
+ - name: "C15: Check nop backoff"
864
+ id: backoff
865
+ uses: actions/github-script@v8
866
+ with:
867
+ script: |
868
+ const fs = require('fs');
869
+ let nopCount = 0;
870
+ try {
871
+ const content = fs.readFileSync('agentic-lib-state.toml', 'utf8');
872
+ const match = content.match(/cumulative-nop-cycles\s*=\s*(\d+)/);
873
+ if (match) nopCount = parseInt(match[1], 10);
874
+ } catch { /* no state file yet */ }
875
+ core.info(`Consecutive nop cycles: ${nopCount}`);
876
+ let shouldSkip = false;
877
+ if (nopCount > 3) {
878
+ const pow = Math.pow(2, Math.floor(Math.log2(nopCount)));
879
+ if (nopCount !== pow) {
880
+ shouldSkip = true;
881
+ core.info(`Backoff: skipping (nop count ${nopCount}, next run at ${pow * 2})`);
882
+ }
883
+ }
884
+ core.setOutput('skip', shouldSkip ? 'true' : 'false');
853
885
 
854
886
  - uses: actions/setup-node@v6
887
+ if: steps.backoff.outputs.skip != 'true'
855
888
  with:
856
889
  node-version: "24"
857
890
 
@@ -886,7 +919,7 @@ jobs:
886
919
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && needs.params.outputs.dry-run != 'true'
887
920
  env:
888
921
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
889
- run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md
922
+ run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md agentic-lib-state.toml
890
923
 
891
924
  # ─── Fix stuck PRs with failing checks ─────────────────────────────
892
925
  fix-stuck:
@@ -1285,7 +1318,9 @@ jobs:
1285
1318
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
1286
1319
  SCREENSHOT_FILE: ${{ needs.params.outputs.screenshot-file }}
1287
1320
  run: |
1321
+ git fetch origin "${LOG_BRANCH}" 2>/dev/null || true
1288
1322
  git show "origin/${LOG_BRANCH}:${SCREENSHOT_FILE}" > "${SCREENSHOT_FILE}" 2>/dev/null || true
1323
+ git show "origin/${LOG_BRANCH}:agentic-lib-state.toml" > "agentic-lib-state.toml" 2>/dev/null || true
1289
1324
 
1290
1325
  - uses: actions/setup-node@v6
1291
1326
  with:
@@ -1455,7 +1490,7 @@ jobs:
1455
1490
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && needs.params.outputs.dry-run != 'true'
1456
1491
  env:
1457
1492
  LOG_BRANCH: ${{ needs.params.outputs.log-branch }}
1458
- run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md
1493
+ run: bash .github/agentic-lib/scripts/push-to-logs.sh agent-log-*.md agentic-lib-state.toml
1459
1494
 
1460
1495
  - name: Create PR and attempt merge
1461
1496
  if: github.repository != 'xn-intenton-z2a/agentic-lib' && steps.issue.outputs.issue-number != '' && needs.params.outputs.dry-run != 'true' && steps.pre-commit-test.outputs.tests-passed == 'true' && steps.pre-commit-behaviour-test.outputs.tests-passed != 'false'
package/README.md CHANGED
@@ -62,13 +62,12 @@ your-repo/
62
62
 
63
63
  ├── .github/
64
64
  │ ├── workflows/ # [INIT] 8 workflow files (always overwritten)
65
- │ │ ├── agent-flow-transform.yml # Core: transform code toward the mission
66
- │ │ ├── agent-flow-maintain.yml # Core: maintain features and library
67
- │ │ ├── agent-flow-review.yml # Core: review and close resolved issues
68
- │ │ ├── agent-flow-fix-code.yml # Core: fix failing tests
69
- │ │ ├── agent-discussions-bot.yml # Bot: respond to GitHub Discussions
70
- │ │ ├── agent-supervisor.yml # Supervisor: orchestrate the pipeline
71
- │ │ ├── ci-automerge.yml # CI: auto-merge passing PRs
65
+ │ │ ├── agentic-lib-workflow.yml # Core: supervisor + transform + maintain + review + dev
66
+ │ │ ├── agentic-lib-bot.yml # Bot: respond to GitHub Discussions
67
+ │ │ ├── agentic-lib-test.yml # CI: run unit + behaviour tests, dispatch fixes
68
+ │ │ ├── agentic-lib-init.yml # Infra: init/purge, optional seed issues
69
+ │ │ ├── agentic-lib-update.yml # Infra: update agentic-lib version
70
+ │ │ ├── agentic-lib-schedule.yml # Infra: change supervisor schedule
72
71
  │ │ └── test.yml # CI: run tests
73
72
  │ │
74
73
  │ └── agentic-lib/ # [INIT] Internal infrastructure (always overwritten)
@@ -187,10 +186,20 @@ profile = "recommended" # min | recommended | max
187
186
  # model = "gpt-5-mini" # override model per-profile
188
187
  # transformation-budget = 8 # max code-changing cycles per run
189
188
 
189
+ [mission-complete]
190
+ min-resolved-issues = 2 # minimum closed-as-RESOLVED issues since init
191
+ max-source-todos = 0 # max TODO comments allowed in ./src (0 = none)
192
+
190
193
  [bot]
191
- log-file = "intentïon.md"
194
+ log-prefix = "agent-log-"
195
+ log-branch = "agentic-lib-logs"
196
+ screenshot-file = "SCREENSHOT_INDEX.png"
192
197
  ```
193
198
 
199
+ ### Persistent State
200
+
201
+ The system maintains `agentic-lib-state.toml` on the `agentic-lib-logs` branch to track counters, budget, and status across workflow runs. This file is automatically created on `init --purge` and updated after each `agentic-step` invocation. It tracks cumulative transforms, token usage, consecutive nop cycles (for backoff), and mission status.
202
+
194
203
  ### Tuning Profiles
195
204
 
196
205
  The `profile` setting controls all tuning defaults. Three profiles are built in:
@@ -219,6 +228,7 @@ The core of the system is a single GitHub Action that handles all autonomous tas
219
228
  | `enhance-issue` | Add detail and acceptance criteria to issues |
220
229
  | `review-issue` | Review and close resolved issues |
221
230
  | `discussions` | Respond to GitHub Discussions |
231
+ | `implementation-review` | Review implementation completeness against mission |
222
232
 
223
233
  Each task calls the GitHub Copilot SDK with context assembled from your repository (mission, code, tests, features) and writes changes back to the working tree. The supervisor can dispatch any of the other tasks via workflow dispatch.
224
234
 
@@ -321,19 +331,20 @@ The session uses SDK hooks for observability (tool call tracking, error recovery
321
331
  | `7-kyu-understand-fizz-buzz` | 7 kyu | Understand | Classic FizzBuzz |
322
332
  | `6-kyu-understand-hamming-distance` | 6 kyu | Understand | Hamming distance (strings + bits) |
323
333
  | `6-kyu-understand-roman-numerals` | 6 kyu | Understand | Roman numeral conversion |
324
- | `5-kyu-create-ascii-face` | 5 kyu | Create | ASCII face art |
334
+ | `5-kyu-apply-ascii-face` | 5 kyu | Apply | ASCII face art |
325
335
  | `5-kyu-apply-string-utils` | 5 kyu | Apply | 10 string utility functions |
326
336
  | `4-kyu-apply-cron-engine` | 4 kyu | Apply | Cron expression parser |
327
337
  | `4-kyu-apply-dense-encoding` | 4 kyu | Apply | Dense binary encoding |
328
338
  | `4-kyu-analyze-json-schema-diff` | 4 kyu | Analyze | JSON Schema diff |
339
+ | `4-kyu-apply-owl-ontology` | 4 kyu | Apply | OWL ontology processor |
329
340
  | `3-kyu-analyze-lunar-lander` | 3 kyu | Analyze | Lunar lander simulation |
330
341
  | `3-kyu-evaluate-time-series-lab` | 3 kyu | Evaluate | Time series analysis |
331
- | `3-kyu-evaluate-owl-ontology` | 3 kyu | Evaluate | OWL ontology processor |
332
- | `2-kyu-evaluate-markdown-compiler` | 2 kyu | Evaluate | Markdown compiler |
342
+ | `2-kyu-create-markdown-compiler` | 2 kyu | Create | Markdown compiler |
333
343
  | `2-kyu-create-plot-code-lib` | 2 kyu | Create | Code visualization library |
334
344
  | `1-kyu-create-ray-tracer` | 1 kyu | Create | Ray tracer |
335
345
  | `1-dan-create-c64-emulator` | 1 dan | Create | C64 emulator |
336
- | `2-dan-create-agi` | 2 dan | Create | AGI vision |
346
+ | `1-dan-create-planning-engine` | 1 dan | Create | Planning engine with POP and belief revision |
347
+ | `2-dan-create-self-hosted` | 2 dan | Create | Self-hosting bootstrap tests |
337
348
 
338
349
  ### Running Local Benchmarks
339
350
 
package/agentic-lib.toml CHANGED
@@ -109,9 +109,9 @@ library-limit = 64 # max library entries in library/ directo
109
109
  [mission-complete]
110
110
  # Thresholds for deterministic mission-complete declaration.
111
111
  # All conditions must be met simultaneously.
112
- min-resolved-issues = 2 # minimum closed-as-RESOLVED issues since init
113
- min-dedicated-tests = 0 # minimum test files that import from src/lib/
112
+ min-resolved-issues = 1 # minimum closed-as-RESOLVED issues since init
114
113
  max-source-todos = 0 # max TODO comments allowed in ./src (0 = none)
114
+ # C6: Removed min-dedicated-tests (replaced by cumulative transforms and acceptance criteria)
115
115
 
116
116
  [bot]
117
117
  log-prefix = "tmp/agent-log-" #@dist "agent-log-"
@@ -1186,14 +1186,44 @@ function initPurgeGitHub() {
1186
1186
  ghExec(`gh api repos/${repoSlug}/git/refs/heads/agentic-lib-logs -X DELETE`);
1187
1187
  console.log(" DELETE: existing agentic-lib-logs branch");
1188
1188
  } catch { /* branch may not exist */ }
1189
- // Create orphan agentic-lib-logs branch with an empty commit via the API
1190
- // First get the empty tree SHA
1191
- const emptyTree = JSON.parse(ghExec(`gh api repos/${repoSlug}/git/trees -X POST -f "tree[0][path]=.gitkeep" -f "tree[0][mode]=100644" -f "tree[0][type]=blob" -f "tree[0][content]="`));
1189
+ // Create orphan agentic-lib-logs branch with initial state file
1190
+ // C1: Include agentic-lib-state.toml with default state
1191
+ const stateContent = [
1192
+ "# agentic-lib-state.toml — Persistent state across workflow runs",
1193
+ "# Written to the agentic-lib-logs branch by each agentic-step invocation",
1194
+ "",
1195
+ "[counters]",
1196
+ "log-sequence = 0",
1197
+ "cumulative-transforms = 0",
1198
+ "cumulative-maintain-features = 0",
1199
+ "cumulative-maintain-library = 0",
1200
+ "cumulative-nop-cycles = 0",
1201
+ "total-tokens = 0",
1202
+ "",
1203
+ "[budget]",
1204
+ "transformation-budget-used = 0",
1205
+ "transformation-budget-cap = 0",
1206
+ "",
1207
+ "[status]",
1208
+ 'mission-complete = false',
1209
+ 'mission-failed = false',
1210
+ 'mission-failed-reason = ""',
1211
+ 'last-transform-at = ""',
1212
+ 'last-non-nop-at = ""',
1213
+ "",
1214
+ "[schedule]",
1215
+ 'current = ""',
1216
+ "auto-disabled = false",
1217
+ 'auto-disabled-reason = ""',
1218
+ "",
1219
+ ].join("\n");
1220
+ const stateBlob = JSON.parse(ghExec(`gh api repos/${repoSlug}/git/blobs -X POST -f "content=${stateContent.replace(/"/g, '\\"')}" -f "encoding=utf-8"`));
1221
+ const emptyTree = JSON.parse(ghExec(`gh api repos/${repoSlug}/git/trees -X POST -f "tree[0][path]=.gitkeep" -f "tree[0][mode]=100644" -f "tree[0][type]=blob" -f "tree[0][content]=" -f "tree[1][path]=agentic-lib-state.toml" -f "tree[1][mode]=100644" -f "tree[1][type]=blob" -f "tree[1][sha]=${stateBlob.sha}"`));
1192
1222
  const commitData = JSON.parse(ghExec(
1193
1223
  `gh api repos/${repoSlug}/git/commits -X POST -f "message=init agentic-lib-logs branch" -f "tree=${emptyTree.sha}"`,
1194
1224
  ));
1195
1225
  ghExec(`gh api repos/${repoSlug}/git/refs -X POST -f "ref=refs/heads/agentic-lib-logs" -f "sha=${commitData.sha}"`);
1196
- console.log(" CREATE: agentic-lib-logs orphan branch");
1226
+ console.log(" CREATE: agentic-lib-logs orphan branch (with agentic-lib-state.toml)");
1197
1227
  initChanges++;
1198
1228
  } else {
1199
1229
  console.log(" CREATE: agentic-lib-logs orphan branch (dry run)");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@xn-intenton-z2a/agentic-lib",
3
- "version": "7.4.14",
3
+ "version": "7.4.16",
4
4
  "description": "Agentic-lib Agentic Coding Systems SDK powering automated GitHub workflows.",
5
5
  "type": "module",
6
6
  "scripts": {
@@ -18,6 +18,7 @@ import {
18
18
  checkInstabilityLabel, countDedicatedTests,
19
19
  countOpenIssues, countResolvedIssues, countMdFiles,
20
20
  } from "./metrics.js";
21
+ import { readState, writeState, updateStateAfterTask } from "../../copilot/state.js";
21
22
 
22
23
  // Task implementations
23
24
  import { resolveIssue } from "./tasks/resolve-issue.js";
@@ -92,6 +93,9 @@ async function run() {
92
93
  logFilePath, screenshotFilePath,
93
94
  };
94
95
 
96
+ // C1: Read persistent state from agentic-lib-state.toml
97
+ const state = readState(".");
98
+
95
99
  const startTime = Date.now();
96
100
  const result = await handler(context);
97
101
  const durationMs = Date.now() - startTime;
@@ -109,14 +113,18 @@ async function run() {
109
113
  && await checkInstabilityLabel(context, issueNumber);
110
114
  if (isInstability) core.info(`Issue #${issueNumber} has instability label — does not count against budget`);
111
115
  const transformationCost = computeTransformationCost(task, result.outcome, isInstability);
112
- const cumulativeCost = transformationCost;
113
116
 
114
- if (result.dedicatedTestCount == null || result.dedicatedTestCount === 0) {
115
- try {
116
- const { scanDirectory: scanDir } = await import("./copilot.js");
117
- result.dedicatedTestCount = countDedicatedTests(scanDir);
118
- } catch { /* ignore */ }
119
- }
117
+ // C1/C2: Update persistent state with this task's results
118
+ updateStateAfterTask(state, {
119
+ task,
120
+ outcome: result.outcome || "completed",
121
+ transformationCost,
122
+ tokensUsed: result.tokensUsed || 0,
123
+ durationMs,
124
+ });
125
+ // C2: Use cumulative cost from persistent state (not just this task)
126
+ const cumulativeCost = state.counters["cumulative-transforms"] || 0;
127
+ state.budget["transformation-budget-cap"] = config.transformationBudget || 0;
120
128
 
121
129
  const { featureIssueCount, maintenanceIssueCount } = await countOpenIssues(context);
122
130
  if (result.resolvedCount == null) result.resolvedCount = await countResolvedIssues(context);
@@ -133,22 +141,39 @@ async function run() {
133
141
  }
134
142
  }
135
143
 
136
- const missionMetrics = buildMissionMetrics(config, result, limitsStatus, cumulativeCost, featureIssueCount, maintenanceIssueCount);
144
+ // C5: Pass per-task costs for split display
145
+ const taskCosts = {
146
+ transformationCost,
147
+ tokensUsed: result.tokensUsed || 0,
148
+ cumulativeTokens: state.counters["total-tokens"] || 0,
149
+ durationMs,
150
+ cumulativeDurationMs: state.counters["total-duration-ms"] || 0,
151
+ };
152
+ const missionMetrics = buildMissionMetrics(config, result, limitsStatus, cumulativeCost, featureIssueCount, maintenanceIssueCount, taskCosts);
137
153
 
138
- // Write standalone agent log file (pushed to agentic-lib-logs branch by workflow)
154
+ // C4: Write standalone agent log file with sequence number
155
+ const seq = state.counters["log-sequence"] || 0;
139
156
  try {
140
157
  const agentLogFile = writeAgentLog({
141
158
  task, outcome: result.outcome || "completed",
142
159
  model: result.model || model, durationMs, tokensUsed: result.tokensUsed,
143
160
  narrative: result.narrative, contextNotes: result.contextNotes,
144
161
  reviewTable: result.reviewTable, completenessAdvice: result.completenessAdvice,
145
- missionMetrics,
162
+ missionMetrics, sequence: seq,
146
163
  });
147
164
  core.info(`Agent log written: ${agentLogFile}`);
148
165
  } catch (err) {
149
166
  core.warning(`Could not write agent log: ${err.message}`);
150
167
  }
151
168
 
169
+ // C1: Write updated state back to agentic-lib-state.toml
170
+ try {
171
+ writeState(".", state);
172
+ core.info(`State written: seq=${seq}, transforms=${cumulativeCost}, nops=${state.counters["cumulative-nop-cycles"]}`);
173
+ } catch (err) {
174
+ core.warning(`Could not write state: ${err.message}`);
175
+ }
176
+
152
177
  core.info(`agentic-step completed: outcome=${result.outcome}`);
153
178
  } catch (error) {
154
179
  core.setFailed(`agentic-step failed: ${error.message}`);
@@ -182,16 +182,19 @@ export function logActivity({
182
182
  export function writeAgentLog({
183
183
  task, outcome, model, durationMs, narrative,
184
184
  reviewTable, completenessAdvice, contextNotes,
185
- missionMetrics, tokensUsed,
185
+ missionMetrics, tokensUsed, sequence,
186
186
  }) {
187
187
  const now = new Date();
188
188
  const stamp = now.toISOString().replace(/:/g, "-").replace(/\./g, "-");
189
- const filename = `agent-log-${stamp}.md`;
189
+ // C4: Include zero-padded sequence number in filename
190
+ const seq = String(sequence || 0).padStart(3, "0");
191
+ const filename = `agent-log-${stamp}-${seq}.md`;
190
192
 
191
193
  const parts = [
192
194
  `# Agent Log: ${task} at ${now.toISOString()}`,
193
195
  "",
194
196
  "## Summary",
197
+ `**Sequence:** ${seq}`,
195
198
  `**Task:** ${task}`,
196
199
  `**Outcome:** ${outcome}`,
197
200
  ];