kodebrain 0.1.0__py3-none-any.whl
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.
- kodebrain/__init__.py +1 -0
- kodebrain/cli.py +116 -0
- kodebrain/hook.py +90 -0
- kodebrain/install.py +179 -0
- kodebrain-0.1.0.dist-info/METADATA +65 -0
- kodebrain-0.1.0.dist-info/RECORD +8 -0
- kodebrain-0.1.0.dist-info/WHEEL +4 -0
- kodebrain-0.1.0.dist-info/entry_points.txt +2 -0
kodebrain/__init__.py
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "0.1.0"
|
kodebrain/cli.py
ADDED
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
"""
|
|
2
|
+
kodebrain CLI — install agent instructions and git hooks.
|
|
3
|
+
|
|
4
|
+
Usage:
|
|
5
|
+
kodebrain install [path] [--platform all|claude|cursor|copilot|windsurf|cline]
|
|
6
|
+
kodebrain uninstall [path]
|
|
7
|
+
kodebrain hook install [path]
|
|
8
|
+
kodebrain hook uninstall [path]
|
|
9
|
+
kodebrain hook status [path]
|
|
10
|
+
"""
|
|
11
|
+
|
|
12
|
+
from __future__ import annotations
|
|
13
|
+
import argparse
|
|
14
|
+
import sys
|
|
15
|
+
from pathlib import Path
|
|
16
|
+
|
|
17
|
+
from kodebrain.install import PLATFORMS, install, uninstall
|
|
18
|
+
from kodebrain import hook as _hook
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
ALL_PLATFORMS = list(PLATFORMS.keys())
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
def cmd_install(args: argparse.Namespace) -> int:
|
|
25
|
+
root = Path(args.path).resolve()
|
|
26
|
+
platforms = ALL_PLATFORMS if args.platform == "all" else [args.platform]
|
|
27
|
+
|
|
28
|
+
try:
|
|
29
|
+
written = install(root, platforms)
|
|
30
|
+
except RuntimeError as e:
|
|
31
|
+
print(f"error: {e}", file=sys.stderr)
|
|
32
|
+
return 1
|
|
33
|
+
|
|
34
|
+
print(f"Kode Brain installed in {root.name}/")
|
|
35
|
+
for f in written:
|
|
36
|
+
label = next(
|
|
37
|
+
(PLATFORMS[p]["label"] for p in PLATFORMS if PLATFORMS[p]["file"] == f),
|
|
38
|
+
f,
|
|
39
|
+
)
|
|
40
|
+
print(f" ✓ {f} ({label})")
|
|
41
|
+
return 0
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
def cmd_uninstall(args: argparse.Namespace) -> int:
|
|
45
|
+
root = Path(args.path).resolve()
|
|
46
|
+
changed = uninstall(root)
|
|
47
|
+
|
|
48
|
+
if not changed:
|
|
49
|
+
print("No Kode Brain blocks found — nothing to remove.")
|
|
50
|
+
return 0
|
|
51
|
+
|
|
52
|
+
print(f"Kode Brain removed from {root.name}/")
|
|
53
|
+
for f in changed:
|
|
54
|
+
print(f" ✓ {f}")
|
|
55
|
+
return 0
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
def cmd_hook(args: argparse.Namespace) -> int:
|
|
59
|
+
root = Path(args.path).resolve()
|
|
60
|
+
|
|
61
|
+
if not (root / ".git").is_dir():
|
|
62
|
+
print(f"error: {root} is not a git repository.", file=sys.stderr)
|
|
63
|
+
return 1
|
|
64
|
+
|
|
65
|
+
if args.hook_cmd == "install":
|
|
66
|
+
path = _hook.install(root)
|
|
67
|
+
print(f"Hook installed: {path}")
|
|
68
|
+
elif args.hook_cmd == "uninstall":
|
|
69
|
+
removed = _hook.uninstall(root)
|
|
70
|
+
print("Hook removed." if removed else "Hook not installed — nothing to remove.")
|
|
71
|
+
elif args.hook_cmd == "status":
|
|
72
|
+
installed = _hook.status(root)
|
|
73
|
+
print(f"Hook {'installed' if installed else 'not installed'}.")
|
|
74
|
+
return 0
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
def main() -> None:
|
|
78
|
+
parser = argparse.ArgumentParser(
|
|
79
|
+
prog="kodebrain",
|
|
80
|
+
description="Kode Brain — install agent instructions across AI platforms.",
|
|
81
|
+
)
|
|
82
|
+
sub = parser.add_subparsers(dest="command", required=True)
|
|
83
|
+
|
|
84
|
+
# install
|
|
85
|
+
p_install = sub.add_parser("install", help="Write KB instruction blocks to platform config files.")
|
|
86
|
+
p_install.add_argument("path", nargs="?", default=".", help="Project root (default: current directory)")
|
|
87
|
+
p_install.add_argument(
|
|
88
|
+
"--platform",
|
|
89
|
+
choices=["all"] + ALL_PLATFORMS,
|
|
90
|
+
default="all",
|
|
91
|
+
help="Target platform (default: all)",
|
|
92
|
+
)
|
|
93
|
+
|
|
94
|
+
# uninstall
|
|
95
|
+
p_uninstall = sub.add_parser("uninstall", help="Remove all KB instruction blocks.")
|
|
96
|
+
p_uninstall.add_argument("path", nargs="?", default=".", help="Project root (default: current directory)")
|
|
97
|
+
|
|
98
|
+
# hook
|
|
99
|
+
p_hook = sub.add_parser("hook", help="Manage the git post-commit hook.")
|
|
100
|
+
hook_sub = p_hook.add_subparsers(dest="hook_cmd", required=True)
|
|
101
|
+
for hcmd in ("install", "uninstall", "status"):
|
|
102
|
+
hp = hook_sub.add_parser(hcmd)
|
|
103
|
+
hp.add_argument("path", nargs="?", default=".", help="Project root (default: current directory)")
|
|
104
|
+
|
|
105
|
+
args = parser.parse_args()
|
|
106
|
+
|
|
107
|
+
if args.command == "install":
|
|
108
|
+
sys.exit(cmd_install(args))
|
|
109
|
+
elif args.command == "uninstall":
|
|
110
|
+
sys.exit(cmd_uninstall(args))
|
|
111
|
+
elif args.command == "hook":
|
|
112
|
+
sys.exit(cmd_hook(args))
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
if __name__ == "__main__":
|
|
116
|
+
main()
|
kodebrain/hook.py
ADDED
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Git post-commit hook that marks KB-tracked source files as dirty
|
|
3
|
+
after each commit, so the next /kodebrain scan knows what changed.
|
|
4
|
+
|
|
5
|
+
The hook does NOT run the LLM — it only updates file-hashes.json
|
|
6
|
+
so scan can detect drift deterministically.
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
from __future__ import annotations
|
|
10
|
+
import os
|
|
11
|
+
import re
|
|
12
|
+
import stat
|
|
13
|
+
import subprocess
|
|
14
|
+
from pathlib import Path
|
|
15
|
+
|
|
16
|
+
HOOK_START = "# kodebrain:start"
|
|
17
|
+
HOOK_END = "# kodebrain:end"
|
|
18
|
+
HOOK_FILE = ".git/hooks/post-commit"
|
|
19
|
+
_HOOK_RE = re.compile(
|
|
20
|
+
r"\n?" + re.escape(HOOK_START) + r".*?" + re.escape(HOOK_END) + r"\n?",
|
|
21
|
+
re.DOTALL,
|
|
22
|
+
)
|
|
23
|
+
|
|
24
|
+
_HOOK_BODY = """\
|
|
25
|
+
# kodebrain:start
|
|
26
|
+
# Kode Brain — mark changed source files as dirty in file-hashes.json
|
|
27
|
+
# Run /kodebrain scan in Claude Code to refresh KB pages after significant changes.
|
|
28
|
+
_KB_HASHES=$(ls docs/brain/projects/*/graph/file-hashes.json 2>/dev/null | head -1)
|
|
29
|
+
if [ -n "$_KB_HASHES" ]; then
|
|
30
|
+
_CHANGED=$(git diff --name-only HEAD~1 2>/dev/null | grep -E '\\.(ts|tsx|js|jsx|py|go|rs|java|rb|swift|kt)$' | head -30)
|
|
31
|
+
if [ -n "$_CHANGED" ]; then
|
|
32
|
+
python3 -c "
|
|
33
|
+
import json, hashlib, sys
|
|
34
|
+
from pathlib import Path
|
|
35
|
+
hashes_path = Path('$_KB_HASHES')
|
|
36
|
+
if not hashes_path.exists():
|
|
37
|
+
sys.exit(0)
|
|
38
|
+
hashes = json.loads(hashes_path.read_text())
|
|
39
|
+
changed = [f for f in '''$_CHANGED'''.strip().split() if f]
|
|
40
|
+
for f in changed:
|
|
41
|
+
p = Path(f)
|
|
42
|
+
if p.exists():
|
|
43
|
+
hashes[f] = hashlib.sha256(p.read_bytes()).hexdigest()
|
|
44
|
+
elif f in hashes:
|
|
45
|
+
del hashes[f]
|
|
46
|
+
hashes_path.write_text(json.dumps(hashes, indent=2))
|
|
47
|
+
" 2>/dev/null || true
|
|
48
|
+
fi
|
|
49
|
+
fi
|
|
50
|
+
# kodebrain:end"""
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
def install(root: Path) -> str:
|
|
54
|
+
hook_path = root / HOOK_FILE
|
|
55
|
+
hook_path.parent.mkdir(parents=True, exist_ok=True)
|
|
56
|
+
|
|
57
|
+
existing = hook_path.read_text(encoding="utf-8") if hook_path.exists() else ""
|
|
58
|
+
|
|
59
|
+
if HOOK_START in existing:
|
|
60
|
+
new_content = _HOOK_RE.sub("", existing).rstrip("\n") + "\n\n" + _HOOK_BODY + "\n"
|
|
61
|
+
elif existing.strip():
|
|
62
|
+
new_content = existing.rstrip("\n") + "\n\n" + _HOOK_BODY + "\n"
|
|
63
|
+
else:
|
|
64
|
+
new_content = "#!/bin/sh\n\n" + _HOOK_BODY + "\n"
|
|
65
|
+
|
|
66
|
+
hook_path.write_text(new_content, encoding="utf-8")
|
|
67
|
+
hook_path.chmod(hook_path.stat().st_mode | stat.S_IEXEC | stat.S_IXGRP | stat.S_IXOTH)
|
|
68
|
+
return HOOK_FILE
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
def uninstall(root: Path) -> bool:
|
|
72
|
+
hook_path = root / HOOK_FILE
|
|
73
|
+
if not hook_path.exists():
|
|
74
|
+
return False
|
|
75
|
+
original = hook_path.read_text(encoding="utf-8")
|
|
76
|
+
if HOOK_START not in original:
|
|
77
|
+
return False
|
|
78
|
+
cleaned = _HOOK_RE.sub("", original).rstrip("\n")
|
|
79
|
+
if cleaned and cleaned.strip() != "#!/bin/sh":
|
|
80
|
+
hook_path.write_text(cleaned + "\n", encoding="utf-8")
|
|
81
|
+
else:
|
|
82
|
+
hook_path.unlink()
|
|
83
|
+
return True
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
def status(root: Path) -> bool:
|
|
87
|
+
hook_path = root / HOOK_FILE
|
|
88
|
+
if not hook_path.exists():
|
|
89
|
+
return False
|
|
90
|
+
return HOOK_START in hook_path.read_text(encoding="utf-8")
|
kodebrain/install.py
ADDED
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Write/remove Kode Brain agent instruction blocks in platform config files.
|
|
3
|
+
|
|
4
|
+
Each platform gets a tagged block:
|
|
5
|
+
<!-- kodebrain:start -->
|
|
6
|
+
...instructions...
|
|
7
|
+
<!-- kodebrain:end -->
|
|
8
|
+
|
|
9
|
+
The block is idempotent — install twice, update safely. Uninstall removes it cleanly.
|
|
10
|
+
"""
|
|
11
|
+
|
|
12
|
+
from __future__ import annotations
|
|
13
|
+
import re
|
|
14
|
+
from pathlib import Path
|
|
15
|
+
|
|
16
|
+
BLOCK_START = "<!-- kodebrain:start -->"
|
|
17
|
+
BLOCK_END = "<!-- kodebrain:end -->"
|
|
18
|
+
_BLOCK_RE = re.compile(
|
|
19
|
+
r"\n?" + re.escape(BLOCK_START) + r".*?" + re.escape(BLOCK_END) + r"\n?",
|
|
20
|
+
re.DOTALL,
|
|
21
|
+
)
|
|
22
|
+
|
|
23
|
+
# ---------------------------------------------------------------------------
|
|
24
|
+
# Platform definitions
|
|
25
|
+
# ---------------------------------------------------------------------------
|
|
26
|
+
|
|
27
|
+
PLATFORMS = {
|
|
28
|
+
"claude": {
|
|
29
|
+
"file": "CLAUDE.md",
|
|
30
|
+
"label": "Claude Code",
|
|
31
|
+
"create_if_missing": True,
|
|
32
|
+
},
|
|
33
|
+
"cursor": {
|
|
34
|
+
"file": ".cursor/rules/kodebrain.mdc",
|
|
35
|
+
"label": "Cursor",
|
|
36
|
+
"create_if_missing": True,
|
|
37
|
+
},
|
|
38
|
+
"copilot": {
|
|
39
|
+
"file": ".github/copilot-instructions.md",
|
|
40
|
+
"label": "GitHub Copilot",
|
|
41
|
+
"create_if_missing": True,
|
|
42
|
+
},
|
|
43
|
+
"windsurf": {
|
|
44
|
+
"file": ".windsurfrules",
|
|
45
|
+
"label": "Windsurf",
|
|
46
|
+
"create_if_missing": True,
|
|
47
|
+
},
|
|
48
|
+
"cline": {
|
|
49
|
+
"file": ".clinerules",
|
|
50
|
+
"label": "Cline",
|
|
51
|
+
"create_if_missing": True,
|
|
52
|
+
},
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
# ---------------------------------------------------------------------------
|
|
56
|
+
# Block content
|
|
57
|
+
# ---------------------------------------------------------------------------
|
|
58
|
+
|
|
59
|
+
def _claude_block(name: str) -> str:
|
|
60
|
+
return f"""{BLOCK_START}
|
|
61
|
+
## Kode Brain — Knowledge Base
|
|
62
|
+
|
|
63
|
+
This project has a structured knowledge map at `docs/brain/projects/{name}/`.
|
|
64
|
+
|
|
65
|
+
**Session start:** Run `/kodebrain reading-pack "<task>"` before touching any code.
|
|
66
|
+
It returns the relevant domain pages, source file hints, and active warnings — 3–25× cheaper than navigating source files cold.
|
|
67
|
+
|
|
68
|
+
**After editing source files:** Run `/kodebrain update --files <f1> <f2>` to keep the KB current.
|
|
69
|
+
Subsequent queries return fresh data, not pre-edit state.
|
|
70
|
+
|
|
71
|
+
**For questions:** Run `/kodebrain query "<question>"` instead of reading raw source files.
|
|
72
|
+
|
|
73
|
+
**KB-first rule:** Use KB pages as primary source of truth.
|
|
74
|
+
Read source files directly only when making a targeted edit or when a node is `confidence: stale`.
|
|
75
|
+
|
|
76
|
+
KB location: `docs/brain/projects/{name}/`
|
|
77
|
+
Graph view: Open `docs/brain/` as an Obsidian vault.
|
|
78
|
+
{BLOCK_END}"""
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
def _generic_block(name: str) -> str:
|
|
82
|
+
return f"""{BLOCK_START}
|
|
83
|
+
## Kode Brain — Knowledge Base
|
|
84
|
+
|
|
85
|
+
This project has a structured knowledge map at `docs/brain/projects/{name}/`.
|
|
86
|
+
|
|
87
|
+
**Before starting any task:**
|
|
88
|
+
1. Read `docs/brain/projects/{name}/{name}.md` — project hub with all domains.
|
|
89
|
+
2. Read the domain hub(s) for areas you'll touch: `docs/brain/projects/{name}/domains/<domain>/<domain>.md`.
|
|
90
|
+
3. Check `docs/brain/projects/{name}/reports/reading-packs/` for a pre-built context pack matching your task.
|
|
91
|
+
|
|
92
|
+
**KB-first rule:** Use KB pages as primary source of truth.
|
|
93
|
+
Read source files directly only for targeted edits or when a page shows `confidence: stale`.
|
|
94
|
+
|
|
95
|
+
**After editing source files:**
|
|
96
|
+
The KB may drift from source. Check `docs/brain/projects/{name}/graph/file-hashes.json`
|
|
97
|
+
to identify which files changed. Run `/kodebrain scan` in Claude Code to refresh the KB.
|
|
98
|
+
|
|
99
|
+
KB location: `docs/brain/projects/{name}/`
|
|
100
|
+
{BLOCK_END}"""
|
|
101
|
+
|
|
102
|
+
|
|
103
|
+
def _make_block(platform: str, name: str) -> str:
|
|
104
|
+
if platform == "claude":
|
|
105
|
+
return _claude_block(name)
|
|
106
|
+
return _generic_block(name)
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
# ---------------------------------------------------------------------------
|
|
110
|
+
# KB discovery
|
|
111
|
+
# ---------------------------------------------------------------------------
|
|
112
|
+
|
|
113
|
+
def find_kb_name(root: Path) -> str | None:
|
|
114
|
+
"""Return the project name by scanning docs/brain/projects/."""
|
|
115
|
+
projects_dir = root / "docs" / "brain" / "projects"
|
|
116
|
+
if not projects_dir.is_dir():
|
|
117
|
+
return None
|
|
118
|
+
for child in projects_dir.iterdir():
|
|
119
|
+
if child.is_dir() and (child / "graph" / "nodes.json").exists():
|
|
120
|
+
return child.name
|
|
121
|
+
return None
|
|
122
|
+
|
|
123
|
+
|
|
124
|
+
# ---------------------------------------------------------------------------
|
|
125
|
+
# Install / uninstall
|
|
126
|
+
# ---------------------------------------------------------------------------
|
|
127
|
+
|
|
128
|
+
def install(root: Path, platforms: list[str]) -> list[str]:
|
|
129
|
+
"""Write KB instruction blocks. Returns list of files written."""
|
|
130
|
+
name = find_kb_name(root)
|
|
131
|
+
if name is None:
|
|
132
|
+
raise RuntimeError(
|
|
133
|
+
"No Kode Brain KB found in docs/brain/projects/. "
|
|
134
|
+
"Run /kodebrain init first."
|
|
135
|
+
)
|
|
136
|
+
|
|
137
|
+
written: list[str] = []
|
|
138
|
+
for platform in platforms:
|
|
139
|
+
cfg = PLATFORMS[platform]
|
|
140
|
+
target = root / cfg["file"]
|
|
141
|
+
|
|
142
|
+
target.parent.mkdir(parents=True, exist_ok=True)
|
|
143
|
+
|
|
144
|
+
existing = target.read_text(encoding="utf-8") if target.exists() else ""
|
|
145
|
+
block = _make_block(platform, name)
|
|
146
|
+
|
|
147
|
+
if BLOCK_START in existing:
|
|
148
|
+
# Replace existing block
|
|
149
|
+
new_content = _BLOCK_RE.sub("", existing).rstrip("\n") + "\n\n" + block + "\n"
|
|
150
|
+
elif existing.strip():
|
|
151
|
+
# Append to existing file
|
|
152
|
+
new_content = existing.rstrip("\n") + "\n\n" + block + "\n"
|
|
153
|
+
else:
|
|
154
|
+
# New file
|
|
155
|
+
new_content = block + "\n"
|
|
156
|
+
|
|
157
|
+
target.write_text(new_content, encoding="utf-8")
|
|
158
|
+
written.append(str(target.relative_to(root)))
|
|
159
|
+
|
|
160
|
+
return written
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
def uninstall(root: Path) -> list[str]:
|
|
164
|
+
"""Remove KB blocks from all platform files. Returns list of files changed."""
|
|
165
|
+
changed: list[str] = []
|
|
166
|
+
for cfg in PLATFORMS.values():
|
|
167
|
+
target = root / cfg["file"]
|
|
168
|
+
if not target.exists():
|
|
169
|
+
continue
|
|
170
|
+
original = target.read_text(encoding="utf-8")
|
|
171
|
+
if BLOCK_START not in original:
|
|
172
|
+
continue
|
|
173
|
+
cleaned = _BLOCK_RE.sub("", original).rstrip("\n")
|
|
174
|
+
if cleaned:
|
|
175
|
+
target.write_text(cleaned + "\n", encoding="utf-8")
|
|
176
|
+
else:
|
|
177
|
+
target.unlink()
|
|
178
|
+
changed.append(str(target.relative_to(root)))
|
|
179
|
+
return changed
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: kodebrain
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Living knowledge map for codebases — install agent instructions across AI platforms
|
|
5
|
+
Project-URL: Homepage, https://github.com/mekku/kb-builder
|
|
6
|
+
License: MIT
|
|
7
|
+
Requires-Python: >=3.9
|
|
8
|
+
Description-Content-Type: text/markdown
|
|
9
|
+
|
|
10
|
+
# kb-builder
|
|
11
|
+
|
|
12
|
+
**Kode Brain** — a living knowledge system for evolving software projects.
|
|
13
|
+
|
|
14
|
+
Converts an imperfect, growing codebase into a structured, searchable knowledge map of domains, capabilities, concepts, flows, runtime behavior, dependencies, legacy areas, migration states, and source evidence — so humans and AI agents can understand and modify the system without rediscovering everything from scratch.
|
|
15
|
+
|
|
16
|
+
## Design Documents
|
|
17
|
+
|
|
18
|
+
| Document | Purpose |
|
|
19
|
+
|---|---|
|
|
20
|
+
| [Taxonomy](docs/design/taxonomy.md) | Finalized node types, edge types, status labels, confidence labels |
|
|
21
|
+
| [Skills](docs/design/skills.md) | Skill API contracts — inputs, outputs, guarantees |
|
|
22
|
+
| [Agents](docs/design/agents.md) | Agent role boundaries — responsibilities, allowed skills, forbidden actions |
|
|
23
|
+
| [Workflows](docs/design/workflows.md) | Core workflow sequence diagrams |
|
|
24
|
+
| [Open Decisions](docs/design/open-decisions.md) | Unresolved architectural decisions |
|
|
25
|
+
|
|
26
|
+
## Schemas
|
|
27
|
+
|
|
28
|
+
| File | Purpose |
|
|
29
|
+
|---|---|
|
|
30
|
+
| [schema/node.schema.json](schema/node.schema.json) | JSON Schema for KnowledgeNode |
|
|
31
|
+
| [schema/edge.schema.json](schema/edge.schema.json) | JSON Schema for KnowledgeEdge |
|
|
32
|
+
| [schema/knowledge-base.schema.json](schema/knowledge-base.schema.json) | Top-level graph container schema |
|
|
33
|
+
|
|
34
|
+
## Design Order
|
|
35
|
+
|
|
36
|
+
Per the Kode Brain spec (§20.7):
|
|
37
|
+
|
|
38
|
+
```
|
|
39
|
+
Taxonomy → Workflow → Skills → Agents → Plugin/CLI
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
This repository is currently at the **design phase**. Implementation comes after the design is validated.
|
|
43
|
+
|
|
44
|
+
## Commands
|
|
45
|
+
|
|
46
|
+
```
|
|
47
|
+
/kodebrain init [path] Scan project, scaffold docs/kodebrain/
|
|
48
|
+
/kodebrain scan [path] Re-scan and update knowledge graph
|
|
49
|
+
/kodebrain query "<task or symptom>" Query the KB by task description
|
|
50
|
+
/kodebrain reading-pack "<task>" Generate + save a context pack
|
|
51
|
+
/kodebrain detect-legacy [--domain slug] Flag suspected dead code
|
|
52
|
+
/kodebrain review [--page path] Review KB pages for stale claims
|
|
53
|
+
/kodebrain update [--diff] [--files ...] Update KB from changed files
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
## Installation
|
|
57
|
+
|
|
58
|
+
The skill must be installed into Claude Code's skills directory:
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
# From the repo root
|
|
62
|
+
ln -s "$(pwd)" ~/.claude/skills/kodebrain
|
|
63
|
+
```
|
|
64
|
+
|
|
65
|
+
After symlinking, `SKILL.md` is discoverable by Claude Code and `/kodebrain` becomes available in any Claude Code session.
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
kodebrain/__init__.py,sha256=kUR5RAFc7HCeiqdlX36dZOHkUI5wI6V_43RpEcD8b-0,22
|
|
2
|
+
kodebrain/cli.py,sha256=WGuvRWbT6ZSSXGYeMrBUEklXMinyxkm-qU0rgz5aDHw,3569
|
|
3
|
+
kodebrain/hook.py,sha256=SydLKkho0tyUi13_RJt-OL4xCcEALwu4o37GD-pVG24,2854
|
|
4
|
+
kodebrain/install.py,sha256=gyqODHXmubCQEjYPm0jFIASM6xyD6Bpomx7uJqWNQVM,6097
|
|
5
|
+
kodebrain-0.1.0.dist-info/METADATA,sha256=NniPdUODjsSO_ROz2D4Qg35-7Td2xlMyQ5uYO15XAkU,2618
|
|
6
|
+
kodebrain-0.1.0.dist-info/WHEEL,sha256=QccIxa26bgl1E6uMy58deGWi-0aeIkkangHcxk2kWfw,87
|
|
7
|
+
kodebrain-0.1.0.dist-info/entry_points.txt,sha256=ANdDDnzUVgeAX5QIxThWzGL9_8wyYFJSGAY93UXaWiE,49
|
|
8
|
+
kodebrain-0.1.0.dist-info/RECORD,,
|