lithermes-ai 0.6.0 → 0.8.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/README.md CHANGED
@@ -57,7 +57,8 @@ Restart any running Hermes CLI or Hermes gateway process. Then open Hermes and t
57
57
  - Interactive install spinner keeps terminal installs lively while redirected or scripted installs stay plain; use `npx lithermes-ai install --yes --no-spinner` for quiet terminal installs.
58
58
  - `start-work`: open or dry-run a LitHermes plan inside Hermes.
59
59
  - LitHermes workflow skill set: `ai-slop-remover`, `comment-checker`,
60
- `debugging`, `deep-interview`, `frontend-ui-ux`, `lsp`, `programming`, `refactor`,
60
+ `debugging`, `deep-interview`, `frontend-ui-ux`, `git-master`, `init-deep`,
61
+ `lsp`, `programming`, `refactor`,
61
62
  `remove-ai-slops`, `review-work`, `rules`, `start-work`, `lit-plan`,
62
63
  `litgoal`, and `litwork` are installed as `lithermes:*` skills.
63
64
  - The full plugin payload — the `pre_llm_call` / `subagent_stop` hooks, every
package/README_Ko-KR.md CHANGED
@@ -57,7 +57,8 @@ npx lithermes-ai install --yes
57
57
  - interactive install spinner가 terminal 설치는 더 생동감 있게 보여주고, redirect/script 설치는 기존처럼 plain output을 유지합니다. 조용한 terminal 설치가 필요하면 `npx lithermes-ai install --yes --no-spinner`를 사용합니다.
58
58
  - `start-work`: LitHermes plan을 Hermes 작업으로 엽니다.
59
59
  - LitHermes workflow skill set: `ai-slop-remover`, `comment-checker`,
60
- `debugging`, `deep-interview`, `frontend-ui-ux`, `lsp`, `programming`, `refactor`,
60
+ `debugging`, `deep-interview`, `frontend-ui-ux`, `git-master`, `init-deep`,
61
+ `lsp`, `programming`, `refactor`,
61
62
  `remove-ai-slops`, `review-work`, `rules`, `start-work`, `lit-plan`,
62
63
  `litgoal`, `litwork`가 `lithermes:*` skill로 함께 설치됩니다.
63
64
  - 전체 plugin payload — `pre_llm_call` / `subagent_stop`
@@ -15,7 +15,8 @@ first-class Hermes skills:
15
15
  - Explicit skills are available as:
16
16
  `lithermes:ai-slop-remover`, `lithermes:comment-checker`,
17
17
  `lithermes:debugging`, `lithermes:deep-interview`,
18
- `lithermes:frontend-ui-ux`, `lithermes:lsp`,
18
+ `lithermes:frontend-ui-ux`, `lithermes:git-master`,
19
+ `lithermes:init-deep`, `lithermes:lsp`,
19
20
  `lithermes:programming`, `lithermes:refactor`,
20
21
  `lithermes:remove-ai-slops`, `lithermes:review-work`,
21
22
  `lithermes:rules`, `lithermes:start-work`, `lithermes:lit-plan`,
@@ -1,5 +1,6 @@
1
1
  from __future__ import annotations
2
2
 
3
+ import functools
3
4
  from pathlib import Path
4
5
  from typing import Any
5
6
 
@@ -30,6 +31,14 @@ PORTED_SKILLS = [
30
31
  "frontend-ui-ux",
31
32
  "Apply the LitHermes frontend UI/UX review discipline.",
32
33
  ),
34
+ (
35
+ "git-master",
36
+ "Run the LitHermes git-history specialist for commits, rebases, blame, and bisect.",
37
+ ),
38
+ (
39
+ "init-deep",
40
+ "Generate a hierarchical AGENTS.md knowledge base with the LitHermes onboarding workflow.",
41
+ ),
33
42
  (
34
43
  "lsp",
35
44
  "Use Hermes' native LSP diagnostics with LitHermes LSP guidance.",
@@ -107,6 +116,16 @@ def _handle_lithermes_cli(args) -> int:
107
116
  return 1
108
117
 
109
118
 
119
+ def _ignited(handler):
120
+ """Wrap a slash-command handler so its display prints the LITBURN banner."""
121
+
122
+ @functools.wraps(handler)
123
+ def wrapped(user_args):
124
+ return core.ignite(handler(user_args))
125
+
126
+ return wrapped
127
+
128
+
110
129
  def register(ctx) -> None:
111
130
  base = Path(__file__).resolve().parent
112
131
 
@@ -128,55 +147,55 @@ def register(ctx) -> None:
128
147
 
129
148
  ctx.register_command(
130
149
  "lit-plan",
131
- core.command_lit_plan,
150
+ _ignited(core.command_lit_plan),
132
151
  description="Create a durable Litwork implementation plan",
133
152
  args_hint='"what to build"',
134
153
  )
135
154
  ctx.register_command(
136
155
  "litwork-plan",
137
- core.command_lit_plan,
156
+ _ignited(core.command_lit_plan),
138
157
  description="Alias for /lit-plan",
139
158
  args_hint='"what to build"',
140
159
  )
141
160
  ctx.register_command(
142
161
  "lit",
143
- core.command_lit,
162
+ _ignited(core.command_lit),
144
163
  description="Start an Litwork run and execute the task immediately",
145
164
  args_hint='"task" [--completion-promise TEXT] [--strategy reset|continue]',
146
165
  )
147
166
  ctx.register_command(
148
167
  "lit-loop",
149
- core.command_lit_loop,
168
+ _ignited(core.command_lit_loop),
150
169
  description="Start an Litwork run and execute the task immediately",
151
170
  args_hint='"task" [--completion-promise TEXT] [--strategy reset|continue]',
152
171
  )
153
172
  ctx.register_command(
154
173
  "litwork-loop",
155
- core.command_lit_loop,
174
+ _ignited(core.command_lit_loop),
156
175
  description="Alias for /lit-loop",
157
176
  args_hint='"task" [--completion-promise TEXT] [--strategy reset|continue]',
158
177
  )
159
178
  ctx.register_command(
160
179
  "litgoal",
161
- core.command_litgoal,
180
+ _ignited(core.command_litgoal),
162
181
  description="Open or inspect the LitHermes litgoal durable runtime",
163
182
  args_hint='["objective"] [--worktree PATH]',
164
183
  )
165
184
  ctx.register_command(
166
185
  "review-work",
167
- core.command_review_work,
186
+ _ignited(core.command_review_work),
168
187
  description="Run the LitHermes 5-lane review orchestrator on the current diff",
169
188
  args_hint="[--base REF]",
170
189
  )
171
190
  ctx.register_command(
172
191
  "start-work",
173
- core.command_start_work,
192
+ _ignited(core.command_start_work),
174
193
  description="Open or dry-run a LitHermes plan against a workspace",
175
194
  args_hint="[plan-name] [--worktree PATH] [--dry-run]",
176
195
  )
177
196
  ctx.register_command(
178
197
  "deep-interview",
179
- core.command_deep_interview,
198
+ _ignited(core.command_deep_interview),
180
199
  description="Run the LitHermes Socratic clarity gate before planning/execution",
181
200
  args_hint="[--quick|--standard|--deep] <idea>",
182
201
  )
@@ -33,9 +33,16 @@ DIRECT_LIT_PATTERN = re.compile(r"^\s*(?:lit|litwork)\b\s+(?P<task>.+?)\s*$", re
33
33
  MAX_TASK_LEN = 4000
34
34
  _SLUG_PATTERN = re.compile(r"[^a-z0-9]+")
35
35
 
36
+ # Deterministic ignite banner. Printed verbatim on every LitHermes slash-command
37
+ # display (the only user-visible plugin channel); also instructed into LIT_CONTEXT
38
+ # for the bare-`lit` keyword path (best-effort — that path only reaches the model).
39
+ LITBURN_BANNER = "🔥 LITBURN IGNITED 🔥"
40
+
41
+
36
42
  LIT_CONTEXT = "\n".join(
37
43
  [
38
44
  "<lithermes-litwork>",
45
+ f"FIRST, open your reply with this exact line so the user sees Litwork engage: {LITBURN_BANNER}",
39
46
  "The user invoked Litwork/LitHermes. Operate in a durable, evidence-first loop:",
40
47
  "- restate the concrete completion promise before changing files;",
41
48
  "- keep the implementation scoped to the current repository and existing Hermes patterns;",
@@ -210,9 +217,53 @@ def _extract_run_context_task(message: str) -> str:
210
217
  return _clamp_task(m.group("task")) if m else ""
211
218
 
212
219
 
220
+ # Slash-command handlers are dispatched as handler(user_args) with NO session_id,
221
+ # so they cannot bind the native /goal themselves. They instead embed this marker
222
+ # in their agent_message; pre_llm_call (which DOES receive session_id) reads it and
223
+ # performs the bind. /lit & /lit-loop bind via the run-context block; /litgoal &
224
+ # /lit-plan declare an objective and bind via this marker.
225
+ _BIND_GOAL_PATTERN = re.compile(
226
+ r"<lithermes-bind-goal>(?P<obj>.+?)</lithermes-bind-goal>", re.DOTALL
227
+ )
228
+
229
+
230
+ def _extract_bind_goal(message: str) -> str:
231
+ m = _BIND_GOAL_PATTERN.search(message)
232
+ return _clamp_task(m.group("obj")) if m else ""
233
+
234
+
235
+ def bind_goal_marker(objective: str) -> str:
236
+ """Render the bind-goal marker a command embeds so pre_llm_call binds /goal."""
237
+ objective = (objective or "").strip()
238
+ return f"<lithermes-bind-goal>{objective}</lithermes-bind-goal>" if objective else ""
239
+
240
+
241
+ def ignite(result: str | dict[str, str]) -> str | dict[str, str]:
242
+ """Prepend the LITBURN banner to a command result's user-visible display.
243
+
244
+ ``display`` is the one channel Hermes prints to the user verbatim
245
+ (cli.py _cprint), so the banner deterministically fires on every LitHermes
246
+ slash command. agent_message (model-facing) is left untouched.
247
+ """
248
+ if isinstance(result, dict):
249
+ display = result.get("display")
250
+ if display and not str(display).startswith(LITBURN_BANNER):
251
+ return {**result, "display": f"{LITBURN_BANNER}\n{display}"}
252
+ return result
253
+ if isinstance(result, str) and result.strip() and not result.startswith(LITBURN_BANNER):
254
+ return f"{LITBURN_BANNER}\n{result}"
255
+ return result
256
+
257
+
213
258
  def pre_llm_call(**kwargs: Any) -> dict[str, str] | None:
214
259
  user_message = str(kwargs.get("user_message") or "")
215
260
  session_id = str(kwargs.get("session_id") or "")
261
+ # /litgoal & /lit-plan declare an objective via the bind-goal marker. Bind it
262
+ # (we have session_id here) and stop — those messages are self-contained.
263
+ bind_obj = _extract_bind_goal(user_message)
264
+ if bind_obj:
265
+ bind_native_goal(session_id, bind_obj)
266
+ return None
216
267
  # The /lit command injects a run-context message. Bind the native goal from
217
268
  # it (we have session_id here), then skip re-injecting context.
218
269
  if "<lithermes-run-context>" in user_message:
@@ -629,6 +680,7 @@ def build_plan_agent_message(brief: str, plan: Path, workspace: Path) -> str:
629
680
  "goal tools (goal_set / goal_add_criterion / goal_evidence / goal_complete) and inspect",
630
681
  "with `hermes lithermes goal status`.",
631
682
  "</lithermes-plan-context>",
683
+ bind_goal_marker(brief),
632
684
  ]
633
685
  )
634
686
 
@@ -799,6 +851,12 @@ def command_litgoal(raw_args: str) -> dict[str, str]:
799
851
  "Load the lithermes:litgoal skill for the full discipline.",
800
852
  "</lithermes-litgoal-command>",
801
853
  ]
854
+ # When an objective is given, bind the native /goal too (pre_llm_call reads
855
+ # this marker — slash handlers have no session_id). Inspect-only /litgoal
856
+ # (no objective) leaves any active goal untouched.
857
+ marker = bind_goal_marker(objective)
858
+ if marker:
859
+ agent_lines.append(marker)
802
860
  return {
803
861
  "display": f"{intro}\nState dir: {lithermes_dir(workspace) / 'litgoal'}",
804
862
  "agent_message": "\n".join(agent_lines),
@@ -1,7 +1,7 @@
1
1
  {
2
- "syncedAt": "2026-06-14T02:25:40.475Z",
2
+ "syncedAt": "2026-06-14T03:56:58.019Z",
3
3
  "source": "source-reference",
4
- "sourceHash": "09f07fa73866ccb4c0a7dc271d4d1ce45a9ac662ff911fab6f4a6d6e7db73c07",
4
+ "sourceHash": "23886fd1b52dc30433f8886ba15ccedbc3d134ba8f0b99b7a90a83d07c0351fe",
5
5
  "files": [
6
6
  {
7
7
  "path": "NOTICE.md",
@@ -9,15 +9,15 @@
9
9
  },
10
10
  {
11
11
  "path": "README.md",
12
- "sha256": "32bbef20afd99f774502c2b4cbf2e2326d40c4e4cd71108645849dddcc2608c4"
12
+ "sha256": "e0bc7d60f61a8d35df9f6287876e236e59e80e871261558701375a12cc4e4feb"
13
13
  },
14
14
  {
15
15
  "path": "__init__.py",
16
- "sha256": "e545ac92efb1a8d50c467b21b180eb41dad5e9a19379a8cbe5086956c21c3654"
16
+ "sha256": "14951813219a77f7074ff8ca36e26cc46b66b0987f28dbcf1827c9bcfa98d65c"
17
17
  },
18
18
  {
19
19
  "path": "core.py",
20
- "sha256": "c8cac49c17e573dabc59c4d5aa56402a71320f62145fabf9552e7fdb648f340a"
20
+ "sha256": "da2888e70b560697eaf81fe29d0b92a36e8e0563ab3bcab95c34472533faa937"
21
21
  },
22
22
  {
23
23
  "path": "litgoal/__init__.py",
@@ -49,7 +49,7 @@
49
49
  },
50
50
  {
51
51
  "path": "plugin.yaml",
52
- "sha256": "e90d47b24dc2cb5340d9485929ba40e62b2b5d6858951992c414701f015286fe"
52
+ "sha256": "4b8a31a093d883cf1714250564955c3d8ca87889887780515a7df15ed317e732"
53
53
  },
54
54
  {
55
55
  "path": "skills/ai-slop-remover/SKILL.md",
@@ -143,6 +143,14 @@
143
143
  "path": "skills/frontend-ui-ux/SKILL.md",
144
144
  "sha256": "914667044f135563658ceac733a085a6bbdd71a00a5f4030f73d43444e0388f7"
145
145
  },
146
+ {
147
+ "path": "skills/git-master/SKILL.md",
148
+ "sha256": "31d59a91767423094fd84ed668c8b8c7e14d515cd17e3845d91a0ce4aa0144c8"
149
+ },
150
+ {
151
+ "path": "skills/init-deep/SKILL.md",
152
+ "sha256": "f571334ad9150fd93ef57fcc9dd85d240812649975811e63045ff2a72e84260b"
153
+ },
146
154
  {
147
155
  "path": "skills/lit-plan/SKILL.md",
148
156
  "sha256": "1f09901f9bb8f19b92add59c3613231228c8b5b7adbefae1cb3eb5cf7c3c61dc"
@@ -1,5 +1,5 @@
1
1
  name: lithermes
2
- version: 0.6.0
2
+ version: 0.8.0
3
3
  description: "Hermes-native workflow toolkit: litgoal durable runtime, 5-lane review orchestrator, Litwork commands, skills, and prompt steering."
4
4
  author: "Hermes Agent"
5
5
  kind: standalone
@@ -0,0 +1,130 @@
1
+ ---
2
+ name: git-master
3
+ description: "MUST USE whenever a task needs a commit or git-history investigation. Covers atomic commits, staging, commit-message style, rebase, squash, fixup/autosquash, blame, bisect, reflog, git log -S/-G, and questions like who wrote this or when was this added. Do not use for ordinary code edits unless the user asks for git work."
4
+ ---
5
+
6
+ # Git Master
7
+
8
+ The LitHermes git-history specialist for Hermes. Use this skill when the user
9
+ asks you to operate on Git history or answer a Git-history question. Be exact,
10
+ conservative, and evidence-led. Read the repository state before you infer anything.
11
+
12
+ ## LitHermes publish boundary
13
+
14
+ Commit, push, force-push, and history rewrites are outward-facing or hard-to-reverse
15
+ operations. Per LitHermes discipline, do **not** commit, push, force-push, reset,
16
+ stash-pop, or rewrite history unless the user explicitly authorized that exact
17
+ operation. Investigative requests report findings and stop.
18
+
19
+ ## Mode Gate
20
+
21
+ Classify the request first:
22
+
23
+ - `COMMIT`: stage and commit local changes.
24
+ - `REBASE`: rebase, squash, fixup, autosquash, reorder, split, or otherwise rewrite branch history.
25
+ - `HISTORY`: answer when, where, who, why, or which commit changed something.
26
+ - `STATUS`: inspect branch, diff, or working-tree state without changing it.
27
+
28
+ If the request is only investigative, report findings and stop.
29
+
30
+ ## Ground Truth
31
+
32
+ Gather independent facts first (these are read-only and safe to run in parallel):
33
+
34
+ ```bash
35
+ git status --short
36
+ git diff --stat
37
+ git diff --staged --stat
38
+ git branch --show-current
39
+ git log -30 --oneline
40
+ git rev-parse --abbrev-ref @{upstream}
41
+ git merge-base HEAD origin/main
42
+ git merge-base HEAD origin/master
43
+ ```
44
+
45
+ Missing upstream or missing `main`/`master` is normal. Fall back to the best
46
+ available branch or report the missing fact. Never treat a failed lookup as proof.
47
+
48
+ ## Commit Mode
49
+
50
+ Commit only the user's requested changes. Preserve unrelated dirty work.
51
+
52
+ 1. Detect message style from recent history (`git log -30 --pretty=format:%s`). Use the
53
+ dominant local pattern, language, and casing. Do not default to Conventional
54
+ Commits unless the repo already uses them.
55
+ 2. Inspect the full diff, not only filenames. Separate unrelated user edits from the
56
+ requested commit.
57
+ 3. Build atomic groups by behavior, module, and revertability. Keep implementation and
58
+ its direct tests together.
59
+ 4. Prefer multiple commits for unrelated concerns. A single commit is acceptable only
60
+ when the changed files form one indivisible behavior or the user explicitly asks for one.
61
+ 5. Stage by path or hunk so each commit contains only its atomic group.
62
+ 6. Before each commit, verify `git diff --staged --stat` and enough staged diff to prove
63
+ the group is right.
64
+ 7. Commit with the detected style. After each commit, verify `git log -1 --oneline`.
65
+
66
+ Grouping rules:
67
+
68
+ - Split different features, modules, generated artifacts, config, docs, and test-only
69
+ changes unless they are inseparable.
70
+ - Keep generated files with the source change that produced them when omitting them
71
+ would leave the repo inconsistent.
72
+ - Never hide failing or unrelated changes inside a broad commit.
73
+ - Follow the user's git conventions (e.g. no AI/co-author attribution when the repo or
74
+ the user's rules forbid it).
75
+
76
+ Final report: list commit hashes, messages, and any remaining uncommitted files.
77
+
78
+ ## Rebase Mode
79
+
80
+ History rewriting is a shared-impact operation.
81
+
82
+ - Never rebase or rewrite `main`, `master`, `dev`, release branches, or a protected
83
+ branch unless the user explicitly named that exact operation.
84
+ - If commits may already be pushed, ask before force-pushing. Use `--force-with-lease`,
85
+ never plain `--force`.
86
+ - If the worktree is dirty, preserve it intentionally before rebasing. Do not stash-pop
87
+ over conflicts without checking what changed.
88
+ - For fixups, prefer `git commit --fixup=<hash>` then
89
+ `GIT_SEQUENCE_EDITOR=: git rebase -i --autosquash <base>`.
90
+ - For conflicts, read the conflicting files and resolve by intent. Do not choose
91
+ ours/theirs blindly.
92
+ - If a rebase goes wrong, run `git rebase --abort` first. Use reflog only after
93
+ explaining the recovery path.
94
+
95
+ After rewriting, run the relevant tests or at least the project's cheapest smoke check,
96
+ then show the new branch log from base to HEAD.
97
+
98
+ ## History Mode
99
+
100
+ Choose the Git tool by the question:
101
+
102
+ - `git log -S "text"`: when the count of an exact string changed.
103
+ - `git log -G "regex"`: when diffs touched lines matching a pattern.
104
+ - `git blame -L start,end -- file`: who last changed specific lines.
105
+ - `git log --follow -- file`: history across renames for one file.
106
+ - `git show <hash>`: inspect the commit that appears relevant.
107
+ - `git bisect`: find the first bad commit when there is a deterministic pass/fail
108
+ command and known good/bad bounds.
109
+ - `git reflog`: recover or explain recent local history movement.
110
+
111
+ Always cite the exact command evidence in the answer: commit hash, subject, file path,
112
+ and line or diff context when relevant. If the evidence is ambiguous, say what remains
113
+ unproven.
114
+
115
+ ## Safety Checks
116
+
117
+ Before any write to Git history:
118
+
119
+ - Current branch is known.
120
+ - Dirty work is accounted for.
121
+ - Upstream/pushed status is known or explicitly unknown.
122
+ - The operation matches an explicit user request and authorization.
123
+ - Recovery path is known (`rebase --abort`, reflog hash, or untouched worktree).
124
+
125
+ Before finishing:
126
+
127
+ - Run the most relevant verification available for the changed behavior or history
128
+ operation (Manual QA evidence where a behavior changed).
129
+ - Report commands that passed and any command you could not run.
130
+ - Leave the worktree state explicit.
@@ -0,0 +1,198 @@
1
+ ---
2
+ name: init-deep
3
+ description: "Initialize a hierarchical AGENTS.md knowledge base for a repository — a root AGENTS.md plus complexity-scored subdirectory files. Use when the user wants to bootstrap or refresh project knowledge for Hermes, onboard a codebase, generate AGENTS.md guidance (reading any existing CLAUDE.md for context), or map an unfamiliar repo. Adapted for Hermes: discovery and parallel generation via delegate_task children + Hermes lsp tools."
4
+ ---
5
+
6
+ # Init-Deep — hierarchical AGENTS.md generator (Hermes)
7
+
8
+ Generate hierarchical `AGENTS.md` files: a root knowledge base plus complexity-scored subdirectory
9
+ files. This is the LitHermes onboarding/knowledge-base skill, re-authored for Hermes surfaces:
10
+ read-only `delegate_task` children for discovery, Hermes' `lsp` tools for the code map, and parallel
11
+ `delegate_task` fan-out for generation. (`AGENTS.md` is the file Hermes loads natively as project
12
+ context — see the `lithermes:rules` skill.)
13
+
14
+ ## Usage
15
+
16
+ ```
17
+ init-deep # Update mode: modify existing AGENTS.md + create new where warranted
18
+ init-deep --create-new # Read existing → remove all → regenerate from scratch
19
+ init-deep --max-depth=2 # Limit directory depth (default: 3)
20
+ ```
21
+
22
+ ## Workflow (high level)
23
+
24
+ 1. **Discovery + analysis** (concurrent) — read-only `delegate_task` children + local bash structure +
25
+ `lsp` code map + read existing AGENTS.md.
26
+ 2. **Score & decide** — determine AGENTS.md locations from merged findings.
27
+ 3. **Generate** — root first, then subdirectories in parallel.
28
+ 4. **Review** — deduplicate, trim, validate.
29
+
30
+ Track all four phases explicitly and report each one `pending → in_progress → completed` as you go
31
+ (Hermes has no TodoWrite tool; keep the running state in your reply or a working note).
32
+
33
+ ## Phase 1 — Discovery + analysis (concurrent)
34
+
35
+ Mark "discovery" in_progress.
36
+
37
+ ### Fan out read-only discovery children immediately
38
+
39
+ Dispatch the discovery lanes as read-only `delegate_task` children — pass a `tasks` array so they run
40
+ concurrently and the parent blocks until all return. Each child is self-contained (goal + scope +
41
+ "read-only, return findings only"). Suggested lanes (one child each):
42
+
43
+ - **Structure** — predict standard patterns for the detected language; report deviations only.
44
+ - **Entry points** — find main/entry files; report non-standard organization.
45
+ - **Conventions** — find config files (`.eslintrc`, `pyproject.toml`, `.editorconfig`, …); report
46
+ project-specific rules.
47
+ - **Anti-patterns** — find `DO NOT` / `NEVER` / `ALWAYS` / `DEPRECATED` markers; list forbidden patterns.
48
+ - **Build/CI** — find `.github/workflows`, `Makefile`, `Taskfile`; report non-standard patterns.
49
+ - **Tests** — find test configs and structure; report unique conventions.
50
+
51
+ **Dynamic scaling** — after the bash pass below, add MORE `delegate_task` children based on project
52
+ scale (never a static count):
53
+
54
+ | Factor | Threshold | Additional children |
55
+ |--------|-----------|---------------------|
56
+ | Total files | >100 | +1 per 100 files |
57
+ | Total lines | >10k | +1 per 10k lines |
58
+ | Directory depth | ≥4 | +2 for deep exploration |
59
+ | Large files (>500 lines) | >10 files | +1 for complexity hotspots |
60
+ | Monorepo | detected | +1 per package/workspace |
61
+ | Multiple languages | >1 | +1 per language |
62
+
63
+ ```bash
64
+ total_files=$(find . -type f -not -path '*/node_modules/*' -not -path '*/.git/*' | wc -l)
65
+ total_lines=$(find . -type f \( -name "*.ts" -o -name "*.py" -o -name "*.go" \) -not -path '*/node_modules/*' -exec wc -l {} + 2>/dev/null | tail -1 | awk '{print $1}')
66
+ large_files=$(find . -type f \( -name "*.ts" -o -name "*.py" \) -not -path '*/node_modules/*' -exec wc -l {} + 2>/dev/null | awk '$1 > 500 {c++} END {print c+0}')
67
+ max_depth=$(find . -type d -not -path '*/node_modules/*' -not -path '*/.git/*' | awk -F/ '{print NF}' | sort -rn | head -1)
68
+ ```
69
+
70
+ For very broad repos, split the fan-out across several `delegate_task` batches rather than one giant
71
+ batch, but keep every child read-only.
72
+
73
+ ### Main session: concurrent local analysis
74
+
75
+ While the discovery children run, the main session does:
76
+
77
+ **1. Bash structural analysis**
78
+ ```bash
79
+ # Directory depth distribution
80
+ find . -type d -not -path '*/.*' -not -path '*/node_modules/*' -not -path '*/dist/*' -not -path '*/build/*' | awk -F/ '{print NF-1}' | sort -n | uniq -c
81
+ # Files per directory (top 30)
82
+ find . -type f -not -path '*/.*' -not -path '*/node_modules/*' | sed 's|/[^/]*$||' | sort | uniq -c | sort -rn | head -30
83
+ # Existing knowledge bases
84
+ find . -type f \( -name "AGENTS.md" -o -name "CLAUDE.md" \) -not -path '*/node_modules/*' 2>/dev/null
85
+ ```
86
+
87
+ **2. Read existing AGENTS.md** — for each file found, read it and extract key insights,
88
+ conventions, and anti-patterns into an EXISTING map. With `--create-new`, read ALL existing files
89
+ first (preserve context), THEN delete, THEN regenerate.
90
+
91
+ **3. LSP code map (if available)** — use Hermes' `lsp` tools: `lsp.status` to list configured servers,
92
+ then `lsp.symbols` for entry-point/workspace symbols (`class` / `interface` / `function`) and
93
+ `lsp.find_references` on the top exports to gauge centrality. If no server is configured, fall back to
94
+ the discovery children + plain search. (See the `lithermes:lsp` skill.)
95
+
96
+ Merge bash + LSP + existing + child findings. Mark "discovery" completed.
97
+
98
+ ## Phase 2 — Scoring & location decision
99
+
100
+ Mark "scoring" in_progress.
101
+
102
+ ### Scoring matrix
103
+
104
+ | Factor | Weight | High threshold | Source |
105
+ |--------|--------|----------------|--------|
106
+ | File count | 3× | >20 | bash |
107
+ | Subdir count | 2× | >5 | bash |
108
+ | Code ratio | 2× | >70% | bash |
109
+ | Unique patterns | 1× | has own config | child |
110
+ | Module boundary | 2× | has `index.ts`/`__init__.py` | bash |
111
+ | Symbol density | 2× | >30 symbols | LSP |
112
+ | Export count | 2× | >10 exports | LSP |
113
+ | Reference centrality | 3× | >20 refs | LSP |
114
+
115
+ ### Decision rules
116
+
117
+ | Score | Action |
118
+ |-------|--------|
119
+ | Root (`.`) | ALWAYS create |
120
+ | >15 | Create AGENTS.md |
121
+ | 8–15 | Create if it is a distinct domain |
122
+ | <8 | Skip (parent covers it) |
123
+
124
+ Mark "scoring" completed.
125
+
126
+ ## Phase 3 — Generate AGENTS.md
127
+
128
+ Mark "generate" in_progress.
129
+
130
+ **File-writing rule:** if `AGENTS.md` already exists at the target path, edit it in place; if not,
131
+ create it. NEVER overwrite an existing file — check existence first (via the discovery results or a
132
+ read).
133
+
134
+ ### Root AGENTS.md (full treatment)
135
+
136
+ ```markdown
137
+ # PROJECT KNOWLEDGE BASE
138
+ **Generated:** {TIMESTAMP} **Commit:** {SHORT_SHA} **Branch:** {BRANCH}
139
+
140
+ ## OVERVIEW
141
+ {1–2 sentences: what + core stack}
142
+
143
+ ## STRUCTURE
144
+ {tree with non-obvious purposes only}
145
+
146
+ ## WHERE TO LOOK
147
+ | Task | Location | Notes |
148
+
149
+ ## CODE MAP
150
+ {from LSP — skip if unavailable or project <10 files}
151
+
152
+ ## CONVENTIONS
153
+ {ONLY deviations from standard}
154
+
155
+ ## ANTI-PATTERNS (THIS PROJECT)
156
+ {explicitly forbidden here}
157
+
158
+ ## COMMANDS
159
+ {dev / test / build}
160
+
161
+ ## NOTES
162
+ {gotchas}
163
+ ```
164
+
165
+ Quality gate: 50–150 lines, no generic advice, no obvious info.
166
+
167
+ ### Subdirectory AGENTS.md (parallel)
168
+
169
+ Generate each non-root location in parallel — dispatch one writing `delegate_task` child per location
170
+ (batch them in one `delegate_task` call). Each child gets a `TASK:` line plus `DELIVERABLE` (the
171
+ AGENTS.md), `SCOPE` (this directory only), and `VERIFY` (30–80 lines, never repeats parent content;
172
+ sections: OVERVIEW 1 line, STRUCTURE if >5 subdirs, WHERE TO LOOK, CONVENTIONS if different,
173
+ ANTI-PATTERNS). Wait for all. Mark "generate" completed.
174
+
175
+ ## Phase 4 — Review & deduplicate
176
+
177
+ Mark "review" in_progress. For each generated file: remove generic advice, remove parent duplicates,
178
+ trim to the size limits, verify telegraphic style. Mark "review" completed.
179
+
180
+ ## Final report
181
+
182
+ ```
183
+ === init-deep complete ===
184
+ Mode: {update | create-new}
185
+ Files: [OK] ./AGENTS.md (root, {N} lines) · [OK] ./src/hooks/AGENTS.md ({N} lines)
186
+ Dirs analyzed: {N} · Created: {N} · Updated: {N}
187
+ Hierarchy: ./AGENTS.md └── src/hooks/AGENTS.md
188
+ ```
189
+
190
+ ## Anti-patterns
191
+
192
+ - **Static child count** — vary discovery `delegate_task` children by project size/depth (see the scaling table).
193
+ - **Sequential execution** — run discovery children + LSP concurrently; generate subdirectories in parallel.
194
+ - **Ignoring existing** — ALWAYS read existing AGENTS.md first, even with `--create-new`.
195
+ - **Over-documenting** — not every directory needs an AGENTS.md.
196
+ - **Redundancy** — a child file never repeats its parent.
197
+ - **Generic content** — remove anything that applies to all projects.
198
+ - **Verbose style** — telegraphic or die.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lithermes-ai",
3
- "version": "0.6.0",
3
+ "version": "0.8.0",
4
4
  "description": "npx/bunx installer for the LitHermes Hermes plugin",
5
5
  "license": "MIT",
6
6
  "repository": {