memnant 0.1.0 → 0.2.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.
Files changed (159) hide show
  1. package/README.md +131 -61
  2. package/dist/cli/archive.d.ts +9 -0
  3. package/dist/cli/archive.d.ts.map +1 -0
  4. package/dist/cli/archive.js +101 -0
  5. package/dist/cli/archive.js.map +1 -0
  6. package/dist/cli/export.d.ts.map +1 -1
  7. package/dist/cli/export.js +88 -7
  8. package/dist/cli/export.js.map +1 -1
  9. package/dist/cli/graph.d.ts +9 -0
  10. package/dist/cli/graph.d.ts.map +1 -0
  11. package/dist/cli/graph.js +108 -0
  12. package/dist/cli/graph.js.map +1 -0
  13. package/dist/cli/health.d.ts +9 -0
  14. package/dist/cli/health.d.ts.map +1 -0
  15. package/dist/cli/health.js +49 -0
  16. package/dist/cli/health.js.map +1 -0
  17. package/dist/cli/import.d.ts +10 -0
  18. package/dist/cli/import.d.ts.map +1 -0
  19. package/dist/cli/import.js +91 -0
  20. package/dist/cli/import.js.map +1 -0
  21. package/dist/cli/index.js +16 -0
  22. package/dist/cli/index.js.map +1 -1
  23. package/dist/cli/instructions.d.ts +11 -0
  24. package/dist/cli/instructions.d.ts.map +1 -1
  25. package/dist/cli/instructions.js +172 -32
  26. package/dist/cli/instructions.js.map +1 -1
  27. package/dist/cli/lint.d.ts +3 -0
  28. package/dist/cli/lint.d.ts.map +1 -1
  29. package/dist/cli/lint.js +81 -9
  30. package/dist/cli/lint.js.map +1 -1
  31. package/dist/cli/patterns.d.ts +8 -0
  32. package/dist/cli/patterns.d.ts.map +1 -0
  33. package/dist/cli/patterns.js +56 -0
  34. package/dist/cli/patterns.js.map +1 -0
  35. package/dist/cli/recall.d.ts.map +1 -1
  36. package/dist/cli/recall.js +24 -9
  37. package/dist/cli/recall.js.map +1 -1
  38. package/dist/cli/retract.d.ts +9 -0
  39. package/dist/cli/retract.d.ts.map +1 -0
  40. package/dist/cli/retract.js +64 -0
  41. package/dist/cli/retract.js.map +1 -0
  42. package/dist/cli/setup.d.ts +1 -0
  43. package/dist/cli/setup.d.ts.map +1 -1
  44. package/dist/cli/setup.js +33 -0
  45. package/dist/cli/setup.js.map +1 -1
  46. package/dist/cli/snapshot.d.ts.map +1 -1
  47. package/dist/cli/snapshot.js +21 -0
  48. package/dist/cli/snapshot.js.map +1 -1
  49. package/dist/cli/stats.d.ts +8 -0
  50. package/dist/cli/stats.d.ts.map +1 -0
  51. package/dist/cli/stats.js +96 -0
  52. package/dist/cli/stats.js.map +1 -0
  53. package/dist/cli/synthesise.d.ts +8 -0
  54. package/dist/cli/synthesise.d.ts.map +1 -0
  55. package/dist/cli/synthesise.js +55 -0
  56. package/dist/cli/synthesise.js.map +1 -0
  57. package/dist/context/branch.d.ts +27 -0
  58. package/dist/context/branch.d.ts.map +1 -0
  59. package/dist/context/branch.js +59 -0
  60. package/dist/context/branch.js.map +1 -0
  61. package/dist/context/brief.d.ts +27 -0
  62. package/dist/context/brief.d.ts.map +1 -0
  63. package/dist/context/brief.js +153 -0
  64. package/dist/context/brief.js.map +1 -0
  65. package/dist/context/compile.d.ts.map +1 -1
  66. package/dist/context/compile.js +19 -7
  67. package/dist/context/compile.js.map +1 -1
  68. package/dist/context/file-context.d.ts +27 -0
  69. package/dist/context/file-context.d.ts.map +1 -0
  70. package/dist/context/file-context.js +47 -0
  71. package/dist/context/file-context.js.map +1 -0
  72. package/dist/context/patterns.d.ts +23 -0
  73. package/dist/context/patterns.d.ts.map +1 -0
  74. package/dist/context/patterns.js +50 -0
  75. package/dist/context/patterns.js.map +1 -0
  76. package/dist/governor/drift.d.ts +26 -0
  77. package/dist/governor/drift.d.ts.map +1 -0
  78. package/dist/governor/drift.js +66 -0
  79. package/dist/governor/drift.js.map +1 -0
  80. package/dist/governor/overrides.d.ts +22 -0
  81. package/dist/governor/overrides.d.ts.map +1 -0
  82. package/dist/governor/overrides.js +39 -0
  83. package/dist/governor/overrides.js.map +1 -0
  84. package/dist/graph/queries.d.ts +33 -0
  85. package/dist/graph/queries.d.ts.map +1 -0
  86. package/dist/graph/queries.js +93 -0
  87. package/dist/graph/queries.js.map +1 -0
  88. package/dist/graph/relationships.d.ts +55 -0
  89. package/dist/graph/relationships.d.ts.map +1 -0
  90. package/dist/graph/relationships.js +176 -0
  91. package/dist/graph/relationships.js.map +1 -0
  92. package/dist/ledger/admin.d.ts +49 -0
  93. package/dist/ledger/admin.d.ts.map +1 -0
  94. package/dist/ledger/admin.js +121 -0
  95. package/dist/ledger/admin.js.map +1 -0
  96. package/dist/ledger/database.d.ts +4 -0
  97. package/dist/ledger/database.d.ts.map +1 -1
  98. package/dist/ledger/database.js +145 -3
  99. package/dist/ledger/database.js.map +1 -1
  100. package/dist/ledger/migrations.d.ts +15 -0
  101. package/dist/ledger/migrations.d.ts.map +1 -0
  102. package/dist/ledger/migrations.js +19 -0
  103. package/dist/ledger/migrations.js.map +1 -0
  104. package/dist/ledger/records.d.ts.map +1 -1
  105. package/dist/ledger/records.js +12 -1
  106. package/dist/ledger/records.js.map +1 -1
  107. package/dist/ledger/stats.d.ts +43 -0
  108. package/dist/ledger/stats.d.ts.map +1 -0
  109. package/dist/ledger/stats.js +81 -0
  110. package/dist/ledger/stats.js.map +1 -0
  111. package/dist/mcp/server.d.ts +3 -1
  112. package/dist/mcp/server.d.ts.map +1 -1
  113. package/dist/mcp/server.js +178 -25
  114. package/dist/mcp/server.js.map +1 -1
  115. package/dist/mcp/session-manager.d.ts +45 -0
  116. package/dist/mcp/session-manager.d.ts.map +1 -0
  117. package/dist/mcp/session-manager.js +136 -0
  118. package/dist/mcp/session-manager.js.map +1 -0
  119. package/dist/monitoring/health.d.ts +29 -0
  120. package/dist/monitoring/health.d.ts.map +1 -0
  121. package/dist/monitoring/health.js +112 -0
  122. package/dist/monitoring/health.js.map +1 -0
  123. package/dist/relevance/access.d.ts +27 -0
  124. package/dist/relevance/access.d.ts.map +1 -0
  125. package/dist/relevance/access.js +63 -0
  126. package/dist/relevance/access.js.map +1 -0
  127. package/dist/relevance/profiles.d.ts +15 -0
  128. package/dist/relevance/profiles.d.ts.map +1 -0
  129. package/dist/relevance/profiles.js +17 -0
  130. package/dist/relevance/profiles.js.map +1 -0
  131. package/dist/relevance/scoring.d.ts +58 -0
  132. package/dist/relevance/scoring.d.ts.map +1 -0
  133. package/dist/relevance/scoring.js +76 -0
  134. package/dist/relevance/scoring.js.map +1 -0
  135. package/dist/relevance/search.d.ts +26 -0
  136. package/dist/relevance/search.d.ts.map +1 -0
  137. package/dist/relevance/search.js +66 -0
  138. package/dist/relevance/search.js.map +1 -0
  139. package/dist/synthesis/cache.d.ts +30 -0
  140. package/dist/synthesis/cache.d.ts.map +1 -0
  141. package/dist/synthesis/cache.js +64 -0
  142. package/dist/synthesis/cache.js.map +1 -0
  143. package/dist/synthesis/patterns.d.ts +24 -0
  144. package/dist/synthesis/patterns.d.ts.map +1 -0
  145. package/dist/synthesis/patterns.js +117 -0
  146. package/dist/synthesis/patterns.js.map +1 -0
  147. package/dist/synthesis/synthesise.d.ts +31 -0
  148. package/dist/synthesis/synthesise.d.ts.map +1 -0
  149. package/dist/synthesis/synthesise.js +84 -0
  150. package/dist/synthesis/synthesise.js.map +1 -0
  151. package/dist/types.d.ts +24 -1
  152. package/dist/types.d.ts.map +1 -1
  153. package/dist/types.js +2 -0
  154. package/dist/types.js.map +1 -1
  155. package/dist/vector/search.d.ts +2 -0
  156. package/dist/vector/search.d.ts.map +1 -1
  157. package/dist/vector/search.js +6 -0
  158. package/dist/vector/search.js.map +1 -1
  159. package/package.json +7 -2
package/README.md CHANGED
@@ -1,100 +1,170 @@
1
1
  # memnant
2
2
 
3
- Your agent forgets everything between sessions. memnant is the structured ledger that survives.
3
+ Shared project memory for any MCP client.
4
4
 
5
- Context windows die. Conversations end. Three weeks later you're re-explaining decisions your agent already made with you. memnant gives your agent a typed, searchable, staleness-aware decision ledger — and it already knows how to use it.
5
+ ## The problem
6
6
 
7
- **[memnant.vercel.app](https://memnant.vercel.app)**
7
+ Your AI agent forgets everything between sessions. The Next.js caching gotcha you solved last Tuesday? Gone. The architecture decision from three weeks ago? Not in the context window.
8
8
 
9
- ## Get started
9
+ But the real problem is bigger. Platform memory is locked to one client and one project. Claude Code's memory doesn't work in Cursor. Cursor's memory doesn't work in Windsurf. And none of them carry the framework fix you solved in project A into project B.
10
+
11
+ memnant is locked to nothing. It works across any MCP-compatible agent, any project, any session. Your engineering knowledge compounds everywhere you build.
12
+
13
+ ## How it works
14
+
15
+ **It remembers.** The agent silently logs decisions, framework fixes, and rejections during conversation. Every record gets a vector embedding for semantic search. Ask "auth approach" and find the record where you chose JWTs over sessions.
16
+
17
+ **It compiles.** Sessions start and close automatically. At session start, memnant compiles context: last session's log, open TODOs, relevant decisions, framework fixes, staleness warnings. Three weeks away? One command. Full context. Under two minutes.
18
+
19
+ **It flags.** Codebase snapshots track file hashes. When a file changes after a decision was logged about it, that record is flagged `[stale]` everywhere. Every other memory tool serves old decisions as current. memnant tracks validity.
20
+
21
+ **It travels.** Export framework fixes from one project, import them into the next. The gotcha you solved once never bites you again — across any project, any codebase. No platform memory tool can do this because they're siloed by project. Your experience isn't.
22
+
23
+ ## Quick start
10
24
 
11
25
  ```bash
12
- cd your-project
13
26
  npx memnant
14
27
  ```
15
28
 
16
- That's it. First run walks you through setup — project name, agent config, starter specs. Every run after that starts a session and prints compiled context. Open your agent, start building.
29
+ First run creates your config and ledger. After that, it starts a session with compiled context.
17
30
 
18
- ## How it works
31
+ Add memnant to your agent's MCP config:
32
+
33
+ ```json
34
+ {
35
+ "mcpServers": {
36
+ "memnant": {
37
+ "command": "memnant",
38
+ "args": ["serve"]
39
+ }
40
+ }
41
+ }
42
+ ```
43
+
44
+ Start building. The agent logs decisions automatically. Start your next session with full context.
45
+
46
+ ## What a session looks like
47
+
48
+ ```
49
+ $ npx memnant
19
50
 
20
- 1. **Run one command.** `npx memnant` in any project. It auto-detects what to do: first time → guided setup, no session start one, in session → show status.
51
+ memnant · session start
52
+ Compiled context: ~4,200 tokens
21
53
 
22
- 2. **Open your agent.** memnant registers as an MCP server. Your agent gets 7 tools — recall, log, session context, session close, copy check, design check, status. It already knows when to call them.
54
+ ── Last Session (Feb 21) ──
55
+ Shipped: snapshot-first analytics pipeline
56
+ Decided: materialised views over live aggregation
57
+ TODO: wire dashboard filters to snapshot queries
23
58
 
24
- 3. **Build.** Your agent checks prior decisions before making new ones. Logs what it decides. Catches stale records when the codebase drifts. Closes the session with a summary when you're done — through conversation, not CLI.
59
+ ── Relevant Decisions (3) ──
60
+ [a3f2] Chose snapshot-first analytics — live adds 200ms
61
+ [b7e1] Dashboard uses server components, no client state
62
+ [c4d9] [stale] Analytics schema — analytics.ts changed Feb 24
25
63
 
26
- ## What the agent gets
64
+ ── Framework Fixes (1) ──
65
+ [d2a8] Next.js 15: useSearchParams needs Suspense boundary
27
66
 
28
- ### Decision Ledger
29
- Append-only records with vector embeddings. Decisions, framework fixes, spec snapshots — all semantically searchable. The agent calls `memnant_recall` and finds what it needs.
67
+ Session e8f3 started. Good building.
68
+ ```
69
+
70
+ ## Fixes that travel
30
71
 
31
- ### Session Lifecycle
32
- Compiled context at session start: last session's log, open TODOs, relevant decisions, framework fixes, spec constraints. Session close happens through the agent via `memnant_session_close`. No CLI needed.
72
+ ```bash
73
+ # In project A you solved a Next.js gotcha
74
+ memnant export --type framework_fix --format portable
75
+
76
+ # In project B — it's already there before you hit it
77
+ memnant import .../framework-fixes.portable.json
78
+ # → Imported 3 framework fixes (1 skipped as duplicate)
79
+ ```
33
80
 
34
- ### Staleness Detection
35
- Codebase snapshots track file hashes. When a file changes after a decision was logged about it, that record is flagged `[stale]` in recall and session context.
81
+ Framework fixes aren't project-specific. The caching bug you solved in your SaaS app applies to your next Next.js project. `memnant export` strips project-specific fields (embeddings, relationships, staleness). `memnant import` re-generates embeddings locally, deduplicates, and tags imports with their source.
36
82
 
37
- ### Spec Governor
38
- Copy audits catch banned phrases. Design system checks catch banned components. The agent validates via MCP tools. Also runs in CI with `memnant lint`.
83
+ Platform memory is siloed by project. Your experience isn't.
39
84
 
40
- ### Model Orchestrator
41
- Three tiers: triage (Haiku), analysis (Sonnet), build (Opus). Each gets tier-appropriate context.
85
+ ## Under the hood
42
86
 
43
- ## MCP Tools
87
+ **Storage.** Single SQLite file at `.memnant/ledger.db`. Copy it to another machine and everything comes with you.
44
88
 
45
- memnant exposes 7 tools via MCP (stdio transport):
89
+ **Search.** Local vector embeddings via all-MiniLM-L6-v2. Semantic search on CPU. No API calls. Works on a plane.
46
90
 
47
- | Tool | Description |
48
- |------|-------------|
49
- | `memnant_recall` | Semantic search across all records |
50
- | `memnant_log` | Log a decision, framework fix, or session log |
51
- | `memnant_session_context` | Get compiled session context |
52
- | `memnant_session_close` | Close the active session with a summary |
91
+ **Integration.** MCP server over stdio. 10 tools. Plugs into Claude Code, Cursor, or any MCP-compatible agent.
92
+
93
+ **Config.** `memnant.yaml` at your project root. Version-controlled. No dashboard, no account, no login.
94
+
95
+ **Export.** Markdown or JSON. Every record, every decision, every session log. Your history is never locked in.
96
+
97
+ ## As your ledger grows
98
+
99
+ The core loop is four things: remember, compile, flag, travel. As records accumulate, memnant has depth that earns its way in.
100
+
101
+ | Capability | What it does | Requires |
102
+ |---|---|---|
103
+ | **Connection Graph** | Records auto-link, supersede, and contradict at write time | Records in the ledger |
104
+ | **Relevance Scoring** | 4-signal composite: similarity, recency, freshness, frequency | Configurable in memnant.yaml |
105
+ | **Synthesis** | Cross-record questions with citations | `ANTHROPIC_API_KEY` |
106
+ | **Spec Governor** | Copy audits, design checks, persona tests, CI lint | Spec docs in `docs/` |
107
+ | **Predictive Context** | File-aware search, branch detection, co-occurrence patterns | Builds over sessions |
108
+ | **Model Routing** | Route tasks to Haiku/Sonnet/Opus with tier-appropriate context | API keys |
109
+ | **Health Monitoring** | Staleness rate, contradictions, spec drift, status levels | — |
110
+ | **Continuous Governance** | Pre-commit hooks, override tracking, governance feedback | Spec docs + git hooks |
111
+ | **Telegram** | Triage from your phone | `MEMRANT_TELEGRAM_TOKEN` |
112
+
113
+ Every capability is independent. Use what you need. Ignore the rest.
114
+
115
+ ## Core commands
116
+
117
+ ```bash
118
+ npx memnant # auto-detect: init, start session, or status
119
+ memnant log --type decision # write a record
120
+ memnant recall "auth approach" # semantic search
121
+ memnant session start # compile context
122
+ memnant session close # capture what happened
123
+ memnant snapshot # codebase snapshot for staleness
124
+ memnant export # full ledger to markdown/JSON
125
+ memnant lint # validate against spec docs
126
+ ```
127
+
128
+ 25 commands total. Full reference in the [docs](docs/).
129
+
130
+ ## MCP tools
131
+
132
+ | Tool | Purpose |
133
+ |---|---|
134
+ | `memnant_recall` | Semantic search over the ledger |
135
+ | `memnant_log` | Write a record (auto-starts session) |
136
+ | `memnant_session_context` | Compiled context for session start |
137
+ | `memnant_session_close` | Close session with summary |
53
138
  | `memnant_status` | Project status |
54
139
  | `memnant_check_copy` | Copy audit against spec |
55
140
  | `memnant_check_design` | Design system validation |
141
+ | `memnant_synthesise` | Cross-record questions with citations |
142
+ | `memnant_context_for_file` | Records relevant to a specific file |
143
+ | `memnant_project_brief` | Dynamic 500-token project summary |
56
144
 
57
- MCP is auto-configured by `npx memnant` on first run. Works with Claude Code, Codex, and any MCP-compatible agent.
145
+ ## What it's not
58
146
 
59
- ## Advanced CLI
147
+ **Not agent memory.** Agent memory stores preferences from conversations. memnant stores typed decisions with staleness tracking. It's a ledger, not a scratchpad.
60
148
 
61
- All commands are still available for scripts, CI, and power users:
149
+ **Not a context window.** Context windows are session-scoped. memnant is cross-session. It selects the right subset and injects it.
62
150
 
63
- ```
64
- memnant init memnant session start memnant check-copy
65
- memnant setup claude-code memnant session close memnant check-design
66
- memnant setup codex memnant session status memnant test-persona
67
- memnant log memnant snapshot memnant lint
68
- memnant recall memnant export memnant serve
69
- memnant ask memnant specs memnant instructions
70
- ```
151
+ **Not CLAUDE.md.** Static instructions tell agents how to behave. memnant is dynamic institutional knowledge — what was decided, when, why, and whether it's still valid.
71
152
 
72
- ## Stack
153
+ **Not chat history.** Chat history is what was said. memnant is what was decided.
73
154
 
74
- - TypeScript, Node.js (ESM)
75
- - SQLite via node-sqlite3-wasm
76
- - Local vector embeddings via @xenova/transformers (all-MiniLM-L6-v2)
77
- - CLI via Commander.js
78
- - MCP server via @modelcontextprotocol/sdk
79
- - 192 tests via vitest
155
+ ## Who it's for
80
156
 
81
- ## Development
157
+ Solo builders shipping multiple products with AI agents. You work in sessions — days or weeks apart. You juggle 3-4 projects. You already have agents doing the work. You need your engineering knowledge to compound across everything you build, not reset every time you switch projects.
82
158
 
83
- ```bash
84
- git clone https://github.com/peureka/memnant.git
85
- cd memnant
86
- npm install
87
- npm run build
88
- npm test
89
- ```
159
+ The test: three weeks away from a project, `npx memnant` gives full context in under two minutes. Switch to a new project, `memnant import` brings your framework fixes with you.
160
+
161
+ ## Dependencies
162
+
163
+ **Required:** Node.js >= 20
90
164
 
91
- ## Documentation
165
+ **Bundled:** SQLite (WASM, no native deps), local embeddings, MCP SDK
92
166
 
93
- - [`docs/PRODUCT.md`](docs/PRODUCT.md) What memnant is, what it isn't, why it's different
94
- - [`docs/SPEC.md`](docs/SPEC.md) — Data model and system behaviours
95
- - [`docs/PLAN.md`](docs/PLAN.md) — Build plan with epics, stories, and acceptance criteria
96
- - [`docs/PROJECT_INSTRUCTIONS.md`](docs/PROJECT_INSTRUCTIONS.md) — Decision framework
97
- - [`docs/PERSONA_KAI.md`](docs/PERSONA_KAI.md) — Primary persona
167
+ **Optional:** `ANTHROPIC_API_KEY` for synthesis and routing. `MEMRANT_TELEGRAM_TOKEN` for Telegram. Core functionality ledger, sessions, recall, staleness, export, lint — works fully offline with no API keys.
98
168
 
99
169
  ## License
100
170
 
@@ -0,0 +1,9 @@
1
+ /**
2
+ * memnant archive / unarchive — Archive old or superseded records.
3
+ *
4
+ * Archived records are excluded from recall, context compilation, and export.
5
+ * They are not deleted — they can be unarchived later.
6
+ */
7
+ import { Command } from 'commander';
8
+ export declare function registerArchiveCommand(program: Command): void;
9
+ //# sourceMappingURL=archive.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"archive.d.ts","sourceRoot":"","sources":["../../src/cli/archive.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AA2CpC,wBAAgB,sBAAsB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAgE7D"}
@@ -0,0 +1,101 @@
1
+ /**
2
+ * memnant archive / unarchive — Archive old or superseded records.
3
+ *
4
+ * Archived records are excluded from recall, context compilation, and export.
5
+ * They are not deleted — they can be unarchived later.
6
+ */
7
+ import { existsSync, readFileSync } from 'fs';
8
+ import { join } from 'path';
9
+ import yaml from 'js-yaml';
10
+ import { openDatabase } from '../ledger/database.js';
11
+ import { archiveRecord, unarchiveRecord, unarchiveAll, archiveSuperseded, archiveStaleOlderThan, } from '../ledger/admin.js';
12
+ function loadDb() {
13
+ const cwd = process.cwd();
14
+ const configPath = join(cwd, 'memnant.yaml');
15
+ if (!existsSync(configPath)) {
16
+ console.error('No memnant project found. Run `memnant init` first.');
17
+ process.exit(1);
18
+ }
19
+ const config = yaml.load(readFileSync(configPath, 'utf-8'));
20
+ const dbPath = join(cwd, config.memory.db_path);
21
+ if (!existsSync(dbPath)) {
22
+ console.error(`Ledger database not found at ${config.memory.db_path}. Run \`memnant init\` to recreate.`);
23
+ process.exit(1);
24
+ }
25
+ return openDatabase(dbPath);
26
+ }
27
+ function parseDuration(duration) {
28
+ const match = duration.match(/^(\d+)d$/);
29
+ if (!match) {
30
+ console.error(`Invalid duration '${duration}'. Expected format: <number>d (e.g. 90d for 90 days).`);
31
+ process.exit(1);
32
+ }
33
+ return parseInt(match[1], 10);
34
+ }
35
+ export function registerArchiveCommand(program) {
36
+ program
37
+ .command('archive')
38
+ .description('Archive old or superseded records')
39
+ .option('--id <id>', 'Archive a single record')
40
+ .option('--superseded', 'Archive all superseded records')
41
+ .option('--stale-older-than <duration>', 'Archive stale records older than duration (e.g. 90d)')
42
+ .action((opts) => {
43
+ if (!opts.id && !opts.superseded && !opts.staleOlderThan) {
44
+ console.error('Specify at least one: --id <id>, --superseded, or --stale-older-than <duration>');
45
+ process.exit(1);
46
+ }
47
+ const db = loadDb();
48
+ try {
49
+ if (opts.id) {
50
+ archiveRecord(db, opts.id);
51
+ console.log(`Archived record ${opts.id.slice(0, 8)}.`);
52
+ }
53
+ if (opts.superseded) {
54
+ const count = archiveSuperseded(db);
55
+ console.log(`Archived ${count} superseded record(s).`);
56
+ }
57
+ if (opts.staleOlderThan) {
58
+ const days = parseDuration(opts.staleOlderThan);
59
+ const count = archiveStaleOlderThan(db, days);
60
+ console.log(`Archived ${count} stale record(s) older than ${days} days.`);
61
+ }
62
+ }
63
+ catch (err) {
64
+ console.error(err.message);
65
+ process.exit(1);
66
+ }
67
+ finally {
68
+ db.close();
69
+ }
70
+ });
71
+ program
72
+ .command('unarchive')
73
+ .description('Restore archived records')
74
+ .option('--id <id>', 'Unarchive a single record')
75
+ .option('--all', 'Unarchive all archived records')
76
+ .action((opts) => {
77
+ if (!opts.id && !opts.all) {
78
+ console.error('Specify at least one: --id <id> or --all');
79
+ process.exit(1);
80
+ }
81
+ const db = loadDb();
82
+ try {
83
+ if (opts.id) {
84
+ unarchiveRecord(db, opts.id);
85
+ console.log(`Unarchived record ${opts.id.slice(0, 8)}. It will appear in queries again.`);
86
+ }
87
+ if (opts.all) {
88
+ const count = unarchiveAll(db);
89
+ console.log(`Unarchived ${count} record(s).`);
90
+ }
91
+ }
92
+ catch (err) {
93
+ console.error(err.message);
94
+ process.exit(1);
95
+ }
96
+ finally {
97
+ db.close();
98
+ }
99
+ });
100
+ }
101
+ //# sourceMappingURL=archive.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"archive.js","sourceRoot":"","sources":["../../src/cli/archive.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../src/cli/export.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAyBpC,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAoE5D"}
1
+ {"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../src/cli/export.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AA4BpC,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAsF5D"}
@@ -9,6 +9,7 @@ import { existsSync, readFileSync, mkdirSync, writeFileSync, rmSync } from 'fs';
9
9
  import { join } from 'path';
10
10
  import yaml from 'js-yaml';
11
11
  import { openDatabase } from '../ledger/database.js';
12
+ import { RECORD_TYPES } from '../types.js';
12
13
  const TYPE_SUBDIRS = {
13
14
  decision: 'decisions',
14
15
  session_log: 'session_logs',
@@ -16,17 +17,25 @@ const TYPE_SUBDIRS = {
16
17
  spec_snapshot: 'spec_snapshots',
17
18
  codebase_snapshot: 'codebase_snapshots',
18
19
  orchestrator_task: 'orchestrator_tasks',
20
+ synthesis_cache: 'synthesis_cache',
21
+ governance_override: 'governance_overrides',
19
22
  };
20
23
  export function registerExportCommand(program) {
21
24
  program
22
25
  .command('export')
23
26
  .description('Export the ledger to markdown or JSON')
24
- .option('--format <format>', 'Export format: markdown or json', 'markdown')
27
+ .option('--format <format>', 'Export format: markdown, json, portable, or notebooklm', 'markdown')
25
28
  .option('--since <date>', 'Export only records after YYYY-MM-DD')
29
+ .option('--type <type>', 'Export only records of this type')
26
30
  .action((opts) => {
27
31
  // Validate --format
28
- if (opts.format !== 'markdown' && opts.format !== 'json') {
29
- console.error(`Unknown export format '${opts.format}'. Valid formats: markdown, json`);
32
+ if (!['markdown', 'json', 'portable', 'notebooklm'].includes(opts.format)) {
33
+ console.error(`Unknown export format '${opts.format}'. Valid formats: markdown, json, portable, notebooklm`);
34
+ process.exit(1);
35
+ }
36
+ // Validate --type
37
+ if (opts.type && !RECORD_TYPES.includes(opts.type)) {
38
+ console.error(`Unknown record type '${opts.type}'. Valid types: ${RECORD_TYPES.join(', ')}`);
30
39
  process.exit(1);
31
40
  }
32
41
  // Validate --since
@@ -48,18 +57,28 @@ export function registerExportCommand(program) {
48
57
  process.exit(1);
49
58
  }
50
59
  const db = openDatabase(dbPath);
51
- // Query records
52
- let query = 'SELECT id, type, content_text, tags, related_records, created_at FROM record';
60
+ // Query records (exclude retracted and archived)
61
+ let query = 'SELECT id, type, content_text, tags, related_records, created_at FROM record WHERE retracted_at IS NULL AND archived_at IS NULL';
53
62
  const params = [];
54
63
  if (opts.since) {
55
- query += ' WHERE created_at >= ?';
64
+ query += ' AND created_at >= ?';
56
65
  params.push(opts.since + 'T00:00:00.000Z');
57
66
  }
67
+ if (opts.type) {
68
+ query += ' AND type = ?';
69
+ params.push(opts.type);
70
+ }
58
71
  query += ' ORDER BY created_at ASC';
59
72
  const records = db.all(query, params);
60
73
  db.close();
61
74
  const exportPath = join(cwd, config.memory.export_path);
62
- if (opts.format === 'json') {
75
+ if (opts.format === 'notebooklm') {
76
+ exportNotebookLM(records, exportPath, config.project.name);
77
+ }
78
+ else if (opts.format === 'portable') {
79
+ exportPortable(records, exportPath, config.project.name);
80
+ }
81
+ else if (opts.format === 'json') {
63
82
  exportJson(records, exportPath);
64
83
  }
65
84
  else {
@@ -93,6 +112,68 @@ function exportMarkdown(records, exportPath) {
93
112
  writeFileSync(join(exportPath, subdir, filename), content);
94
113
  }
95
114
  }
115
+ function exportPortable(records, exportPath, projectName) {
116
+ mkdirSync(exportPath, { recursive: true });
117
+ const portablePath = join(exportPath, 'framework-fixes.portable.json');
118
+ const data = {
119
+ memnant_version: '0.1.0',
120
+ source_project: projectName,
121
+ exported_at: new Date().toISOString(),
122
+ record_count: records.length,
123
+ records: records.map((r) => ({
124
+ type: r.type,
125
+ content_text: r.content_text,
126
+ tags: JSON.parse(r.tags),
127
+ original_id: r.id,
128
+ created_at: r.created_at,
129
+ })),
130
+ };
131
+ writeFileSync(portablePath, JSON.stringify(data, null, 2) + '\n');
132
+ }
133
+ const TYPE_LABELS_PLURAL = {
134
+ decision: 'Decisions',
135
+ session_log: 'Session Logs',
136
+ framework_fix: 'Framework Fixes',
137
+ spec_snapshot: 'Spec Snapshots',
138
+ codebase_snapshot: 'Codebase Snapshots',
139
+ orchestrator_task: 'Orchestrator Tasks',
140
+ synthesis_cache: 'Synthesis Cache',
141
+ governance_override: 'Governance Overrides',
142
+ };
143
+ function exportNotebookLM(records, exportPath, projectName) {
144
+ mkdirSync(exportPath, { recursive: true });
145
+ const filePath = join(exportPath, 'notebooklm.md');
146
+ const lines = [];
147
+ lines.push(`# ${projectName} — Project Knowledge Ledger`);
148
+ lines.push('');
149
+ lines.push(`Exported from memnant on ${new Date().toISOString().slice(0, 10)}. ${records.length} records.`);
150
+ lines.push('');
151
+ lines.push('---');
152
+ lines.push('');
153
+ // Group by type
154
+ const byType = new Map();
155
+ for (const r of records) {
156
+ const group = byType.get(r.type) || [];
157
+ group.push(r);
158
+ byType.set(r.type, group);
159
+ }
160
+ for (const [type, group] of byType) {
161
+ lines.push(`## ${TYPE_LABELS_PLURAL[type]} (${group.length})`);
162
+ lines.push('');
163
+ for (const r of group) {
164
+ const date = r.created_at.slice(0, 10);
165
+ const tags = JSON.parse(r.tags);
166
+ const tagStr = tags.length > 0 ? ` [${tags.join(', ')}]` : '';
167
+ lines.push(`### ${date} — ${r.id.slice(0, 8)}${tagStr}`);
168
+ lines.push('');
169
+ lines.push(r.content_text);
170
+ lines.push('');
171
+ lines.push('---');
172
+ lines.push('');
173
+ }
174
+ }
175
+ writeFileSync(filePath, lines.join('\n'));
176
+ }
96
177
  function exportJson(records, exportPath) {
97
178
  mkdirSync(exportPath, { recursive: true });
98
179
  const jsonPath = join(exportPath, 'export.json');
@@ -1 +1 @@
1
- {"version":3,"file":"export.js","sourceRoot":"","sources":["../../src/cli/export.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAGH,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,EAAE,MAAM,IAAI,CAAC;AAChF,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AAC5B,OAAO,IAAI,MAAM,SAAS,CAAC;AAC3B,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAGrD,MAAM,YAAY,GAA+B;IAC/C,QAAQ,EAAE,WAAW;IACrB,WAAW,EAAE,cAAc;IAC3B,aAAa,EAAE,iBAAiB;IAChC,aAAa,EAAE,gBAAgB;IAC/B,iBAAiB,EAAE,oBAAoB;IACvC,iBAAiB,EAAE,oBAAoB;CACxC,CAAC;AAWF,MAAM,UAAU,qBAAqB,CAAC,OAAgB;IACpD,OAAO;SACJ,OAAO,CAAC,QAAQ,CAAC;SACjB,WAAW,CAAC,uCAAuC,CAAC;SACpD,MAAM,CAAC,mBAAmB,EAAE,iCAAiC,EAAE,UAAU,CAAC;SAC1E,MAAM,CAAC,gBAAgB,EAAE,sCAAsC,CAAC;SAChE,MAAM,CAAC,CAAC,IAAwC,EAAE,EAAE;QACnD,oBAAoB;QACpB,IAAI,IAAI,CAAC,MAAM,KAAK,UAAU,IAAI,IAAI,CAAC,MAAM,KAAK,MAAM,EAAE,CAAC;YACzD,OAAO,CAAC,KAAK,CACX,0BAA0B,IAAI,CAAC,MAAM,kCAAkC,CACxE,CAAC;YACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QAED,mBAAmB;QACnB,IAAI,IAAI,CAAC,KAAK,IAAI,CAAC,qBAAqB,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;YAC1D,OAAO,CAAC,KAAK,CACX,wBAAwB,IAAI,CAAC,KAAK,2CAA2C,CAC9E,CAAC;YACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QAED,sBAAsB;QACtB,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC;QAC1B,MAAM,UAAU,GAAG,IAAI,CAAC,GAAG,EAAE,cAAc,CAAC,CAAC;QAE7C,IAAI,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;YAC5B,OAAO,CAAC,KAAK,CAAC,qDAAqD,CAAC,CAAC;YACrE,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QAED,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,YAAY,CAAC,UAAU,EAAE,OAAO,CAAC,CAAkB,CAAC;QAC7E,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;QAEhD,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,EAAE,CAAC;YACxB,OAAO,CAAC,KAAK,CACX,gCAAgC,MAAM,CAAC,MAAM,CAAC,OAAO,qCAAqC,CAC3F,CAAC;YACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QAED,MAAM,EAAE,GAAG,YAAY,CAAC,MAAM,CAAC,CAAC;QAEhC,gBAAgB;QAChB,IAAI,KAAK,GAAG,8EAA8E,CAAC;QAC3F,MAAM,MAAM,GAAa,EAAE,CAAC;QAE5B,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;YACf,KAAK,IAAI,wBAAwB,CAAC;YAClC,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,gBAAgB,CAAC,CAAC;QAC7C,CAAC;QAED,KAAK,IAAI,0BAA0B,CAAC;QAEpC,MAAM,OAAO,GAAG,EAAE,CAAC,GAAG,CAAC,KAAK,EAAE,MAAM,CAA2B,CAAC;QAChE,EAAE,CAAC,KAAK,EAAE,CAAC;QAEX,MAAM,UAAU,GAAG,IAAI,CAAC,GAAG,EAAE,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QAExD,IAAI,IAAI,CAAC,MAAM,KAAK,MAAM,EAAE,CAAC;YAC3B,UAAU,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC;QAClC,CAAC;aAAM,CAAC;YACN,cAAc,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC;QACtC,CAAC;QAED,OAAO,CAAC,GAAG,CAAC,YAAY,OAAO,CAAC,MAAM,eAAe,MAAM,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC,CAAC;IACpF,CAAC,CAAC,CAAC;AACP,CAAC;AAED,SAAS,cAAc,CAAC,OAAoB,EAAE,UAAkB;IAC9D,yCAAyC;IACzC,KAAK,MAAM,MAAM,IAAI,MAAM,CAAC,MAAM,CAAC,YAAY,CAAC,EAAE,CAAC;QACjD,MAAM,OAAO,GAAG,IAAI,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;QACzC,MAAM,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC;QAClD,SAAS,CAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC;IAED,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;QAC7B,MAAM,IAAI,GAAG,MAAM,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QAC5C,MAAM,OAAO,GAAG,MAAM,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;QACtC,MAAM,QAAQ,GAAG,GAAG,IAAI,IAAI,OAAO,KAAK,CAAC;QAEzC,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,CAAa,CAAC;QACjD,MAAM,cAAc,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,eAAe,CAAa,CAAC;QAEtE,MAAM,WAAW,GAAG,IAAI,CAAC,IAAI,CAC3B;YACE,EAAE,EAAE,MAAM,CAAC,EAAE;YACb,IAAI,EAAE,MAAM,CAAC,IAAI;YACjB,UAAU,EAAE,MAAM,CAAC,UAAU;YAC7B,IAAI;YACJ,eAAe,EAAE,cAAc;SAChC,EACD,EAAE,SAAS,EAAE,CAAC,CAAC,EAAE,CAClB,CAAC,IAAI,EAAE,CAAC;QAET,MAAM,OAAO,GAAG,QAAQ,WAAW,YAAY,MAAM,CAAC,YAAY,IAAI,CAAC;QAEvE,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QACzC,aAAa,CAAC,IAAI,CAAC,UAAU,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,OAAO,CAAC,CAAC;IAC7D,CAAC;AACH,CAAC;AAED,SAAS,UAAU,CAAC,OAAoB,EAAE,UAAkB;IAC1D,SAAS,CAAC,UAAU,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAE3C,MAAM,QAAQ,GAAG,IAAI,CAAC,UAAU,EAAE,aAAa,CAAC,CAAC;IAEjD,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QAC/B,EAAE,EAAE,CAAC,CAAC,EAAE;QACR,IAAI,EAAE,CAAC,CAAC,IAAI;QACZ,YAAY,EAAE,CAAC,CAAC,YAAY;QAC5B,IAAI,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAa;QACpC,eAAe,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,eAAe,CAAa;QAC1D,UAAU,EAAE,CAAC,CAAC,UAAU;KACzB,CAAC,CAAC,CAAC;IAEJ,aAAa,CAAC,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;AAChE,CAAC"}
1
+ {"version":3,"file":"export.js","sourceRoot":"","sources":["../../src/cli/export.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * memnant graph — Connection graph visualization and management.
3
+ *
4
+ * Story 9.4: Text-based graph, with --json, --type, --contradictions options.
5
+ * Also: unsupersede and dismiss-contradiction commands.
6
+ */
7
+ import { Command } from 'commander';
8
+ export declare function registerGraphCommand(program: Command): void;
9
+ //# sourceMappingURL=graph.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"graph.d.ts","sourceRoot":"","sources":["../../src/cli/graph.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AASpC,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAsG3D"}
@@ -0,0 +1,108 @@
1
+ /**
2
+ * memnant graph — Connection graph visualization and management.
3
+ *
4
+ * Story 9.4: Text-based graph, with --json, --type, --contradictions options.
5
+ * Also: unsupersede and dismiss-contradiction commands.
6
+ */
7
+ import { existsSync, readFileSync } from 'fs';
8
+ import { join } from 'path';
9
+ import yaml from 'js-yaml';
10
+ import { openDatabase } from '../ledger/database.js';
11
+ import { buildGraph, formatGraphAsText } from '../graph/queries.js';
12
+ import { unsupersede, dismissContradiction } from '../graph/relationships.js';
13
+ export function registerGraphCommand(program) {
14
+ program
15
+ .command('graph')
16
+ .description('Show the connection graph between records')
17
+ .argument('[record-id]', 'Show connections for a specific record')
18
+ .option('--json', 'Output as JSON')
19
+ .option('--type <type>', 'Filter by record type')
20
+ .option('--contradictions', 'Show only unresolved contradictions')
21
+ .action((recordId, opts) => {
22
+ const cwd = process.cwd();
23
+ const configPath = join(cwd, 'memnant.yaml');
24
+ if (!existsSync(configPath)) {
25
+ console.error('No memnant project found. Run `memnant init` first.');
26
+ process.exit(1);
27
+ }
28
+ const config = yaml.load(readFileSync(configPath, 'utf-8'));
29
+ const dbPath = join(cwd, config.memory.db_path);
30
+ if (!existsSync(dbPath)) {
31
+ console.error(`Ledger database not found at ${config.memory.db_path}. Run \`memnant init\` to recreate.`);
32
+ process.exit(1);
33
+ }
34
+ const db = openDatabase(dbPath);
35
+ try {
36
+ const nodes = buildGraph(db, {
37
+ recordId,
38
+ type: opts.type,
39
+ contradictionsOnly: opts.contradictions,
40
+ });
41
+ if (opts.json) {
42
+ console.log(JSON.stringify(nodes, null, 2));
43
+ }
44
+ else {
45
+ console.log(formatGraphAsText(nodes));
46
+ }
47
+ }
48
+ finally {
49
+ db.close();
50
+ }
51
+ });
52
+ program
53
+ .command('unsupersede')
54
+ .description('Remove a supersession relationship for a record')
55
+ .argument('<record-id>', 'Record ID to unsupersede')
56
+ .action((recordId) => {
57
+ const cwd = process.cwd();
58
+ const configPath = join(cwd, 'memnant.yaml');
59
+ if (!existsSync(configPath)) {
60
+ console.error('No memnant project found. Run `memnant init` first.');
61
+ process.exit(1);
62
+ }
63
+ const config = yaml.load(readFileSync(configPath, 'utf-8'));
64
+ const dbPath = join(cwd, config.memory.db_path);
65
+ const db = openDatabase(dbPath);
66
+ try {
67
+ const removed = unsupersede(db, recordId);
68
+ if (removed) {
69
+ console.log(`Removed supersession relationship for record ${recordId.slice(0, 8)}.`);
70
+ }
71
+ else {
72
+ console.log(`No supersession relationship found for record ${recordId.slice(0, 8)}.`);
73
+ }
74
+ }
75
+ finally {
76
+ db.close();
77
+ }
78
+ });
79
+ program
80
+ .command('dismiss-contradiction')
81
+ .description('Dismiss a contradiction between two records')
82
+ .argument('<id1>', 'First record ID')
83
+ .argument('<id2>', 'Second record ID')
84
+ .action((id1, id2) => {
85
+ const cwd = process.cwd();
86
+ const configPath = join(cwd, 'memnant.yaml');
87
+ if (!existsSync(configPath)) {
88
+ console.error('No memnant project found. Run `memnant init` first.');
89
+ process.exit(1);
90
+ }
91
+ const config = yaml.load(readFileSync(configPath, 'utf-8'));
92
+ const dbPath = join(cwd, config.memory.db_path);
93
+ const db = openDatabase(dbPath);
94
+ try {
95
+ const dismissed = dismissContradiction(db, id1, id2);
96
+ if (dismissed) {
97
+ console.log(`Dismissed contradiction between ${id1.slice(0, 8)} and ${id2.slice(0, 8)}.`);
98
+ }
99
+ else {
100
+ console.log(`No active contradiction found between ${id1.slice(0, 8)} and ${id2.slice(0, 8)}.`);
101
+ }
102
+ }
103
+ finally {
104
+ db.close();
105
+ }
106
+ });
107
+ }
108
+ //# sourceMappingURL=graph.js.map