leerness 1.9.208 β 1.9.209
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 +45 -0
- package/README.md +3 -3
- package/bin/harness.js +270 -2
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,50 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 1.9.209 β 2026-05-22
|
|
4
|
+
|
|
5
|
+
**π pre-wake sub-agent audit + κΉ¨μ΄λ¨ μ§ν μλ λ
ΈμΆ (μ¬μ©μ λͺ
μ).**
|
|
6
|
+
|
|
7
|
+
### μ¬μ©μ λͺ
μ
|
|
8
|
+
> *"λ©μΈ μμ΄μ νΈκ° μ¬λ¦½μ μ μλΈμμ΄μ νΈλ₯Ό νΈμΆν΄μ λ―ΈλΉλ λΆλΆμ΄ μλμ§, μΆ©λλλ λΆλΆμ΄ μλμ§, μ΄μ μ λλ½λ μμ
μ΄ μλμ§ λ±λ± μ¬λ¬λΆλΆμ νμνλ©΄μ νμν λ΄μ©μ μ 리νκ³ λ©μΈ μμ΄μ νΈκ° κΉ¨μ΄λ¬μλ, μλΈμμ΄μ νΈκ° μ 리ν λ΄μ©μ νμΈν΄λ³΄κ±°λ νλ κΈ°λ₯"*
|
|
9
|
+
|
|
10
|
+
### 1. `.harness/pre-wake-report.json` β sleep μ audit λμ
|
|
11
|
+
- `_preWakeReportPath/_loadPreWakeReport/_writePreWakeReport` νμΌ I/O ν¬νΌ
|
|
12
|
+
- μ΅κ·Ό 10κ°λ§ μ μ§ (rotate)
|
|
13
|
+
- ꡬ쑰: `{ auditedAt, auditVersion, findings: {critical/warning/info}, summary }`
|
|
14
|
+
|
|
15
|
+
### 2. `_runPreWakeAudit(root)` β sub-agent audit 6μμ
|
|
16
|
+
- **missing-user-requests** (1.9.207 ν΅ν©) β task-log/plan/decisions λ§€μΉ μ λ μμ²
|
|
17
|
+
- **stale-user-requests** β 7μΌ+ open μμ²
|
|
18
|
+
- **stale-in-progress** β 24h+ μ§μ² μλ task
|
|
19
|
+
- **drift-handoff-stale** β session-handoff.md 5μΌ+ stale
|
|
20
|
+
- **wakeup-missed** β wakeup miss κ°μ§ (1.9.205)
|
|
21
|
+
- **next-action-pending** β next-action queue λκΈ°
|
|
22
|
+
- **auto-resume-plan-ready/stale** β 1.9.203 plan μν
|
|
23
|
+
|
|
24
|
+
### 3. `leerness pre-wake-audit` CLI
|
|
25
|
+
- κΈ°λ³Έ: μ audit μ€ν + μ μ₯
|
|
26
|
+
- `--last` / `show` / `review` β κ°μ₯ μ΅κ·Ό μ μ₯λ audit νμ
|
|
27
|
+
- `--json` β JSON μΆλ ₯
|
|
28
|
+
|
|
29
|
+
### 4. handoff μλ λ
ΈμΆ (μ¬μ©μ λͺ
μ "κΉ¨μ΄λ¬μλ νμΈ")
|
|
30
|
+
- ν€λλΌμΈ 14λ²μ§Έ μμ: `π pre-wake NC/MW (ageMin)` β critical N건 + warning M건
|
|
31
|
+
- λ³Έλ¬Έ μλ μΉμ
: `## π μ§μ sleep pre-wake-audit (1.9.209, NλΆ μ )`
|
|
32
|
+
Β· critical/warning μ΅λ 3κ°μ© λ
ΈμΆ
|
|
33
|
+
Β· 4μκ° μ΄λ΄ λ³΄κ³ μλ§ (stale μλ hide)
|
|
34
|
+
- ν€λλΌμΈ λΌλ²¨: `1.9.81/93/113/152/162/192/197/204/207/209`
|
|
35
|
+
|
|
36
|
+
### 5. λμ νκ· (1.9.200~208) β λͺ¨λ μ μ§
|
|
37
|
+
|
|
38
|
+
### 6. stress-v154 β 18/18 PASS
|
|
39
|
+
- 1.9.209 (9) + μ±λ₯ (2) + λμ νκ· (7)
|
|
40
|
+
- 격리 tmp dir λΌμ΄νμ¬μ΄ν΄ κ²μ¦ (μ€ν β μ μ₯ β --last β rotate to 10)
|
|
41
|
+
- 6 findings kind ν€μλ κ²μ¦
|
|
42
|
+
- μ±λ₯: --version cold start avg 517ms Β· MCP 54 λꡬ 574ms
|
|
43
|
+
|
|
44
|
+
### 7. μλ release (71 λΌμ΄λ main-push streak Β· 32 λΌμ΄λ npm publish streak)
|
|
45
|
+
|
|
46
|
+
---
|
|
47
|
+
|
|
3
48
|
## 1.9.208 β 2026-05-22
|
|
4
49
|
|
|
5
50
|
**π¦ νλ«νΌ/API μ μ½ μ¬μ μ²΄ν¬ (μ¬μ©μ λͺ
μ).**
|
package/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
> **AI μ½λ© μμ΄μ νΈμ κ±°μ§ μλ£Β·μ€λ³΅Β·λ§κ°Β·μΆ©λμ λ§μμ£Όλ κ²μΒ·κΈ°μ΅Β·νμ
CLI νλ€μ€.**
|
|
4
4
|
|
|
5
|
-
[](https://www.npmjs.com/package/leerness) [](https://www.npmjs.com/package/leerness) []() []() []() []() []() []() [-brightgreen)]() []() []() []() []() []()
|
|
6
6
|
|
|
7
7
|
```
|
|
8
8
|
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
@@ -12,9 +12,9 @@
|
|
|
12
12
|
β βββ ββββββ ββββββ ββββββββββββββββββββββββ ββββββββ β
|
|
13
13
|
β βββββββββββββββββββββββββββ ββββββ ββββββββββββββββββββββ β
|
|
14
14
|
β βββββββββββββββββββββββββββ ββββββ βββββββββββββββββββββ β
|
|
15
|
-
β v1.9.
|
|
15
|
+
β v1.9.209 AI Agent Reliability Harness + Sandbox β
|
|
16
16
|
β verify Β· remember Β· orchestrate Β· audit Β· sandbox Β· drift β
|
|
17
|
-
β
|
|
17
|
+
β π pre-wake sub-agent audit (sleep μ μ κ²) (μ¬μ©μ λͺ
μ) β
|
|
18
18
|
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
19
19
|
```
|
|
20
20
|
|
package/bin/harness.js
CHANGED
|
@@ -7,7 +7,7 @@ const cp = require('child_process');
|
|
|
7
7
|
const os = require('os'); // 1.9.178: _publishToNpm μμ os.tmpdir() μ¬μ© (μ μ import)
|
|
8
8
|
const readline = require('readline');
|
|
9
9
|
|
|
10
|
-
const VERSION = '1.9.
|
|
10
|
+
const VERSION = '1.9.209';
|
|
11
11
|
|
|
12
12
|
// 1.9.184: DEP0190 (child_process shell: true) deprecation warning μ΅μ (μ¬μ©μ λͺ
μ).
|
|
13
13
|
// leerness λ cross-platform PATH resolution μ μν΄ shell: true λ₯Ό μλμ μΌλ‘ μ¬μ© (claude.cmd / ollama.cmd λ± Windows .cmd μ²λ¦¬).
|
|
@@ -2111,6 +2111,146 @@ function _checkRequestConstraints(root, text) {
|
|
|
2111
2111
|
return { matched, suggestions, totalPlatforms: Object.keys(catalog.platforms).length };
|
|
2112
2112
|
}
|
|
2113
2113
|
|
|
2114
|
+
// 1.9.209: pre-wake sub-agent audit (μ¬μ©μ λͺ
μ)
|
|
2115
|
+
// "λ©μΈ μμ΄μ νΈκ° μ¬λ¦½μ μ μλΈμμ΄μ νΈλ₯Ό νΈμΆν΄μ λ―ΈλΉλ λΆλΆμ΄ μλμ§, μΆ©λλλ λΆλΆμ΄ μλμ§,
|
|
2116
|
+
// μ΄μ μ λλ½λ μμ
μ΄ μλμ§ λ±λ± μ¬λ¬λΆλΆμ νμνλ©΄μ νμν λ΄μ©μ μ 리νκ³
|
|
2117
|
+
// λ©μΈ μμ΄μ νΈκ° κΉ¨μ΄λ¬μλ, μλΈμμ΄μ νΈκ° μ 리ν λ΄μ©μ νμΈν΄λ³΄κ±°λ νλ κΈ°λ₯"
|
|
2118
|
+
// .harness/pre-wake-report.json μ sleep μ audit κ²°κ³Ό λμ (μ΅κ·Ό 10κ° μ μ§) β
|
|
2119
|
+
// λ€μ handoff μμ μλ λ
ΈμΆ β κΉ¨μ΄λ¨ μ§ν λ©μΈ μμ΄μ νΈκ° κ²ν κ°λ₯
|
|
2120
|
+
// audit μμ: λ―Έλ΅ μμ² / 24h+ 무μ§μ² task / drift μ νΈ / feature_graph μΆ©λ / νλ«νΌ μ μ½ λλ½
|
|
2121
|
+
function _preWakeReportPath(root) { return path.join(root, '.harness', 'pre-wake-report.json'); }
|
|
2122
|
+
function _loadPreWakeReport(root) {
|
|
2123
|
+
try {
|
|
2124
|
+
const fp = _preWakeReportPath(root);
|
|
2125
|
+
if (!exists(fp)) return { reports: [] };
|
|
2126
|
+
const j = JSON.parse(read(fp));
|
|
2127
|
+
return { reports: Array.isArray(j.reports) ? j.reports : [] };
|
|
2128
|
+
} catch { return { reports: [] }; }
|
|
2129
|
+
}
|
|
2130
|
+
function _writePreWakeReport(root, reports) {
|
|
2131
|
+
try {
|
|
2132
|
+
mkdirp(path.join(root, '.harness'));
|
|
2133
|
+
writeUtf8(_preWakeReportPath(root), JSON.stringify({ reports, updatedAt: new Date().toISOString() }, null, 2));
|
|
2134
|
+
return true;
|
|
2135
|
+
} catch { return false; }
|
|
2136
|
+
}
|
|
2137
|
+
// μ€μ audit μ€ν β sub-agent μν (λ¨μΌ νλ‘μΈμ€μμ syncλ‘ λ€μν μ νΈ μμ§)
|
|
2138
|
+
function _runPreWakeAudit(root) {
|
|
2139
|
+
const audit = {
|
|
2140
|
+
auditedAt: new Date().toISOString(),
|
|
2141
|
+
auditVersion: VERSION,
|
|
2142
|
+
findings: { critical: [], warning: [], info: [] }
|
|
2143
|
+
};
|
|
2144
|
+
// 1) λ―Έλ΅ μ¬μ©μ μμ² (1.9.207)
|
|
2145
|
+
try {
|
|
2146
|
+
const reqAudit = _auditUserRequests(root);
|
|
2147
|
+
if (reqAudit.missing && reqAudit.missing.length > 0) {
|
|
2148
|
+
audit.findings.critical.push({
|
|
2149
|
+
kind: 'missing-user-requests',
|
|
2150
|
+
count: reqAudit.missing.length,
|
|
2151
|
+
detail: `${reqAudit.missing.length}건 μ¬μ©μ μμ²μ΄ task-log/plan/decisions μ λ§€μΉ μ λ¨`,
|
|
2152
|
+
items: reqAudit.missing.slice(0, 5).map(r => ({ id: r.id, text: r.text.slice(0, 80) }))
|
|
2153
|
+
});
|
|
2154
|
+
}
|
|
2155
|
+
if (reqAudit.stale && reqAudit.stale.length > 0) {
|
|
2156
|
+
audit.findings.warning.push({
|
|
2157
|
+
kind: 'stale-user-requests',
|
|
2158
|
+
count: reqAudit.stale.length,
|
|
2159
|
+
detail: `${reqAudit.stale.length}건 μ¬μ©μ μμ²μ΄ 7μΌ+ open μν`
|
|
2160
|
+
});
|
|
2161
|
+
}
|
|
2162
|
+
} catch (e) { audit.findings.info.push({ kind: 'audit-error', area: 'user-requests', error: String(e.message || e) }); }
|
|
2163
|
+
|
|
2164
|
+
// 2) 24h+ 무μ§μ² task β progress-tracker κ²μ¬
|
|
2165
|
+
try {
|
|
2166
|
+
const ptPath = path.join(root, '.harness', 'progress-tracker.md');
|
|
2167
|
+
if (exists(ptPath)) {
|
|
2168
|
+
const content = read(ptPath);
|
|
2169
|
+
const stat = fs.statSync(ptPath);
|
|
2170
|
+
const ageMin = Math.floor((Date.now() - stat.mtimeMs) / 60000);
|
|
2171
|
+
// in-progress νκ·Έκ° μλλ° 24h+ κ°±μ μμ
|
|
2172
|
+
const inProgressCount = (content.match(/status:\s*in-progress/gi) || []).length;
|
|
2173
|
+
if (inProgressCount > 0 && ageMin > 24 * 60) {
|
|
2174
|
+
audit.findings.warning.push({
|
|
2175
|
+
kind: 'stale-in-progress',
|
|
2176
|
+
count: inProgressCount,
|
|
2177
|
+
detail: `${inProgressCount}건 in-progress task, ${Math.floor(ageMin/60)}h κ°±μ μμ`,
|
|
2178
|
+
ageMin
|
|
2179
|
+
});
|
|
2180
|
+
}
|
|
2181
|
+
}
|
|
2182
|
+
} catch {}
|
|
2183
|
+
|
|
2184
|
+
// 3) drift μ νΈ β session-handoff/progress-tracker stale κ²μ¬
|
|
2185
|
+
try {
|
|
2186
|
+
const handoffPath = path.join(root, '.harness', 'session-handoff.md');
|
|
2187
|
+
if (exists(handoffPath)) {
|
|
2188
|
+
const stat = fs.statSync(handoffPath);
|
|
2189
|
+
const ageDay = (Date.now() - stat.mtimeMs) / 86400000;
|
|
2190
|
+
if (ageDay > 5) {
|
|
2191
|
+
audit.findings.warning.push({
|
|
2192
|
+
kind: 'drift-handoff-stale',
|
|
2193
|
+
ageDay: Math.round(ageDay * 10) / 10,
|
|
2194
|
+
detail: `session-handoff.md ${ageDay.toFixed(1)}μΌ stale β drift μν`
|
|
2195
|
+
});
|
|
2196
|
+
}
|
|
2197
|
+
}
|
|
2198
|
+
} catch {}
|
|
2199
|
+
|
|
2200
|
+
// 4) λ€μ λΌμ΄λ plan μ μ© κ°λ₯ μ¬λΆ (1.9.203)
|
|
2201
|
+
try {
|
|
2202
|
+
const plan = _loadAutoResumePlan(root);
|
|
2203
|
+
if (!plan) {
|
|
2204
|
+
audit.findings.info.push({ kind: 'no-auto-resume-plan', detail: 'auto-resume-plan.json μμ β λ€μ λΌμ΄λ μ§μ
μ manual context' });
|
|
2205
|
+
} else if (plan.ageMin > 12 * 60) {
|
|
2206
|
+
audit.findings.warning.push({ kind: 'auto-resume-plan-stale', detail: `plan ${plan.ageMin}λΆ μ μμ± β outdated κ°λ₯` });
|
|
2207
|
+
} else {
|
|
2208
|
+
audit.findings.info.push({ kind: 'auto-resume-plan-ready', detail: `nextRoundVersion=${plan.nextRoundVersion}, focus=${(plan.focus||'').slice(0,50)}` });
|
|
2209
|
+
}
|
|
2210
|
+
} catch {}
|
|
2211
|
+
|
|
2212
|
+
// 5) Active wakeup μν (1.9.205)
|
|
2213
|
+
try {
|
|
2214
|
+
const wkStat = _analyzeWakeupStatus(root);
|
|
2215
|
+
if (wkStat.hasWakeup && wkStat.kind === 'missed') {
|
|
2216
|
+
audit.findings.critical.push({
|
|
2217
|
+
kind: 'wakeup-missed',
|
|
2218
|
+
deltaMin: wkStat.deltaMin,
|
|
2219
|
+
detail: `wakeup ${wkStat.deltaMin}λΆ μ§λ¨ β λ€μ λΌμ΄λ μ§μ
λ¦μ`
|
|
2220
|
+
});
|
|
2221
|
+
}
|
|
2222
|
+
} catch {}
|
|
2223
|
+
|
|
2224
|
+
// 6) next-action queue μμ¬ (1.9.201)
|
|
2225
|
+
try {
|
|
2226
|
+
const q = _loadNextActionQueue(root);
|
|
2227
|
+
if (q && q.pending && q.pending.length > 0) {
|
|
2228
|
+
audit.findings.info.push({
|
|
2229
|
+
kind: 'next-action-pending',
|
|
2230
|
+
count: q.pending.length,
|
|
2231
|
+
detail: `${q.pending.length}건 next-action λκΈ° β leerness next-action take λ‘ μ¦μ μ²λ¦¬`
|
|
2232
|
+
});
|
|
2233
|
+
}
|
|
2234
|
+
} catch {}
|
|
2235
|
+
|
|
2236
|
+
// 7) ν΅ν© μμ½
|
|
2237
|
+
audit.summary = {
|
|
2238
|
+
criticalCount: audit.findings.critical.length,
|
|
2239
|
+
warningCount: audit.findings.warning.length,
|
|
2240
|
+
infoCount: audit.findings.info.length,
|
|
2241
|
+
needsAttention: audit.findings.critical.length > 0 || audit.findings.warning.length >= 2
|
|
2242
|
+
};
|
|
2243
|
+
return audit;
|
|
2244
|
+
}
|
|
2245
|
+
function _saveAndAppendPreWakeReport(root, audit) {
|
|
2246
|
+
const state = _loadPreWakeReport(root);
|
|
2247
|
+
state.reports.push(audit);
|
|
2248
|
+
// μ΅κ·Ό 10κ°λ§ μ μ§
|
|
2249
|
+
if (state.reports.length > 10) state.reports = state.reports.slice(-10);
|
|
2250
|
+
_writePreWakeReport(root, state.reports);
|
|
2251
|
+
return audit;
|
|
2252
|
+
}
|
|
2253
|
+
|
|
2114
2254
|
// 1.9.203: μλ λΌμ΄λ plan μ 리 β μ¬μ©μ λͺ
μ
|
|
2115
2255
|
// "λ°±κ·ΈλΌμ΄λμ λ€μ μμ
μ΄ μμκ°λ₯ν μμ μκ° + μΌμ΄λ¬μλ ν΄μΌνλ μΌμ μ 리"
|
|
2116
2256
|
// λΌμ΄λ λ§λ¬΄λ¦¬ μ .harness/auto-resume-plan.json μλ μ μ₯ β λ€μ wakeup μ μ¦μ μ€ν κ°λ₯
|
|
@@ -2434,6 +2574,93 @@ function constraintsCmd(root, sub, ...rest) {
|
|
|
2434
2574
|
process.exit(1);
|
|
2435
2575
|
}
|
|
2436
2576
|
|
|
2577
|
+
// 1.9.209: leerness pre-wake-audit β sleep μ sub-agent audit CLI (μ¬μ©μ λͺ
μ)
|
|
2578
|
+
// "λ©μΈ μμ΄μ νΈκ° μ¬λ¦½μ μ μλΈμμ΄μ νΈλ₯Ό νΈμΆν΄μ λ―ΈλΉλ λΆλΆμ΄ μλμ§, μΆ©λλλ λΆλΆμ΄ μλμ§,
|
|
2579
|
+
// μ΄μ μ λλ½λ μμ
μ΄ μλμ§ λ±λ± μ¬λ¬λΆλΆμ νμνλ©΄μ νμν λ΄μ©μ μ 리"
|
|
2580
|
+
// κΈ°λ³Έ: μ audit μ€ν + μ μ₯ + μΆλ ₯
|
|
2581
|
+
// --last: μ΅κ·Ό μ μ₯λ audit νμ (μ¬μ©μ κΉ¨μ΄λ¬μ λ κ²ν μ©)
|
|
2582
|
+
// --json: JSON μΆλ ₯
|
|
2583
|
+
function preWakeAuditCmd(root, sub) {
|
|
2584
|
+
root = absRoot(root);
|
|
2585
|
+
const isTty = process.stdout && process.stdout.isTTY;
|
|
2586
|
+
const cyan = s => isTty ? `\x1b[36m${s}\x1b[0m` : s;
|
|
2587
|
+
const grn = s => isTty ? `\x1b[32m${s}\x1b[0m` : s;
|
|
2588
|
+
const yel = s => isTty ? `\x1b[33m${s}\x1b[0m` : s;
|
|
2589
|
+
const red = s => isTty ? `\x1b[31m${s}\x1b[0m` : s;
|
|
2590
|
+
const dim = s => isTty ? `\x1b[2m${s}\x1b[0m` : s;
|
|
2591
|
+
|
|
2592
|
+
// --last λλ review/show β κ°μ₯ μ΅κ·Ό audit νμ (μ€ν μ ν¨)
|
|
2593
|
+
if (has('--last') || sub === 'show' || sub === 'review') {
|
|
2594
|
+
const state = _loadPreWakeReport(root);
|
|
2595
|
+
if (state.reports.length === 0) {
|
|
2596
|
+
log(cyan(`# leerness pre-wake-audit (1.9.209) β review`));
|
|
2597
|
+
log(dim(` (μ μ₯λ audit μμ β leerness pre-wake-audit μΌλ‘ μ μ€ν)`));
|
|
2598
|
+
return;
|
|
2599
|
+
}
|
|
2600
|
+
const latest = state.reports[state.reports.length - 1];
|
|
2601
|
+
if (has('--json')) { log(JSON.stringify(latest, null, 2)); return; }
|
|
2602
|
+
log(cyan(`# leerness pre-wake-audit (1.9.209) β review (latest)`));
|
|
2603
|
+
log(dim(` audited at: ${latest.auditedAt} (version ${latest.auditVersion})`));
|
|
2604
|
+
log('');
|
|
2605
|
+
const sum = latest.summary || {};
|
|
2606
|
+
log(` π ${red(`critical ${sum.criticalCount || 0}`)} Β· ${yel(`warning ${sum.warningCount || 0}`)} Β· info ${sum.infoCount || 0}`);
|
|
2607
|
+
if (sum.needsAttention) log(yel(` β needsAttention=true β λ©μΈ μμ΄μ νΈ κ²ν νμ`));
|
|
2608
|
+
log('');
|
|
2609
|
+
if (latest.findings.critical && latest.findings.critical.length) {
|
|
2610
|
+
log(red(`## π¨ critical (${latest.findings.critical.length})`));
|
|
2611
|
+
latest.findings.critical.forEach(f => log(` - [${f.kind}] ${f.detail}`));
|
|
2612
|
+
log('');
|
|
2613
|
+
}
|
|
2614
|
+
if (latest.findings.warning && latest.findings.warning.length) {
|
|
2615
|
+
log(yel(`## β warning (${latest.findings.warning.length})`));
|
|
2616
|
+
latest.findings.warning.forEach(f => log(` - [${f.kind}] ${f.detail}`));
|
|
2617
|
+
log('');
|
|
2618
|
+
}
|
|
2619
|
+
if (latest.findings.info && latest.findings.info.length) {
|
|
2620
|
+
log(dim(`## βΉ info (${latest.findings.info.length})`));
|
|
2621
|
+
latest.findings.info.forEach(f => log(dim(` - [${f.kind}] ${f.detail}`)));
|
|
2622
|
+
}
|
|
2623
|
+
return;
|
|
2624
|
+
}
|
|
2625
|
+
|
|
2626
|
+
// κΈ°λ³Έ: μ audit μ€ν + μ μ₯
|
|
2627
|
+
const audit = _runPreWakeAudit(root);
|
|
2628
|
+
_saveAndAppendPreWakeReport(root, audit);
|
|
2629
|
+
|
|
2630
|
+
if (has('--json')) { log(JSON.stringify(audit, null, 2)); return; }
|
|
2631
|
+
log(cyan(`# leerness pre-wake-audit (1.9.209) β sleep μ sub-agent audit`));
|
|
2632
|
+
log(dim(` audited at: ${audit.auditedAt}`));
|
|
2633
|
+
log('');
|
|
2634
|
+
const sum = audit.summary;
|
|
2635
|
+
log(` π ${red(`critical ${sum.criticalCount}`)} Β· ${yel(`warning ${sum.warningCount}`)} Β· info ${sum.infoCount}`);
|
|
2636
|
+
if (sum.needsAttention) {
|
|
2637
|
+
log(yel(` β needsAttention=true β κΉ¨μ΄λ ν λ©μΈ μμ΄μ νΈ κ²ν νμ`));
|
|
2638
|
+
} else {
|
|
2639
|
+
log(grn(` β μ μ¬ μ΄μ μμ β sleep μμ `));
|
|
2640
|
+
}
|
|
2641
|
+
log('');
|
|
2642
|
+
if (audit.findings.critical.length) {
|
|
2643
|
+
log(red(`## π¨ critical (${audit.findings.critical.length})`));
|
|
2644
|
+
audit.findings.critical.forEach(f => {
|
|
2645
|
+
log(` - [${f.kind}] ${f.detail}`);
|
|
2646
|
+
if (f.items) f.items.forEach(i => log(dim(` β’ ${i.id}: ${i.text}`)));
|
|
2647
|
+
});
|
|
2648
|
+
log('');
|
|
2649
|
+
}
|
|
2650
|
+
if (audit.findings.warning.length) {
|
|
2651
|
+
log(yel(`## β warning (${audit.findings.warning.length})`));
|
|
2652
|
+
audit.findings.warning.forEach(f => log(` - [${f.kind}] ${f.detail}`));
|
|
2653
|
+
log('');
|
|
2654
|
+
}
|
|
2655
|
+
if (audit.findings.info.length) {
|
|
2656
|
+
log(dim(`## βΉ info (${audit.findings.info.length})`));
|
|
2657
|
+
audit.findings.info.forEach(f => log(dim(` - [${f.kind}] ${f.detail}`)));
|
|
2658
|
+
log('');
|
|
2659
|
+
}
|
|
2660
|
+
log(dim(` β μ μ₯: .harness/pre-wake-report.json (μ΅κ·Ό 10κ° μ μ§)`));
|
|
2661
|
+
log(dim(` β κΉ¨μ΄λ ν: leerness pre-wake-audit --last`));
|
|
2662
|
+
}
|
|
2663
|
+
|
|
2437
2664
|
// 1.9.199: wakeup miss μλ ν볡 κ°ν β last-handoff timestamp κΈ°λ‘ + 25min κΈ°λ interval μ λ° μΈ‘μ
|
|
2438
2665
|
// μ¬μ©μ λͺ
μ (1.9.198 νμ): "22:01μ λΌμ΄λμ μλμ§μ
λμ§μμμ΄"
|
|
2439
2666
|
// 1.9.196 task-log mtime κΈ°λ° detector λ task-log κ° μμ£Ό μ μ
λ°μ΄νΈλλ©΄ false positive.
|
|
@@ -4477,13 +4704,52 @@ function handoff(root) {
|
|
|
4477
4704
|
parts.push(`π₯ μμ² ${audit.open} (tracked)`);
|
|
4478
4705
|
}
|
|
4479
4706
|
} catch {}
|
|
4707
|
+
// 14) 1.9.209: pre-wake-audit μ΅κ·Ό λ³΄κ³ μ (μ¬μ©μ λͺ
μ) β κΉ¨μ΄λ¨ μ§ν μλ λ
ΈμΆ
|
|
4708
|
+
try {
|
|
4709
|
+
const pwState = _loadPreWakeReport(root);
|
|
4710
|
+
if (pwState.reports.length > 0) {
|
|
4711
|
+
const latest = pwState.reports[pwState.reports.length - 1];
|
|
4712
|
+
const sum = latest.summary || {};
|
|
4713
|
+
if (sum.criticalCount > 0 || sum.warningCount > 0) {
|
|
4714
|
+
const ageMin = Math.floor((Date.now() - new Date(latest.auditedAt).getTime()) / 60000);
|
|
4715
|
+
parts.push(`π pre-wake ${sum.criticalCount}C/${sum.warningCount}W (${ageMin}m)`);
|
|
4716
|
+
}
|
|
4717
|
+
}
|
|
4718
|
+
} catch {}
|
|
4480
4719
|
if (parts.length) {
|
|
4481
4720
|
const isTty = process.stdout && process.stdout.isTTY;
|
|
4482
4721
|
const cy = s => isTty ? `\x1b[36m${s}\x1b[0m` : s;
|
|
4483
|
-
log(cy(`π ν€λλΌμΈ (1.9.81/93/113/152/162/192/197/204/207): ${parts.join(' Β· ')}`));
|
|
4722
|
+
log(cy(`π ν€λλΌμΈ (1.9.81/93/113/152/162/192/197/204/207/209): ${parts.join(' Β· ')}`));
|
|
4484
4723
|
}
|
|
4485
4724
|
} catch {}
|
|
4486
4725
|
}
|
|
4726
|
+
|
|
4727
|
+
// 1.9.209: pre-wake-audit λ³Έλ¬Έ μλ λ
ΈμΆ (handoff λ§μ§λ§ λΆλΆ, μ¬μ©μ λͺ
μ)
|
|
4728
|
+
// "λ©μΈ μμ΄μ νΈκ° κΉ¨μ΄λ¬μλ, μλΈμμ΄μ νΈκ° μ 리ν λ΄μ©μ νμΈ"
|
|
4729
|
+
try {
|
|
4730
|
+
const pwState = _loadPreWakeReport(root);
|
|
4731
|
+
if (pwState.reports.length > 0) {
|
|
4732
|
+
const latest = pwState.reports[pwState.reports.length - 1];
|
|
4733
|
+
const ageMin = Math.floor((Date.now() - new Date(latest.auditedAt).getTime()) / 60000);
|
|
4734
|
+
// 4μκ° μ΄λ΄ λ³΄κ³ μλ§ μλ λ
ΈμΆ (μ€λλ 건 stale)
|
|
4735
|
+
if (ageMin < 240 && (latest.summary.criticalCount > 0 || latest.summary.warningCount > 0)) {
|
|
4736
|
+
const isTty = process.stdout && process.stdout.isTTY;
|
|
4737
|
+
const cy2 = s => isTty ? `\x1b[36m${s}\x1b[0m` : s;
|
|
4738
|
+
const rd2 = s => isTty ? `\x1b[31m${s}\x1b[0m` : s;
|
|
4739
|
+
const yl2 = s => isTty ? `\x1b[33m${s}\x1b[0m` : s;
|
|
4740
|
+
const dm2 = s => isTty ? `\x1b[2m${s}\x1b[0m` : s;
|
|
4741
|
+
log('');
|
|
4742
|
+
log(cy2(`## π μ§μ sleep pre-wake-audit (1.9.209, ${ageMin}λΆ μ )`));
|
|
4743
|
+
if (latest.findings.critical && latest.findings.critical.length) {
|
|
4744
|
+
latest.findings.critical.slice(0, 3).forEach(f => log(rd2(` π¨ [${f.kind}] ${f.detail}`)));
|
|
4745
|
+
}
|
|
4746
|
+
if (latest.findings.warning && latest.findings.warning.length) {
|
|
4747
|
+
latest.findings.warning.slice(0, 3).forEach(f => log(yl2(` β [${f.kind}] ${f.detail}`)));
|
|
4748
|
+
}
|
|
4749
|
+
log(dm2(` β μμΈ: leerness pre-wake-audit --last`));
|
|
4750
|
+
}
|
|
4751
|
+
}
|
|
4752
|
+
} catch {}
|
|
4487
4753
|
// 1.9.8: active rules μλ λ
ΈμΆ (λ§€ μΈμ
μμ μ AIμκ² λ³΄μ)
|
|
4488
4754
|
const activeRules = readRules(root).filter(r => r.status === 'active');
|
|
4489
4755
|
if (activeRules.length) {
|
|
@@ -15796,6 +16062,8 @@ async function main() {
|
|
|
15796
16062
|
if (cmd === 'requests') return requestsCmd(arg('--path', process.cwd()), args[1], ...args.slice(2));
|
|
15797
16063
|
// 1.9.208: leerness constraints <list|check|add> β νλ«νΌ/API μ μ½ μ¬μ μ²΄ν¬ (μ¬μ©μ λͺ
μ)
|
|
15798
16064
|
if (cmd === 'constraints') return constraintsCmd(arg('--path', process.cwd()), args[1], ...args.slice(2));
|
|
16065
|
+
// 1.9.209: leerness pre-wake-audit β sleep μ sub-agent audit (μ¬μ©μ λͺ
μ)
|
|
16066
|
+
if (cmd === 'pre-wake-audit') return preWakeAuditCmd(arg('--path', process.cwd()), args[1]);
|
|
15799
16067
|
if (cmd === 'rule' && args[1] === 'add') return ruleAdd(arg('--path', process.cwd()), args.slice(2).filter(x => !x.startsWith('-')).join(' '));
|
|
15800
16068
|
if (cmd === 'rule' && args[1] === 'list') return ruleList(arg('--path', process.cwd()));
|
|
15801
16069
|
if (cmd === 'rule' && args[1] === 'remove') return ruleRemove(arg('--path', process.cwd()), args[2]);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "leerness",
|
|
3
|
-
"version": "1.9.
|
|
3
|
+
"version": "1.9.209",
|
|
4
4
|
"description": "Leerness: λΉνκ΄΄ λ§μ΄κ·Έλ μ΄μ
, μλ λ²μ κ°μ§Β·μ
λ°μ΄νΈ, κ³ν/μ§ν/νΈλμ€ν μλν, κ²μΌλ¦Β·μν¬λ¦ΏΒ·μΈμ½λ© μλ κ°λ, Claude Code μ¬λμ ν΅ν©μ κ°μΆ νκ΅μ΄ μ°μ AI κ°λ° νλ€μ€.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"leerness",
|