leerness 1.36.28 → 1.36.29
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/CHANGELOG.md +8 -0
- package/README.md +4 -4
- package/bin/leerness.js +6 -2
- package/lib/agents.js +6 -3
- package/lib/toggles.js +70 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,13 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 1.36.29 — 2026-07-15 — `agents multi` 위임 브리프 접두 — 백그라운드 AI 도 leerness 프로토콜을 받도록 (사용자 보고)
|
|
4
|
+
|
|
5
|
+
사용자 질문("백그라운드에서 호출된 AI 가 leerness 를 참조하는가?")에 대한 조사 결과: `agents dispatch` 는 1.35.6 부터 "[leerness 위임 프로토콜]" 브리프(handoff 적재→task 등록→evidence→verify-claim→session close)를 자동 접두하지만, **`agents multi`(--execute 실 spawn 포함)는 원문 그대로 위임** — 병렬 백그라운드 AI 들이 프로토콜을 받지 못하는 실제 갭이었다.
|
|
6
|
+
|
|
7
|
+
- **multi 3지점 브리프 접두**: `--execute` 실 spawn(`_cliChat`) + 명령 목록 출력 + `--json` commands. dispatch 와 동일 규칙(`--raw` 로 원문 위임). 로그/`_recordRun` 의 task 표시는 원문 유지(기록 정직성).
|
|
8
|
+
- 참조 경로 정리(조사 확정): ① dispatch/multi 프롬프트 접두(이번에 완성) ② AGENTS.md 자동 로드(codex 실측 준수 — cwd 가 루트가 아니거나 미지원 CLI 면 무력해서 접두가 안전망) ③ orchestrate 는 자체 JSON 계약 컨텍스트 포함.
|
|
9
|
+
- **검증**: selftest 299/299(브리프 4단계 + dispatch 와이어 + **multi 3지점 와이어**), 실측(multi 출력에 프로토콜 1회 포함 · `--raw` 0회), 게이트 e2e, 게시본 클린룸.
|
|
10
|
+
|
|
3
11
|
## 1.36.28 — 2026-07-15 — 미검토 표면 헌트: 데이터 유실 클래스(손상 스토어 클로버 · URL 덮어쓰기) + 정확성(impact 전이 · alias 경계)
|
|
4
12
|
|
|
5
13
|
rotate-review-targets 교훈 적용 — 최근 잘 검토된 표면(lens/memory/plan/requests/skill)을 **제외**하고 미검토 표면(state/team/api-skill/wakeup/intent/feature)을 codex 로 QA 헌트. 10 findings 중 결정적 5건을 맹신 X(전부 재현) 후, 데이터 유실 클래스 + 저위험 순수 교정 4건을 수정. 동시성 3건(크로스프로세스 락)은 0-deps rabbit-hole 위험이라 정직하게 이연.
|
package/README.md
CHANGED
|
@@ -121,7 +121,7 @@ MIT
|
|
|
121
121
|
<!-- leerness:project-readme:start -->
|
|
122
122
|
## Leerness Project Harness
|
|
123
123
|
|
|
124
|
-
이 프로젝트는 Leerness v1.36.
|
|
124
|
+
이 프로젝트는 Leerness v1.36.29 하네스를 사용합니다. AI 에이전트는 작업 전 `leerness handoff`로 컨텍스트를 적재하고, 작업 후 `leerness check`/`leerness audit`/`leerness session close`를 수행해야 합니다.
|
|
125
125
|
|
|
126
126
|
### 정체성 — AI 에이전트 운영 레이어 (UR-0030)
|
|
127
127
|
|
|
@@ -175,7 +175,7 @@ leerness memory restore decision <date|title>
|
|
|
175
175
|
|
|
176
176
|
### MCP server (외부 AI 통합)
|
|
177
177
|
|
|
178
|
-
Leerness v1.36.
|
|
178
|
+
Leerness v1.36.29는 stdio JSON-RPC MCP server를 내장합니다 — Claude Code · Cursor · Codex CLI 등 외부 AI에 **86개 도구**를 노출:
|
|
179
179
|
|
|
180
180
|
```jsonc
|
|
181
181
|
// 카테고리별
|
|
@@ -196,7 +196,7 @@ Leerness v1.36.28는 stdio JSON-RPC MCP server를 내장합니다 — Claude Cod
|
|
|
196
196
|
`<<autonomous-loop-dynamic>>` 신호만 보내면 AI가:
|
|
197
197
|
1) 다음 라운드 후보 선정 → 2) 코드 변경 → 3) stress-v* 신규 작성 + 누적 회귀 → 4) e2e 219/219 → 5) npm pack + git tag + GitHub release → 6) main 자동 push → 7) session close → 8) 다음 라운드 예약.
|
|
198
198
|
|
|
199
|
-
현재 누적: **70 라운드 (1.9.40 → 1.36.
|
|
199
|
+
현재 누적: **70 라운드 (1.9.40 → 1.36.29)** · 매 라운드 GitHub release/태그 생성 · _reports/는 비공개 보존.
|
|
200
200
|
|
|
201
201
|
### 성능 가이드
|
|
202
202
|
|
|
@@ -234,6 +234,6 @@ leerness release pack --close --auto-main-push
|
|
|
234
234
|
- `.harness/session-handoff.md`: 다음 세션 인수인계 (자동 작성)
|
|
235
235
|
- `.harness/lessons.md` / `decisions.md` / `rules.md`: 영구 메모리 (5 surface)
|
|
236
236
|
|
|
237
|
-
Last synced by Leerness v1.36.
|
|
237
|
+
Last synced by Leerness v1.36.29: 2026-07-15
|
|
238
238
|
<!-- leerness:project-readme:end -->
|
|
239
239
|
|
package/bin/leerness.js
CHANGED
|
@@ -34,7 +34,7 @@ const { CAPABILITY_SURFACE, POWERFUL_COMMANDS, ADAPTERS, REUSE_CATEGORIES, REUSE
|
|
|
34
34
|
const { tokenizeForRank: _tokenizeForRank, expandQuery: _expandQuery, scoreHits: _scoreHits, suggestTerms: _suggestTerms } = require('../lib/search-core'); // 1.36.23: memory search 랭킹 코어(순수·0-deps)
|
|
35
35
|
const { findCorruptedStateJson: _findCorruptedStateJson } = require('../lib/state-integrity'); // 1.36.1 (클린룸 리뷰 FN): .harness/*.json 상태 무결성 (audit/health/check 공유)
|
|
36
36
|
|
|
37
|
-
const VERSION = '1.36.
|
|
37
|
+
const VERSION = '1.36.29';
|
|
38
38
|
|
|
39
39
|
// 1.9.290 (UR-0037, Codex gpt-5.5 #4 수렴): CLI 전용 부작용은 require 시 실행하지 않는다.
|
|
40
40
|
// 이전: warning listener 제거 / NODE_OPTIONS 변경 / chcp IIFE 가 top-level 즉시 실행 → require('harness') 시 호스트 프로세스 오염.
|
|
@@ -2952,7 +2952,11 @@ function _selfTestCases() {
|
|
|
2952
2952
|
const wired = /has\('--raw'\)[\s\S]{0,120}_harnessBrief\(\) \+ task/.test(agentsSrc) && /_harnessBrief,/.test(read(__filename));
|
|
2953
2953
|
// (3) bench stdin hang 수정: codex exec 가 열린 stdin 파이프에서 EOF 대기(실측) → spawn stdio ignore.
|
|
2954
2954
|
const stdinFixed = agentsSrc.includes("{ shell: true, stdio: ['ignore', 'pipe', 'pipe'] }");
|
|
2955
|
-
|
|
2955
|
+
// (4) 1.36.29 (사용자 보고): multi 도 브리프 접두 — --execute 실 spawn(_cliChat) + 명령 목록/JSON 3지점 전부 briefTask.
|
|
2956
|
+
const multiWired = agentsSrc.includes('_cliChat(root, def.id, briefTask,')
|
|
2957
|
+
&& agentsSrc.includes('_dispatchCommand(x.def.id, briefTask, writeMode)')
|
|
2958
|
+
&& agentsSrc.includes('_dispatchCommand(def.id, briefTask, writeMode)');
|
|
2959
|
+
return briefOk && wired && stdinFixed && multiWired;
|
|
2956
2960
|
} },
|
|
2957
2961
|
{ name: '19th GPT5.5평가 (UR-0013): _parseTestStdout 러너 인식(jest/tap/spec/비율) + declared-pass 부풀림 3경로 게이팅 + json ok/reasons (1.35.7)', run: () => {
|
|
2958
2962
|
// (1) 파서 행위: 기존 4형식 보존 + spec 리포터(패턴 6) 신규 — denom = pass + fail.
|
package/lib/agents.js
CHANGED
|
@@ -74,6 +74,9 @@ function agentsCmd(root, sub, args = [], deps = {}) {
|
|
|
74
74
|
if (sub === 'multi') {
|
|
75
75
|
const task = _taskArg();
|
|
76
76
|
if (!task) { fail('multi "<task>" 또는 --task 필요'); return process.exit(1); }
|
|
77
|
+
// 1.36.29 (사용자 보고): dispatch 만 위임 브리프를 접두하고 multi(--execute 실 spawn 포함)는 원문 그대로 위임돼
|
|
78
|
+
// 백그라운드 AI 가 leerness 프로토콜(handoff 적재/task 등록/evidence/session close)을 받지 못했다. dispatch 와 동일 규칙: --raw 로 옵트아웃.
|
|
79
|
+
const briefTask = (has('--raw') || typeof _harnessBrief !== 'function') ? task : (_harnessBrief() + task);
|
|
77
80
|
const onlyArg = arg('--only', null); // 'claude,codex' 처럼 콤마 구분 — 활성 중에서 추가 필터
|
|
78
81
|
const writeMode = has('--write');
|
|
79
82
|
const execute = has('--execute'); // 1.9.156: 명령 출력 → 실제 spawn + consensus 합의
|
|
@@ -109,7 +112,7 @@ function agentsCmd(root, sub, args = [], deps = {}) {
|
|
|
109
112
|
// 병렬 _cliChat 호출 (sandbox 자동: runCommandSafe + env scrub + observability)
|
|
110
113
|
const results = await Promise.all(ready.map(async ({ def }) => {
|
|
111
114
|
const start = Date.now();
|
|
112
|
-
const r = await _cliChat(root, def.id,
|
|
115
|
+
const r = await _cliChat(root, def.id, briefTask, { timeout });
|
|
113
116
|
return {
|
|
114
117
|
agent: def.id,
|
|
115
118
|
elapsed: Date.now() - start,
|
|
@@ -203,7 +206,7 @@ function agentsCmd(root, sub, args = [], deps = {}) {
|
|
|
203
206
|
log(JSON.stringify({
|
|
204
207
|
task, count: ready.length,
|
|
205
208
|
agents: ready.map(x => ({ id: x.def.id, version: x.status.version })),
|
|
206
|
-
commands: ready.map(x => _dispatchCommand(x.def.id,
|
|
209
|
+
commands: ready.map(x => _dispatchCommand(x.def.id, briefTask, writeMode)),
|
|
207
210
|
// 1.9.266 (UR-0021 2단계): 각 에이전트 슬래시 명령 힌트 — sub-agent 가 알맞은 슬래시 사용
|
|
208
211
|
slashCommands: ready.reduce((acc, x) => { const h = _agentSlashHint(root, x.def.id); if (h) acc[x.def.id] = { invoke: h.invoke, commands: h.commands.map(c => c.cmd) }; return acc; }, {})
|
|
209
212
|
}, null, 2));
|
|
@@ -219,7 +222,7 @@ function agentsCmd(root, sub, args = [], deps = {}) {
|
|
|
219
222
|
for (const { def, status } of ready) {
|
|
220
223
|
log(`### [${def.id}] (v${status.version || '?'})`);
|
|
221
224
|
log('```sh');
|
|
222
|
-
log(_dispatchCommand(def.id,
|
|
225
|
+
log(_dispatchCommand(def.id, briefTask, writeMode));
|
|
223
226
|
log('```');
|
|
224
227
|
// 1.9.266 (UR-0021 2단계): 에이전트별 슬래시 명령 힌트
|
|
225
228
|
try {
|
package/lib/toggles.js
ADDED
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
// lib/toggles.js — 기능 토글 (1.36.30, 사용자 요청): 온톨로지 그래프 뷰의 스위치와 연동되는 기능 on/off 스토어.
|
|
2
|
+
// .harness/toggles.json 에 저장. AI/CLI 는 여기 상태를 읽어 준수한다(gate/lens 스킵, 위임 브리프 생략, 자동 그래프).
|
|
3
|
+
// 설계: 기본 전부 ON(파일 없으면 결손 아님). 손상 파일은 SAVE 시 덮어쓰기 거부(1.36.28 _assertStoreParsable 패턴).
|
|
4
|
+
'use strict';
|
|
5
|
+
const path = require('path');
|
|
6
|
+
const { absRoot, exists, read, writeUtf8, mkdirp, log, ok, fail } = require('./io');
|
|
7
|
+
|
|
8
|
+
// 토글 레지스트리 — id: { ko 설명, 영향 명령 }. 새 토글은 여기에 추가.
|
|
9
|
+
const TOGGLE_REGISTRY = {
|
|
10
|
+
'gate': { desc: '완료 게이트 (verify+audit+scan+encoding+lazy 통합 점검)', affects: 'leerness gate' },
|
|
11
|
+
'lens': { desc: '품질 렌즈 자기질문 (완료 선언 전 분야별 점검)', affects: 'leerness lens' },
|
|
12
|
+
'auto-graph': { desc: '온톨로지 그래프(leerness.html) 자동 갱신 (install/session-close)', affects: 'install · session close' },
|
|
13
|
+
'delegation-brief': { desc: '백그라운드 AI 위임 시 leerness 프로토콜 브리프 자동 접두', affects: 'agents dispatch · agents multi' },
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
function _togglesPath(root) { return path.join(absRoot(root), '.harness', 'toggles.json'); }
|
|
17
|
+
|
|
18
|
+
// 전체 토글 상태 로드 — 파일 없으면 전부 기본 ON. 손상 파일은 읽기에선 기본값(비변경 경로 resilient).
|
|
19
|
+
function loadToggles(root) {
|
|
20
|
+
const out = {};
|
|
21
|
+
for (const id of Object.keys(TOGGLE_REGISTRY)) out[id] = true;
|
|
22
|
+
const f = _togglesPath(root);
|
|
23
|
+
if (!exists(f)) return out;
|
|
24
|
+
try {
|
|
25
|
+
const j = JSON.parse(read(f));
|
|
26
|
+
for (const [k, v] of Object.entries(j || {})) if (k in out) out[k] = v !== false;
|
|
27
|
+
} catch {}
|
|
28
|
+
return out;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
// 단일 토글 조회 헬퍼 — 호출부 한 줄용.
|
|
32
|
+
function toggleOn(root, id) { return loadToggles(root)[id] !== false; }
|
|
33
|
+
|
|
34
|
+
function saveToggles(root, toggles) {
|
|
35
|
+
const f = _togglesPath(root);
|
|
36
|
+
// 1.36.28 패턴: 손상 파일 덮어쓰기 거부 — 단 토글은 전량 기본값 복원 가능하니 손상 시 재생성 허용이 사용자 친화적.
|
|
37
|
+
// (여기의 데이터는 bool 4개뿐 — 유실 비용이 0 에 가깝고, 거부하면 토글 자체가 잠긴다. 의도적 예외.)
|
|
38
|
+
mkdirp(path.dirname(f));
|
|
39
|
+
writeUtf8(f, JSON.stringify(toggles, null, 2) + '\n');
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
// `leerness toggle [list|set <id> on|off] [--json]`
|
|
43
|
+
function toggleCmd(root, sub, id, val, deps = {}) {
|
|
44
|
+
const { has, VERSION } = deps;
|
|
45
|
+
root = absRoot(root);
|
|
46
|
+
const json = has && has('--json');
|
|
47
|
+
const cur = loadToggles(root);
|
|
48
|
+
if (!sub || sub === 'list') {
|
|
49
|
+
if (json) { log(JSON.stringify({ version: VERSION, toggles: cur, registry: TOGGLE_REGISTRY }, null, 2)); return; }
|
|
50
|
+
log(`# leerness toggle — 기능 토글 (온톨로지 그래프 뷰 ⚙ 탭과 연동)`);
|
|
51
|
+
for (const [k, meta] of Object.entries(TOGGLE_REGISTRY)) {
|
|
52
|
+
log(` ${cur[k] ? '🟢 ON ' : '⚪ OFF'} ${k.padEnd(17)} ${meta.desc} [${meta.affects}]`);
|
|
53
|
+
}
|
|
54
|
+
log(`\n 변경: leerness toggle set <id> on|off · 그래프 뷰: leerness graph --html → leerness.html 의 ⚙ 탭`);
|
|
55
|
+
return;
|
|
56
|
+
}
|
|
57
|
+
if (sub === 'set') {
|
|
58
|
+
if (!TOGGLE_REGISTRY[id]) { fail(`알 수 없는 토글: ${id} (가능: ${Object.keys(TOGGLE_REGISTRY).join(', ')})`); process.exitCode = 1; return; }
|
|
59
|
+
const on = String(val).toLowerCase();
|
|
60
|
+
if (on !== 'on' && on !== 'off') { fail(`값은 on|off (받음: ${val})`); process.exitCode = 1; return; }
|
|
61
|
+
cur[id] = on === 'on';
|
|
62
|
+
saveToggles(root, cur);
|
|
63
|
+
if (json) { log(JSON.stringify({ ok: true, id, value: cur[id], toggles: cur }, null, 2)); return; }
|
|
64
|
+
ok(`toggle ${id} = ${on.toUpperCase()}${cur[id] ? '' : ' — 관련 명령이 스킵 동작으로 전환됩니다'}`);
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
fail(`알 수 없는 하위명령: ${sub} (가능: list, set)`); process.exitCode = 1;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
module.exports = { TOGGLE_REGISTRY, loadToggles, toggleOn, saveToggles, toggleCmd, _togglesPath };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "leerness",
|
|
3
|
-
"version": "1.36.
|
|
3
|
+
"version": "1.36.29",
|
|
4
4
|
"description": "The AI-coding operations layer that makes \"done\" require evidence — persistent memory, evidence-gated completion checks, and clean handoffs for any AI agent (Claude Code, Codex, Cursor). State lives as plain files in your repo. CLI + MCP, 0 runtime dependencies.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"leerness",
|