@djolex999/vir-cli 0.2.2 → 0.2.4
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/dist/claude/updater.js +34 -2
- package/dist/claude/updater.js.map +1 -1
- package/dist/dedupe/detector.js +2 -2
- package/dist/dedupe/merger.js +2 -2
- package/dist/lint/linter.js +2 -2
- package/dist/pipeline/distiller.js +28 -11
- package/dist/pipeline/distiller.js.map +1 -1
- package/dist/pipeline/summarizer.js +2 -2
- package/dist/search/synthesizer.js +2 -2
- package/package.json +3 -3
- package/CLAUDE.md +0 -152
package/dist/claude/updater.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { existsSync, readFileSync, writeFileSync } from "node:fs";
|
|
1
|
+
import { existsSync, readdirSync, readFileSync, writeFileSync } from "node:fs";
|
|
2
2
|
import { homedir } from "node:os";
|
|
3
3
|
import { join } from "node:path";
|
|
4
4
|
import { kebab } from "../pipeline/writer.js";
|
|
@@ -224,7 +224,39 @@ export function applyPlan(plan) {
|
|
|
224
224
|
export function globalClaudePath() {
|
|
225
225
|
return join(homedir(), ".claude", "CLAUDE.md");
|
|
226
226
|
}
|
|
227
|
+
// Resolve a project's CLAUDE.md across the layouts people actually use.
|
|
228
|
+
// Checks candidates in priority order and returns the first that EXISTS:
|
|
229
|
+
// 1. ~/projects/<slug>/CLAUDE.md
|
|
230
|
+
// 2. ~/projects/<slug>-*/CLAUDE.md (suffixed dirs, e.g. "<slug>-web")
|
|
231
|
+
// 3. ~/code/<slug>/CLAUDE.md
|
|
232
|
+
// 4. ~/dev/<slug>/CLAUDE.md
|
|
233
|
+
// If none exist, falls back to the canonical (#1) location so the plan
|
|
234
|
+
// reports exists=false there. The returned path flows into PlanItem.target,
|
|
235
|
+
// which the dry-run output prints as each plan's heading — so the matched
|
|
236
|
+
// path is always visible.
|
|
227
237
|
export function projectClaudePath(projectSlug) {
|
|
228
|
-
|
|
238
|
+
const home = homedir();
|
|
239
|
+
const candidates = [];
|
|
240
|
+
const canonical = join(home, "projects", projectSlug, "CLAUDE.md");
|
|
241
|
+
candidates.push(canonical);
|
|
242
|
+
// Glob ~/projects/<slug>-* (sorted for deterministic first-match).
|
|
243
|
+
const projectsDir = join(home, "projects");
|
|
244
|
+
try {
|
|
245
|
+
for (const name of readdirSync(projectsDir).sort()) {
|
|
246
|
+
if (name !== projectSlug && name.startsWith(`${projectSlug}-`)) {
|
|
247
|
+
candidates.push(join(projectsDir, name, "CLAUDE.md"));
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
catch {
|
|
252
|
+
// ~/projects may not exist — skip the glob, keep the other candidates.
|
|
253
|
+
}
|
|
254
|
+
candidates.push(join(home, "code", projectSlug, "CLAUDE.md"));
|
|
255
|
+
candidates.push(join(home, "dev", projectSlug, "CLAUDE.md"));
|
|
256
|
+
for (const c of candidates) {
|
|
257
|
+
if (existsSync(c))
|
|
258
|
+
return c;
|
|
259
|
+
}
|
|
260
|
+
return canonical;
|
|
229
261
|
}
|
|
230
262
|
//# sourceMappingURL=updater.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"updater.js","sourceRoot":"","sources":["../../src/claude/updater.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,SAAS,CAAC;
|
|
1
|
+
{"version":3,"file":"updater.js","sourceRoot":"","sources":["../../src/claude/updater.ts"],"names":[],"mappings":"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"}
|
package/dist/dedupe/detector.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { maybeAnthropicClient, callLLM, normalizeModelName, withRateLimitRetry, } from "../pipeline/distiller.js";
|
|
2
2
|
import { kebab } from "../pipeline/writer.js";
|
|
3
3
|
const MAX_CANDIDATE_PAIRS = 30;
|
|
4
4
|
const MIN_DUP_CONFIDENCE = 0.7;
|
|
@@ -79,7 +79,7 @@ export async function detectDuplicates(cfg, db) {
|
|
|
79
79
|
const pairs = findCandidatePairs(rows);
|
|
80
80
|
if (pairs.length === 0)
|
|
81
81
|
return { checked: 0, duplicates: [] };
|
|
82
|
-
const client =
|
|
82
|
+
const client = maybeAnthropicClient(cfg);
|
|
83
83
|
const model = normalizeModelName(cfg.models.classify, cfg.provider);
|
|
84
84
|
const duplicates = [];
|
|
85
85
|
for (const pair of pairs) {
|
package/dist/dedupe/merger.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { appendFileSync, existsSync, mkdirSync, readFileSync, renameSync, writeFileSync, } from "node:fs";
|
|
2
2
|
import { basename, join } from "node:path";
|
|
3
|
-
import {
|
|
3
|
+
import { maybeAnthropicClient, callLLM, normalizeModelName, withRateLimitRetry, } from "../pipeline/distiller.js";
|
|
4
4
|
import { kebab } from "../pipeline/writer.js";
|
|
5
5
|
const CATEGORY_DIRS = {
|
|
6
6
|
pattern: "patterns",
|
|
@@ -46,7 +46,7 @@ ${a.content}
|
|
|
46
46
|
|
|
47
47
|
Note B:
|
|
48
48
|
${b.content}`;
|
|
49
|
-
const client =
|
|
49
|
+
const client = maybeAnthropicClient(cfg);
|
|
50
50
|
const model = normalizeModelName(cfg.models.distill, cfg.provider);
|
|
51
51
|
const merged = (await withRateLimitRetry(() => callLLM(cfg, client, { prompt, model, maxTokens: 2000 }))).trim();
|
|
52
52
|
rewriteWinnerBody(winnerFile, merged);
|
package/dist/lint/linter.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { readFileSync, readdirSync, statSync } from "node:fs";
|
|
2
2
|
import { join, relative } from "node:path";
|
|
3
|
-
import {
|
|
3
|
+
import { maybeAnthropicClient, callLLM, normalizeModelName, withRateLimitRetry, } from "../pipeline/distiller.js";
|
|
4
4
|
import { kebab } from "../pipeline/writer.js";
|
|
5
5
|
const SKIP_BASENAMES = new Set(["index.md", "log.md"]);
|
|
6
6
|
const SKIP_DIRS = new Set(["projects"]);
|
|
@@ -83,7 +83,7 @@ export async function contradictionCheck(cfg, db) {
|
|
|
83
83
|
if (pairs.length === 0) {
|
|
84
84
|
return { checked: 0, contradictions: [] };
|
|
85
85
|
}
|
|
86
|
-
const client =
|
|
86
|
+
const client = maybeAnthropicClient(cfg);
|
|
87
87
|
const model = normalizeModelName(cfg.models.classify, cfg.provider);
|
|
88
88
|
const contradictions = [];
|
|
89
89
|
for (const pair of pairs) {
|
|
@@ -11,6 +11,11 @@ class HttpError extends Error {
|
|
|
11
11
|
export function buildAnthropicClient(config) {
|
|
12
12
|
return new Anthropic({ apiKey: config.anthropicApiKey ?? "" });
|
|
13
13
|
}
|
|
14
|
+
// Returns null on the Kie path — that path uses native fetch (callKie) and
|
|
15
|
+
// never touches the Anthropic SDK, so don't allocate a client there.
|
|
16
|
+
export function maybeAnthropicClient(config) {
|
|
17
|
+
return config.provider === "kie" ? null : buildAnthropicClient(config);
|
|
18
|
+
}
|
|
14
19
|
// Canonical model IDs accepted by Kie's /claude/v1/messages endpoint.
|
|
15
20
|
// Anything that *starts with* one of these keys collapses to the bare ID,
|
|
16
21
|
// so a stray suffix in config (date stamp, accidental path fragment like
|
|
@@ -69,6 +74,9 @@ export async function callLLM(config, client, opts) {
|
|
|
69
74
|
prompt: opts.prompt,
|
|
70
75
|
});
|
|
71
76
|
}
|
|
77
|
+
if (!client) {
|
|
78
|
+
throw new Error("Anthropic client is required for provider 'anthropic' but was null");
|
|
79
|
+
}
|
|
72
80
|
return callAnthropic({
|
|
73
81
|
client,
|
|
74
82
|
model: opts.model,
|
|
@@ -83,7 +91,7 @@ export class Distiller {
|
|
|
83
91
|
distillModel;
|
|
84
92
|
constructor(cfg) {
|
|
85
93
|
this.cfg = cfg;
|
|
86
|
-
this.client =
|
|
94
|
+
this.client = maybeAnthropicClient(cfg);
|
|
87
95
|
this.classifyModel = normalizeModelName(cfg.models.classify, cfg.provider);
|
|
88
96
|
this.distillModel = normalizeModelName(cfg.models.distill, cfg.provider);
|
|
89
97
|
}
|
|
@@ -135,17 +143,26 @@ ${scrubbedContent}`;
|
|
|
135
143
|
}
|
|
136
144
|
}
|
|
137
145
|
const RETRY_DELAYS_MS = [60_000, 120_000, 240_000];
|
|
138
|
-
|
|
146
|
+
// The Kie path (native fetch → HttpError) retries 429 plus transient 5xx.
|
|
147
|
+
// The Anthropic SDK already retries 5xx internally, so on that path we only
|
|
148
|
+
// add 429 on top — never double-retry its 5xx.
|
|
149
|
+
const KIE_RETRYABLE_STATUS = new Set([429, 500, 502, 503, 504]);
|
|
150
|
+
function isRetryable(err) {
|
|
139
151
|
if (!err || typeof err !== "object")
|
|
140
152
|
return false;
|
|
153
|
+
if (err instanceof HttpError)
|
|
154
|
+
return KIE_RETRYABLE_STATUS.has(err.status);
|
|
155
|
+
if (err instanceof Anthropic.APIError)
|
|
156
|
+
return err.status === 429;
|
|
141
157
|
const e = err;
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
return
|
|
148
|
-
|
|
158
|
+
return e.status === 429 || e.statusCode === 429;
|
|
159
|
+
}
|
|
160
|
+
function statusOf(err) {
|
|
161
|
+
if (err && typeof err === "object") {
|
|
162
|
+
const e = err;
|
|
163
|
+
return e.status ?? e.statusCode ?? "?";
|
|
164
|
+
}
|
|
165
|
+
return "?";
|
|
149
166
|
}
|
|
150
167
|
async function sleep(ms) {
|
|
151
168
|
return new Promise((r) => setTimeout(r, ms));
|
|
@@ -156,10 +173,10 @@ export async function withRateLimitRetry(fn) {
|
|
|
156
173
|
return await fn();
|
|
157
174
|
}
|
|
158
175
|
catch (err) {
|
|
159
|
-
if (!
|
|
176
|
+
if (!isRetryable(err))
|
|
160
177
|
throw err;
|
|
161
178
|
const delay = RETRY_DELAYS_MS[attempt] ?? 240_000;
|
|
162
|
-
console.warn(`[vir]
|
|
179
|
+
console.warn(`[vir] retryable error (${statusOf(err)}) — retry ${attempt + 1}/${RETRY_DELAYS_MS.length} in ${delay / 1000}s`);
|
|
163
180
|
await sleep(delay);
|
|
164
181
|
}
|
|
165
182
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"distiller.js","sourceRoot":"","sources":["../../src/pipeline/distiller.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"distiller.js","sourceRoot":"","sources":["../../src/pipeline/distiller.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs";
|
|
2
2
|
import { join } from "node:path";
|
|
3
|
-
import {
|
|
3
|
+
import { maybeAnthropicClient, callLLM, normalizeModelName, withRateLimitRetry, } from "./distiller.js";
|
|
4
4
|
import { kebab } from "./writer.js";
|
|
5
5
|
const EXCERPT_LEN = 200;
|
|
6
6
|
const CHANGELOG_HEADER = "## Changelog";
|
|
@@ -41,7 +41,7 @@ export async function summarizeProject(cfg, projectSlug, db) {
|
|
|
41
41
|
return null;
|
|
42
42
|
const counts = countByCategory(group.rows);
|
|
43
43
|
const prompt = buildPrompt(group, counts);
|
|
44
|
-
const client =
|
|
44
|
+
const client = maybeAnthropicClient(cfg);
|
|
45
45
|
const model = normalizeModelName(cfg.models.distill, cfg.provider);
|
|
46
46
|
const body = await withRateLimitRetry(() => callLLM(cfg, client, { prompt, model, maxTokens: 1500 }));
|
|
47
47
|
const outPath = writeSummaryFile(cfg, projectSlug, body.trim(), counts);
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { maybeAnthropicClient, callLLM, normalizeModelName, withRateLimitRetry, } from "../pipeline/distiller.js";
|
|
2
2
|
export async function synthesize(cfg, query, hits) {
|
|
3
3
|
const notes = hits
|
|
4
4
|
.map((h) => `### ${h.title} (score: ${h.score})\n${h.content.trim()}`)
|
|
@@ -15,7 +15,7 @@ Instructions:
|
|
|
15
15
|
- Quote the specific note title when citing
|
|
16
16
|
- If notes don't contain relevant info, say so clearly
|
|
17
17
|
- Do not invent information not present in the notes`;
|
|
18
|
-
const client =
|
|
18
|
+
const client = maybeAnthropicClient(cfg);
|
|
19
19
|
const model = normalizeModelName(cfg.models.distill, cfg.provider);
|
|
20
20
|
return withRateLimitRetry(() => callLLM(cfg, client, {
|
|
21
21
|
prompt,
|
package/package.json
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@djolex999/vir-cli",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.4",
|
|
4
4
|
"description": "Distills Claude Code sessions into a compounding knowledge vault",
|
|
5
5
|
"author": "Djordje Marković <djordje@growthq.rs>",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"homepage": "https://github.com/djolex999/vir",
|
|
8
8
|
"repository": {
|
|
9
9
|
"type": "git",
|
|
10
|
-
"url": "https://github.com/djolex999/vir"
|
|
10
|
+
"url": "git+https://github.com/djolex999/vir.git"
|
|
11
11
|
},
|
|
12
12
|
"keywords": [
|
|
13
13
|
"claude",
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
],
|
|
21
21
|
"type": "module",
|
|
22
22
|
"bin": {
|
|
23
|
-
"vir": "
|
|
23
|
+
"vir": "dist/cli.js"
|
|
24
24
|
},
|
|
25
25
|
"scripts": {
|
|
26
26
|
"build": "tsc",
|
package/CLAUDE.md
DELETED
|
@@ -1,152 +0,0 @@
|
|
|
1
|
-
# vir
|
|
2
|
-
|
|
3
|
-
Local macOS daemon that distills Claude Code session transcripts into an
|
|
4
|
-
Obsidian vault.
|
|
5
|
-
|
|
6
|
-
Published to npm as `@djolex999/vir-cli` (scoped). Install:
|
|
7
|
-
`npm install -g @djolex999/vir-cli`. Repo: https://github.com/djolex999/vir. Reads `~/.claude/projects/**/*.jsonl`, filters by heuristic,
|
|
8
|
-
classifies with Haiku, extracts durable knowledge with Sonnet, writes typed
|
|
9
|
-
notes to the vault, maintains an index, and syncs back into CLAUDE.md files.
|
|
10
|
-
|
|
11
|
-
## Stack
|
|
12
|
-
|
|
13
|
-
- Node.js ≥ 20, TypeScript strict (`noImplicitAny`, `noUncheckedIndexedAccess`)
|
|
14
|
-
- `commander` for CLI, `chalk` for output, `zod` for config validation
|
|
15
|
-
- `better-sqlite3` for state (synchronous — no async complexity)
|
|
16
|
-
- `@anthropic-ai/sdk` for the Anthropic path; native `fetch` for the Kie path
|
|
17
|
-
- macOS `launchd` for the daemon, `osascript` for notifications
|
|
18
|
-
|
|
19
|
-
## Structure
|
|
20
|
-
|
|
21
|
-
```
|
|
22
|
-
src/
|
|
23
|
-
cli.ts # commander entry — every subcommand wired here
|
|
24
|
-
config.ts # ~/.vir/config.json schema + helpers
|
|
25
|
-
pipeline/
|
|
26
|
-
run.ts # orchestrator (scan → filter → scrub → distill → write)
|
|
27
|
-
scanner.ts # walk ~/.claude/projects, SHA-256 each .jsonl
|
|
28
|
-
parser.ts # extract assistant/user text, tool calls, files touched
|
|
29
|
-
filter.ts # heuristic scorer (length, tools, files, signal words)
|
|
30
|
-
scrubber.ts # strip API keys, bearer tokens, absolute paths, emails
|
|
31
|
-
distiller.ts # callLLM helper, Haiku classify + Sonnet extract,
|
|
32
|
-
# withRateLimitRetry, buildAnthropicClient,
|
|
33
|
-
# normalizeModelName
|
|
34
|
-
writer.ts # frontmatter + body, wikilink injection, index/log
|
|
35
|
-
summarizer.ts # per-project knowledge summaries
|
|
36
|
-
types.ts # ParsedSession, Classification, DistilledNote, Category
|
|
37
|
-
search/
|
|
38
|
-
retriever.ts # unified async search: embeddings → TF-IDF fallback
|
|
39
|
-
embedder.ts # Ollama integration (nomic-embed-text), cosine sim
|
|
40
|
-
synthesizer.ts # Claude synthesis for `vir query`
|
|
41
|
-
lint/
|
|
42
|
-
linter.ts # orphans, staleness, contradictions
|
|
43
|
-
dedupe/
|
|
44
|
-
detector.ts # candidate pairs + LLM judgment
|
|
45
|
-
merger.ts # archive / keep / Sonnet-merge
|
|
46
|
-
claude/
|
|
47
|
-
updater.ts # VIR:START / VIR:END block management
|
|
48
|
-
state/
|
|
49
|
-
db.ts # better-sqlite3, idempotent migrations
|
|
50
|
-
daemon/
|
|
51
|
-
launchd.ts # plist render + load/unload via spawnSync('launchctl')
|
|
52
|
-
ui/
|
|
53
|
-
display.ts # the ONE place console.log lives — palette, glyphs,
|
|
54
|
-
# header(), divider(), box(), spinner(), summary(),
|
|
55
|
-
# wrap(), sourceRow(), categoryRow()
|
|
56
|
-
```
|
|
57
|
-
|
|
58
|
-
## Key conventions
|
|
59
|
-
|
|
60
|
-
- **Path expansion.** All paths from config (`vaultPath`, `claudeProjectsDir`)
|
|
61
|
-
must run through `expandHome()` (or `os.homedir()` directly) before use.
|
|
62
|
-
Never assume `~/` works in `fs.*`.
|
|
63
|
-
- **Per-session try/catch.** The daemon must never die on a single bad
|
|
64
|
-
transcript. `pipeline/run.ts` wraps every session iteration and records the
|
|
65
|
-
error in the DB so it doesn't keep retrying.
|
|
66
|
-
- **Provider routing.**
|
|
67
|
-
- `provider: 'anthropic'` → `@anthropic-ai/sdk` (`buildAnthropicClient`).
|
|
68
|
-
- `provider: 'kie'` → native `fetch` to `https://api.kie.ai/claude/v1/messages`
|
|
69
|
-
with `Authorization: Bearer <kieApiKey>`. The SDK is **not** used for Kie
|
|
70
|
-
even with a `baseURL` override — its `x-api-key` header conflicts.
|
|
71
|
-
- Both flow through `callLLM(config, client, opts)`.
|
|
72
|
-
- **Model names.** `normalizeModelName(model, provider)` collapses any model
|
|
73
|
-
that *starts with* a Kie canonical id (`claude-haiku-4-5`,
|
|
74
|
-
`claude-sonnet-4-6`) back to the bare id. Fallback strips trailing
|
|
75
|
-
`-YYYYMMDD`. Anthropic path passes through untouched.
|
|
76
|
-
- **Rate limits.** Every LLM call is wrapped in `withRateLimitRetry()` — three
|
|
77
|
-
attempts with `60s / 120s / 240s` backoff on `429` (Anthropic SDK
|
|
78
|
-
`APIError.status === 429` and our `HttpError.status === 429` both detected).
|
|
79
|
-
Sessions are processed sequentially with a `2s` delay after each successful
|
|
80
|
-
distill.
|
|
81
|
-
- **State is the source of truth.** `~/.vir/vir.db` records every session by
|
|
82
|
-
path with its SHA-256 hash. Reruns are idempotent; a session is only
|
|
83
|
-
re-distilled if its file content changes. Migrations are additive only
|
|
84
|
-
(`PRAGMA table_info(sessions)` + `ALTER TABLE ADD COLUMN`).
|
|
85
|
-
- **VIR:START / VIR:END markers are sacred.** `sync-claude` only mutates bytes
|
|
86
|
-
between those markers. When a CLAUDE.md has no block, the new one is
|
|
87
|
-
appended; the rest of the file is preserved verbatim.
|
|
88
|
-
- **No comments explaining obvious things.** Comment WHY a non-obvious
|
|
89
|
-
invariant exists — never WHAT the code does.
|
|
90
|
-
- **All user-facing output goes through `ui/display.ts`.** Other modules
|
|
91
|
-
must not call `console.log` directly. The pipeline's `fileLog()` writes
|
|
92
|
-
to `~/.vir/daemon.log` in plain text regardless of UI mode; the
|
|
93
|
-
display module renders only when `!opts.quiet`.
|
|
94
|
-
- **Ollama is best-effort.** `writer.maybeEmbed()` and the search path
|
|
95
|
-
both probe via `isOllamaAvailableCached()` and silently fall back
|
|
96
|
-
(TF-IDF for query; no-op for writer). An embedding failure must never
|
|
97
|
-
fail a write.
|
|
98
|
-
- **Cost prompts respect intent.** `--yes`, `--daemon`, and
|
|
99
|
-
`--rewrite-only` all skip the > 20 new-session confirmation. The
|
|
100
|
-
daemon path *never* prompts (it has no tty).
|
|
101
|
-
- **`vir init` is an @inquirer/* wizard.** Arrow-key `select` for
|
|
102
|
-
provider and models, `input` with `validate` for keys/numbers,
|
|
103
|
-
`confirm` for the "create missing path?" flow. Don't fall back to
|
|
104
|
-
raw readline here — the rest of the file already imports it for
|
|
105
|
-
dedupe/sync-claude/cost prompts, but the init UX is the wizard.
|
|
106
|
-
- **`vir run` prints a preflight line.** `N files found · M cached · K
|
|
107
|
-
new` shows after the scan in dim text, and the same triple goes to
|
|
108
|
-
the daemon log. Diagnoses "fresh DB looks stale" misconfigurations
|
|
109
|
-
in one line.
|
|
110
|
-
|
|
111
|
-
## Commands
|
|
112
|
-
|
|
113
|
-
```
|
|
114
|
-
vir init # interactive setup
|
|
115
|
-
vir run # one pass (used by daemon)
|
|
116
|
-
vir run --full # ignore state cache, re-process everything
|
|
117
|
-
vir run --rewrite-only # re-render notes from stored content
|
|
118
|
-
# (no scan, no LLM, free)
|
|
119
|
-
vir run --yes # skip the > 20 sessions cost prompt
|
|
120
|
-
vir schedule install # write + load ~/Library/LaunchAgents plist
|
|
121
|
-
vir schedule uninstall # unload + remove plist
|
|
122
|
-
vir status # daemon state + knowledge base breakdown
|
|
123
|
-
vir query "<question>" # embeddings (Ollama) → TF-IDF fallback
|
|
124
|
-
# → Claude synthesis
|
|
125
|
-
vir embed # generate Ollama embeddings for notes
|
|
126
|
-
vir embed --force # regenerate all embeddings
|
|
127
|
-
vir summarize <project> # generate per-project summary
|
|
128
|
-
vir summarize --all # all projects with notes
|
|
129
|
-
vir lint # orphans + stale + contradictions
|
|
130
|
-
vir lint --orphans # orphans only (free)
|
|
131
|
-
vir lint --stale # staleness only (free)
|
|
132
|
-
vir lint --contradictions # contradictions only (Haiku tokens)
|
|
133
|
-
vir dedupe # interactive duplicate review + merge
|
|
134
|
-
vir sync-claude # diff then confirm CLAUDE.md updates
|
|
135
|
-
vir sync-claude --dry-run # diff only, never write
|
|
136
|
-
vir sync-claude --force # apply without confirmation
|
|
137
|
-
vir sync-claude <project> # specific project only
|
|
138
|
-
vir sync-claude --global # only ~/.claude/CLAUDE.md
|
|
139
|
-
```
|
|
140
|
-
|
|
141
|
-
## File locations
|
|
142
|
-
|
|
143
|
-
- Config: `~/.vir/config.json`
|
|
144
|
-
- State: `~/.vir/vir.db` (better-sqlite3 with WAL). A one-shot rename in
|
|
145
|
-
`StateDb`'s constructor moves the pre-rename `~/.vir/state.db` over to
|
|
146
|
-
`~/.vir/vir.db` if it's still around — preserves cache, hides the
|
|
147
|
-
history of the doc/code mismatch.
|
|
148
|
-
- Daemon log: `~/.vir/daemon.log`
|
|
149
|
-
- launchd plist: `~/Library/LaunchAgents/lab.growthq.vir.plist`
|
|
150
|
-
- Vault notes: `<vaultPath>/<outputDir>/{patterns,gotchas,decisions,tools,projects,archived}/`
|
|
151
|
-
- Vault index: `<vaultPath>/<outputDir>/index.md`
|
|
152
|
-
- Vault run log: `<vaultPath>/<outputDir>/log.md`
|