@luckydraw/cumulus 0.5.1
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 +148 -0
- package/dist/cli/cumulus.d.ts +3 -0
- package/dist/cli/cumulus.d.ts.map +1 -0
- package/dist/cli/cumulus.js +233 -0
- package/dist/cli/cumulus.js.map +1 -0
- package/dist/index.d.ts +33 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +43 -0
- package/dist/index.js.map +1 -0
- package/dist/lib/config.d.ts +86 -0
- package/dist/lib/config.d.ts.map +1 -0
- package/dist/lib/config.js +241 -0
- package/dist/lib/config.js.map +1 -0
- package/dist/lib/content-detector.d.ts +46 -0
- package/dist/lib/content-detector.d.ts.map +1 -0
- package/dist/lib/content-detector.js +359 -0
- package/dist/lib/content-detector.js.map +1 -0
- package/dist/lib/content-store.d.ts +255 -0
- package/dist/lib/content-store.d.ts.map +1 -0
- package/dist/lib/content-store.js +955 -0
- package/dist/lib/content-store.js.map +1 -0
- package/dist/lib/context-budget.d.ts +83 -0
- package/dist/lib/context-budget.d.ts.map +1 -0
- package/dist/lib/context-budget.js +101 -0
- package/dist/lib/context-budget.js.map +1 -0
- package/dist/lib/embeddings.d.ts +64 -0
- package/dist/lib/embeddings.d.ts.map +1 -0
- package/dist/lib/embeddings.js +176 -0
- package/dist/lib/embeddings.js.map +1 -0
- package/dist/lib/history.d.ts +120 -0
- package/dist/lib/history.d.ts.map +1 -0
- package/dist/lib/history.js +205 -0
- package/dist/lib/history.js.map +1 -0
- package/dist/lib/image-utils.d.ts +41 -0
- package/dist/lib/image-utils.d.ts.map +1 -0
- package/dist/lib/image-utils.js +288 -0
- package/dist/lib/image-utils.js.map +1 -0
- package/dist/lib/migrate.d.ts +35 -0
- package/dist/lib/migrate.d.ts.map +1 -0
- package/dist/lib/migrate.js +196 -0
- package/dist/lib/migrate.js.map +1 -0
- package/dist/lib/retriever.d.ts +56 -0
- package/dist/lib/retriever.d.ts.map +1 -0
- package/dist/lib/retriever.js +644 -0
- package/dist/lib/retriever.js.map +1 -0
- package/dist/lib/revert.d.ts +23 -0
- package/dist/lib/revert.d.ts.map +1 -0
- package/dist/lib/revert.js +75 -0
- package/dist/lib/revert.js.map +1 -0
- package/dist/lib/session.d.ts +65 -0
- package/dist/lib/session.d.ts.map +1 -0
- package/dist/lib/session.js +289 -0
- package/dist/lib/session.js.map +1 -0
- package/dist/lib/snapshots.d.ts +39 -0
- package/dist/lib/snapshots.d.ts.map +1 -0
- package/dist/lib/snapshots.js +99 -0
- package/dist/lib/snapshots.js.map +1 -0
- package/dist/lib/stream-processor.d.ts +149 -0
- package/dist/lib/stream-processor.d.ts.map +1 -0
- package/dist/lib/stream-processor.js +389 -0
- package/dist/lib/stream-processor.js.map +1 -0
- package/dist/lib/summarizer.d.ts +67 -0
- package/dist/lib/summarizer.d.ts.map +1 -0
- package/dist/lib/summarizer.js +213 -0
- package/dist/lib/summarizer.js.map +1 -0
- package/dist/mcp/index.d.ts +3 -0
- package/dist/mcp/index.d.ts.map +1 -0
- package/dist/mcp/index.js +16 -0
- package/dist/mcp/index.js.map +1 -0
- package/dist/mcp/proxy.d.ts +19 -0
- package/dist/mcp/proxy.d.ts.map +1 -0
- package/dist/mcp/proxy.js +120 -0
- package/dist/mcp/proxy.js.map +1 -0
- package/dist/mcp/server.d.ts +6 -0
- package/dist/mcp/server.d.ts.map +1 -0
- package/dist/mcp/server.js +29 -0
- package/dist/mcp/server.js.map +1 -0
- package/dist/mcp/shared-server.d.ts +21 -0
- package/dist/mcp/shared-server.d.ts.map +1 -0
- package/dist/mcp/shared-server.js +210 -0
- package/dist/mcp/shared-server.js.map +1 -0
- package/dist/mcp/tool-handler.d.ts +20 -0
- package/dist/mcp/tool-handler.d.ts.map +1 -0
- package/dist/mcp/tool-handler.js +1405 -0
- package/dist/mcp/tool-handler.js.map +1 -0
- package/dist/tui/components/App.d.ts +11 -0
- package/dist/tui/components/App.d.ts.map +1 -0
- package/dist/tui/components/App.js +607 -0
- package/dist/tui/components/App.js.map +1 -0
- package/dist/tui/components/DebugContextView.d.ts +13 -0
- package/dist/tui/components/DebugContextView.d.ts.map +1 -0
- package/dist/tui/components/DebugContextView.js +78 -0
- package/dist/tui/components/DebugContextView.js.map +1 -0
- package/dist/tui/components/IncludeMenu.d.ts +12 -0
- package/dist/tui/components/IncludeMenu.d.ts.map +1 -0
- package/dist/tui/components/IncludeMenu.js +127 -0
- package/dist/tui/components/IncludeMenu.js.map +1 -0
- package/dist/tui/components/InputArea.d.ts +27 -0
- package/dist/tui/components/InputArea.d.ts.map +1 -0
- package/dist/tui/components/InputArea.js +366 -0
- package/dist/tui/components/InputArea.js.map +1 -0
- package/dist/tui/components/MarkdownText.d.ts +38 -0
- package/dist/tui/components/MarkdownText.d.ts.map +1 -0
- package/dist/tui/components/MarkdownText.js +234 -0
- package/dist/tui/components/MarkdownText.js.map +1 -0
- package/dist/tui/components/MessageBubble.d.ts +11 -0
- package/dist/tui/components/MessageBubble.d.ts.map +1 -0
- package/dist/tui/components/MessageBubble.js +16 -0
- package/dist/tui/components/MessageBubble.js.map +1 -0
- package/dist/tui/components/MessageHistory.d.ts +11 -0
- package/dist/tui/components/MessageHistory.d.ts.map +1 -0
- package/dist/tui/components/MessageHistory.js +12 -0
- package/dist/tui/components/MessageHistory.js.map +1 -0
- package/dist/tui/components/RevertMenu.d.ts +17 -0
- package/dist/tui/components/RevertMenu.d.ts.map +1 -0
- package/dist/tui/components/RevertMenu.js +144 -0
- package/dist/tui/components/RevertMenu.js.map +1 -0
- package/dist/tui/components/StatusBar.d.ts +14 -0
- package/dist/tui/components/StatusBar.d.ts.map +1 -0
- package/dist/tui/components/StatusBar.js +13 -0
- package/dist/tui/components/StatusBar.js.map +1 -0
- package/dist/tui/components/StreamingResponse.d.ts +15 -0
- package/dist/tui/components/StreamingResponse.d.ts.map +1 -0
- package/dist/tui/components/StreamingResponse.js +52 -0
- package/dist/tui/components/StreamingResponse.js.map +1 -0
- package/dist/tui/hooks/useAppState.d.ts +147 -0
- package/dist/tui/hooks/useAppState.d.ts.map +1 -0
- package/dist/tui/hooks/useAppState.js +110 -0
- package/dist/tui/hooks/useAppState.js.map +1 -0
- package/dist/tui/hooks/useClaudeProcess.d.ts +19 -0
- package/dist/tui/hooks/useClaudeProcess.d.ts.map +1 -0
- package/dist/tui/hooks/useClaudeProcess.js +185 -0
- package/dist/tui/hooks/useClaudeProcess.js.map +1 -0
- package/dist/tui/index.d.ts +10 -0
- package/dist/tui/index.d.ts.map +1 -0
- package/dist/tui/index.js +11 -0
- package/dist/tui/index.js.map +1 -0
- package/dist/tui/utils/streamParser.d.ts +31 -0
- package/dist/tui/utils/streamParser.d.ts.map +1 -0
- package/dist/tui/utils/streamParser.js +63 -0
- package/dist/tui/utils/streamParser.js.map +1 -0
- package/package.json +94 -0
package/README.md
ADDED
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
# Cumulus
|
|
2
|
+
|
|
3
|
+
A CLI chat wrapper for Claude that implements the **Recursive Language Model (RLM)** pattern for unlimited conversation context.
|
|
4
|
+
|
|
5
|
+
## The Problem
|
|
6
|
+
|
|
7
|
+
Standard LLM chat interfaces accumulate conversation history in the context window. As conversations grow:
|
|
8
|
+
|
|
9
|
+
- **Context rot**: Model performance degrades as context fills up
|
|
10
|
+
- **Compaction**: Old messages get summarized or dropped, losing detail
|
|
11
|
+
- **Token limits**: Eventually you hit the wall, no matter how large the window
|
|
12
|
+
|
|
13
|
+
## The Solution
|
|
14
|
+
|
|
15
|
+
Cumulus treats conversation history as an **external environment** that Claude queries programmatically, rather than stuffing it all into context.
|
|
16
|
+
|
|
17
|
+
```
|
|
18
|
+
Traditional: [msg1][msg2][msg3]...[msg847] → context rot, compaction, limits
|
|
19
|
+
|
|
20
|
+
Cumulus: [fresh context] + tools to query [external history]
|
|
21
|
+
↓
|
|
22
|
+
Claude retrieves what it needs, when it needs it
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
Each message is a **fresh Claude invocation**. Claude uses MCP tools to retrieve relevant context from the complete conversation history stored in local files.
|
|
26
|
+
|
|
27
|
+
## How It Works
|
|
28
|
+
|
|
29
|
+
```
|
|
30
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
31
|
+
│ $ cumulus my-project │
|
|
32
|
+
│ > Help me refactor the auth module we discussed yesterday │
|
|
33
|
+
└─────────────────────────────────────────────────────────────┘
|
|
34
|
+
│
|
|
35
|
+
▼
|
|
36
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
37
|
+
│ Cumulus │
|
|
38
|
+
│ 1. Append user message to history │
|
|
39
|
+
│ 2. Spawn fresh: claude --print --mcp-config history.json │
|
|
40
|
+
│ 3. Claude uses search_history("auth module") tool │
|
|
41
|
+
│ 4. Claude retrieves relevant messages from history │
|
|
42
|
+
│ 5. Claude responds with full context awareness │
|
|
43
|
+
│ 6. Append response to history │
|
|
44
|
+
│ 7. Next message: completely fresh context │
|
|
45
|
+
└─────────────────────────────────────────────────────────────┘
|
|
46
|
+
│
|
|
47
|
+
▼
|
|
48
|
+
┌─────────────────────────────────────────────────────────────┐
|
|
49
|
+
│ ~/.cumulus/threads/my-project.jsonl │
|
|
50
|
+
│ ──────────────────────────────────────── │
|
|
51
|
+
│ Full conversation history, never truncated │
|
|
52
|
+
│ Claude queries via MCP tools as needed │
|
|
53
|
+
└─────────────────────────────────────────────────────────────┘
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
## Key Features
|
|
57
|
+
|
|
58
|
+
- **Unlimited history**: Conversations can span thousands of messages without degradation
|
|
59
|
+
- **Full Claude Code power**: All tools work (Bash, Edit, Read, etc.) - cumulus just manages context
|
|
60
|
+
- **Persistent threads**: Pick up any conversation where you left off
|
|
61
|
+
- **Selective retrieval**: Claude decides what context it needs, reducing noise
|
|
62
|
+
- **Cost efficient**: Only retrieve relevant context, not everything
|
|
63
|
+
|
|
64
|
+
## Installation
|
|
65
|
+
|
|
66
|
+
```bash
|
|
67
|
+
npm install -g cumulus-cli
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
## Usage
|
|
71
|
+
|
|
72
|
+
```bash
|
|
73
|
+
# Start or continue a conversation thread
|
|
74
|
+
cumulus my-project
|
|
75
|
+
|
|
76
|
+
# List all threads
|
|
77
|
+
cumulus --list
|
|
78
|
+
|
|
79
|
+
# Delete a thread
|
|
80
|
+
cumulus --delete old-project
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
## MCP Tools Available to Claude
|
|
84
|
+
|
|
85
|
+
When you chat through Cumulus, Claude has access to:
|
|
86
|
+
|
|
87
|
+
| Tool | Description |
|
|
88
|
+
| ------------------- | ---------------------------------------------------- |
|
|
89
|
+
| `search_history` | Find messages by keyword, semantic, or hybrid search |
|
|
90
|
+
| `read_messages` | Read a specific range of messages |
|
|
91
|
+
| `peek_recent` | See the last few messages |
|
|
92
|
+
| `get_history_stats` | Get count and token estimate |
|
|
93
|
+
| `sub_query` | Ask focused questions about history snippets |
|
|
94
|
+
| `get_summary` | Get auto-generated summaries of conversation history |
|
|
95
|
+
|
|
96
|
+
## Architecture
|
|
97
|
+
|
|
98
|
+
```
|
|
99
|
+
src/
|
|
100
|
+
├── lib/
|
|
101
|
+
│ └── history.ts # JSONL storage for conversation history
|
|
102
|
+
├── mcp/
|
|
103
|
+
│ ├── server.ts # MCP server exposing history tools
|
|
104
|
+
│ └── index.ts # MCP entry point
|
|
105
|
+
└── cli/
|
|
106
|
+
└── cumulus.ts # Main CLI, chat loop, Claude invocation
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
## Background
|
|
110
|
+
|
|
111
|
+
This project implements ideas from the paper ["Recursive Language Models"](https://arxiv.org/abs/...) which demonstrates that treating long prompts as external environment objects—rather than feeding them directly into the context window—dramatically improves performance on long-context tasks while maintaining reasonable costs.
|
|
112
|
+
|
|
113
|
+
Key insight: LLMs can programmatically examine, decompose, and query their context rather than processing it all at once. This enables effective reasoning over contexts 2+ orders of magnitude beyond the model's context window.
|
|
114
|
+
|
|
115
|
+
## Development
|
|
116
|
+
|
|
117
|
+
```bash
|
|
118
|
+
# Install dependencies
|
|
119
|
+
npm install
|
|
120
|
+
|
|
121
|
+
# Build
|
|
122
|
+
npm run build
|
|
123
|
+
|
|
124
|
+
# Run tests
|
|
125
|
+
npm test
|
|
126
|
+
|
|
127
|
+
# Lint
|
|
128
|
+
npm run lint
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
## Roadmap
|
|
132
|
+
|
|
133
|
+
**Phase 1 (MVP)**
|
|
134
|
+
|
|
135
|
+
- [x] Project setup with TypeScript/ESLint
|
|
136
|
+
- [x] HistoryStore for JSONL persistence
|
|
137
|
+
- [x] MCP server with history tools
|
|
138
|
+
- [x] CLI wrapper with pure RLM chat loop
|
|
139
|
+
- [x] Basic test suite
|
|
140
|
+
|
|
141
|
+
**Phase 2 (Enhancements)**
|
|
142
|
+
|
|
143
|
+
- [x] Semantic search with embeddings
|
|
144
|
+
- [x] Periodic summarization for very long histories
|
|
145
|
+
|
|
146
|
+
## License
|
|
147
|
+
|
|
148
|
+
MIT
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cumulus.d.ts","sourceRoot":"","sources":["../../src/cli/cumulus.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import * as fs from 'fs';
|
|
3
|
+
import { createRequire } from 'module';
|
|
4
|
+
import * as os from 'os';
|
|
5
|
+
import * as path from 'path';
|
|
6
|
+
import * as readline from 'readline';
|
|
7
|
+
import { Command } from 'commander';
|
|
8
|
+
const require = createRequire(import.meta.url);
|
|
9
|
+
const { version: pkgVersion } = require('../../package.json');
|
|
10
|
+
import { addAlwaysIncludeFile, removeAlwaysIncludeFile, listAlwaysIncludeFiles, resolveFilePath, } from '../lib/config.js';
|
|
11
|
+
import { HistoryStore } from '../lib/history.js';
|
|
12
|
+
import { migrateThread, needsMigration } from '../lib/migrate.js';
|
|
13
|
+
import { startTui } from '../tui/index.js';
|
|
14
|
+
const CUMULUS_DIR = path.join(os.homedir(), '.cumulus');
|
|
15
|
+
const THREADS_DIR = path.join(CUMULUS_DIR, 'threads');
|
|
16
|
+
function ensureDirectories() {
|
|
17
|
+
if (!fs.existsSync(THREADS_DIR)) {
|
|
18
|
+
fs.mkdirSync(THREADS_DIR, { recursive: true });
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
function getThreadPath(threadName) {
|
|
22
|
+
return path.join(THREADS_DIR, `${threadName}.jsonl`);
|
|
23
|
+
}
|
|
24
|
+
function validateThreadName(name) {
|
|
25
|
+
return /^[a-zA-Z0-9_-]+$/.test(name);
|
|
26
|
+
}
|
|
27
|
+
function startChatLoop(threadName, debugMode) {
|
|
28
|
+
ensureDirectories();
|
|
29
|
+
if (!validateThreadName(threadName)) {
|
|
30
|
+
console.error('Invalid thread name. Use only letters, numbers, hyphens, and underscores.');
|
|
31
|
+
process.exit(1);
|
|
32
|
+
}
|
|
33
|
+
// Launch the TUI
|
|
34
|
+
startTui({ threadName, debugMode });
|
|
35
|
+
}
|
|
36
|
+
async function listThreads() {
|
|
37
|
+
ensureDirectories();
|
|
38
|
+
const files = fs.readdirSync(THREADS_DIR).filter(f => f.endsWith('.jsonl'));
|
|
39
|
+
if (files.length === 0) {
|
|
40
|
+
console.log('No threads found.');
|
|
41
|
+
return;
|
|
42
|
+
}
|
|
43
|
+
console.log('\nThreads:\n');
|
|
44
|
+
for (const file of files) {
|
|
45
|
+
const threadName = file.replace('.jsonl', '');
|
|
46
|
+
const threadPath = path.join(THREADS_DIR, file);
|
|
47
|
+
const fileStat = fs.statSync(threadPath);
|
|
48
|
+
const store = new HistoryStore(threadPath);
|
|
49
|
+
const stats = await store.getStats();
|
|
50
|
+
const lastModified = fileStat.mtime.toLocaleDateString();
|
|
51
|
+
console.log(` ${threadName}`);
|
|
52
|
+
console.log(` Messages: ${stats.count}`);
|
|
53
|
+
console.log(` Tokens: ~${stats.totalTokens}`);
|
|
54
|
+
console.log(` Last active: ${lastModified}`);
|
|
55
|
+
console.log();
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
async function deleteThread(threadName) {
|
|
59
|
+
const threadPath = getThreadPath(threadName);
|
|
60
|
+
if (!fs.existsSync(threadPath)) {
|
|
61
|
+
console.log(`Thread "${threadName}" not found.`);
|
|
62
|
+
return;
|
|
63
|
+
}
|
|
64
|
+
const rl = readline.createInterface({
|
|
65
|
+
input: process.stdin,
|
|
66
|
+
output: process.stdout,
|
|
67
|
+
});
|
|
68
|
+
return new Promise(resolve => {
|
|
69
|
+
rl.question(`Delete thread "${threadName}"? (y/N) `, answer => {
|
|
70
|
+
rl.close();
|
|
71
|
+
if (answer.toLowerCase() === 'y') {
|
|
72
|
+
fs.unlinkSync(threadPath);
|
|
73
|
+
console.log(`Thread "${threadName}" deleted.`);
|
|
74
|
+
}
|
|
75
|
+
else {
|
|
76
|
+
console.log('Cancelled.');
|
|
77
|
+
}
|
|
78
|
+
resolve();
|
|
79
|
+
});
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
async function configList(threadName) {
|
|
83
|
+
const files = await listAlwaysIncludeFiles(threadName);
|
|
84
|
+
console.log('\nAlways-Include Files Configuration\n');
|
|
85
|
+
if (files.global.length > 0) {
|
|
86
|
+
console.log('Global (~/.cumulus/config.json):');
|
|
87
|
+
for (const file of files.global) {
|
|
88
|
+
const resolved = resolveFilePath(file, process.cwd());
|
|
89
|
+
console.log(` ${file}`);
|
|
90
|
+
if (resolved !== file) {
|
|
91
|
+
console.log(` -> ${resolved}`);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
console.log();
|
|
95
|
+
}
|
|
96
|
+
else {
|
|
97
|
+
console.log('Global: (none)\n');
|
|
98
|
+
}
|
|
99
|
+
if (threadName) {
|
|
100
|
+
if (files.thread.length > 0) {
|
|
101
|
+
console.log(`Thread "${threadName}":`);
|
|
102
|
+
for (const file of files.thread) {
|
|
103
|
+
const resolved = resolveFilePath(file, process.cwd());
|
|
104
|
+
console.log(` ${file}`);
|
|
105
|
+
if (resolved !== file) {
|
|
106
|
+
console.log(` -> ${resolved}`);
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
console.log();
|
|
110
|
+
}
|
|
111
|
+
else {
|
|
112
|
+
console.log(`Thread "${threadName}": (none)\n`);
|
|
113
|
+
}
|
|
114
|
+
if (files.merged.length > 0) {
|
|
115
|
+
console.log('Effective (merged):');
|
|
116
|
+
for (const file of files.merged) {
|
|
117
|
+
console.log(` ${file}`);
|
|
118
|
+
}
|
|
119
|
+
console.log();
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
async function configAdd(filePath, threadName) {
|
|
124
|
+
await addAlwaysIncludeFile(filePath, threadName);
|
|
125
|
+
const scope = threadName ? `thread "${threadName}"` : 'global';
|
|
126
|
+
console.log(`Added "${filePath}" to ${scope} always-include files.`);
|
|
127
|
+
}
|
|
128
|
+
async function configRemove(filePath, threadName) {
|
|
129
|
+
await removeAlwaysIncludeFile(filePath, threadName);
|
|
130
|
+
const scope = threadName ? `thread "${threadName}"` : 'global';
|
|
131
|
+
console.log(`Removed "${filePath}" from ${scope} always-include files.`);
|
|
132
|
+
}
|
|
133
|
+
async function migrate(threadName, options) {
|
|
134
|
+
const threadPath = getThreadPath(threadName);
|
|
135
|
+
if (!fs.existsSync(threadPath)) {
|
|
136
|
+
console.error(`Thread "${threadName}" not found.`);
|
|
137
|
+
process.exit(1);
|
|
138
|
+
}
|
|
139
|
+
if (options.check) {
|
|
140
|
+
// Just check status
|
|
141
|
+
const status = await needsMigration(threadPath);
|
|
142
|
+
console.log(`\nThread: ${threadName}`);
|
|
143
|
+
console.log(` Messages: ${status.messageCount}`);
|
|
144
|
+
console.log(` Embeddings: ${status.embeddingCount}/${status.messageCount}`);
|
|
145
|
+
console.log(` Needs embeddings: ${status.needsEmbeddings ? 'yes' : 'no'}`);
|
|
146
|
+
console.log(` Needs sessions: ${status.needsSessions ? 'yes' : 'no'}`);
|
|
147
|
+
if (!status.needsEmbeddings && !status.needsSessions) {
|
|
148
|
+
console.log('\n Thread is fully migrated.');
|
|
149
|
+
}
|
|
150
|
+
else {
|
|
151
|
+
console.log('\n Run `cumulus migrate ' + threadName + '` to migrate.');
|
|
152
|
+
}
|
|
153
|
+
return;
|
|
154
|
+
}
|
|
155
|
+
console.log(`\nMigrating thread: ${threadName}\n`);
|
|
156
|
+
const result = await migrateThread(threadPath, progress => {
|
|
157
|
+
const phases = {
|
|
158
|
+
loading: '[1/3]',
|
|
159
|
+
embeddings: '[2/3]',
|
|
160
|
+
sessions: '[3/3]',
|
|
161
|
+
done: '[done]',
|
|
162
|
+
};
|
|
163
|
+
const prefix = phases[progress.phase] || '';
|
|
164
|
+
process.stdout.write(`\r${prefix} ${progress.message}`.padEnd(60));
|
|
165
|
+
});
|
|
166
|
+
console.log('\n');
|
|
167
|
+
console.log('Migration complete:');
|
|
168
|
+
console.log(` Messages: ${result.messagesTotal}`);
|
|
169
|
+
console.log(` Embeddings generated: ${result.embeddingsGenerated}`);
|
|
170
|
+
console.log(` Session: ${result.sessionCreated ? `created with ${result.sessionExchanges} exchanges` : 'skipped (already exists)'}`);
|
|
171
|
+
if (result.errors.length > 0) {
|
|
172
|
+
console.log('\nErrors:');
|
|
173
|
+
for (const error of result.errors) {
|
|
174
|
+
console.log(` - ${error}`);
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
// Main program
|
|
179
|
+
const program = new Command();
|
|
180
|
+
program
|
|
181
|
+
.name('cumulus')
|
|
182
|
+
.description('RLM-based CLI chat wrapper for Claude with external history context')
|
|
183
|
+
.version(pkgVersion)
|
|
184
|
+
.argument('[thread]', 'Thread name to start or continue', 'default')
|
|
185
|
+
.option('-l, --list', 'List all threads')
|
|
186
|
+
.option('-d, --delete <name>', 'Delete a thread')
|
|
187
|
+
.option('--debug', 'Show context being sent to Claude with color-coded provenance')
|
|
188
|
+
.action(async (thread, options) => {
|
|
189
|
+
if (options.list) {
|
|
190
|
+
await listThreads();
|
|
191
|
+
}
|
|
192
|
+
else if (options.delete) {
|
|
193
|
+
await deleteThread(options.delete);
|
|
194
|
+
}
|
|
195
|
+
else {
|
|
196
|
+
startChatLoop(thread, options.debug ?? false);
|
|
197
|
+
}
|
|
198
|
+
});
|
|
199
|
+
// Config subcommand
|
|
200
|
+
const configCommand = program
|
|
201
|
+
.command('config')
|
|
202
|
+
.description('Manage always-include files configuration');
|
|
203
|
+
configCommand
|
|
204
|
+
.command('list')
|
|
205
|
+
.description('List always-include files')
|
|
206
|
+
.option('-t, --thread <name>', 'Show thread-specific config')
|
|
207
|
+
.action(async (options) => {
|
|
208
|
+
await configList(options.thread);
|
|
209
|
+
});
|
|
210
|
+
configCommand
|
|
211
|
+
.command('add <file>')
|
|
212
|
+
.description('Add a file to always-include list')
|
|
213
|
+
.option('-t, --thread <name>', 'Add to thread-specific config instead of global')
|
|
214
|
+
.action(async (file, options) => {
|
|
215
|
+
await configAdd(file, options.thread);
|
|
216
|
+
});
|
|
217
|
+
configCommand
|
|
218
|
+
.command('remove <file>')
|
|
219
|
+
.description('Remove a file from always-include list')
|
|
220
|
+
.option('-t, --thread <name>', 'Remove from thread-specific config instead of global')
|
|
221
|
+
.action(async (file, options) => {
|
|
222
|
+
await configRemove(file, options.thread);
|
|
223
|
+
});
|
|
224
|
+
// Migrate subcommand
|
|
225
|
+
program
|
|
226
|
+
.command('migrate <thread>')
|
|
227
|
+
.description('Migrate an old thread to support RAG features (embeddings + sessions)')
|
|
228
|
+
.option('-c, --check', 'Check migration status without migrating')
|
|
229
|
+
.action(async (thread, options) => {
|
|
230
|
+
await migrate(thread, options);
|
|
231
|
+
});
|
|
232
|
+
program.parse();
|
|
233
|
+
//# sourceMappingURL=cumulus.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cumulus.js","sourceRoot":"","sources":["../../src/cli/cumulus.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
export { HistoryStore } from './lib/history.js';
|
|
2
|
+
export type { Attachment, Message, HistoryStats } from './lib/history.js';
|
|
3
|
+
export { ContentStore } from './lib/content-store.js';
|
|
4
|
+
export type { ContentType, ContentSourceType, ContentChunk, StoredContentMeta, StoredContent, StoreOptions, SearchOptions, ContentSearchResult, } from './lib/content-store.js';
|
|
5
|
+
export { analyzeContent, generateHeuristicSummary, generateLLMSummary, generateSummary, detectContentType, } from './lib/content-detector.js';
|
|
6
|
+
export type { ContentAnalysis, SummaryOptions } from './lib/content-detector.js';
|
|
7
|
+
export { estimateTokens, ContextBudget } from './lib/context-budget.js';
|
|
8
|
+
export type { ContextBudgetConfig } from './lib/context-budget.js';
|
|
9
|
+
export { cosineSimilarity, embeddingsAvailable, generateMissingEmbeddings, getEmbeddingProvider, getEmbeddingsPath, loadEmbeddings, saveEmbeddings, } from './lib/embeddings.js';
|
|
10
|
+
export type { EmbeddingConfig, EmbeddingEntry, EmbeddingProvider, EmbeddingsFile, } from './lib/embeddings.js';
|
|
11
|
+
export { SessionManager } from './lib/session.js';
|
|
12
|
+
export type { SessionChunk, SessionSearchResult } from './lib/session.js';
|
|
13
|
+
export { retrieve, RETRIEVAL_BUDGET_FRACTION } from './lib/retriever.js';
|
|
14
|
+
export type { RetrievalResult, RetrieverOptions } from './lib/retriever.js';
|
|
15
|
+
export { StreamProcessor, shouldExternalizeUserInput, externalizeUserInput, } from './lib/stream-processor.js';
|
|
16
|
+
export type { StreamEventType, StreamMessage, ProcessedLine, StreamProcessorConfig, } from './lib/stream-processor.js';
|
|
17
|
+
export { loadGlobalConfig, loadThreadConfig, mergeConfigs, resolveFilePath, readAlwaysIncludeFiles, saveConfig, addAlwaysIncludeFile, removeAlwaysIncludeFile, listAlwaysIncludeFiles, } from './lib/config.js';
|
|
18
|
+
export type { CumulusConfig, AlwaysIncludeFile, AlwaysIncludeResult } from './lib/config.js';
|
|
19
|
+
export { processImagesInMessage, readClipboardImage } from './lib/image-utils.js';
|
|
20
|
+
export type { DetectedImage, ImageProcessingResult } from './lib/image-utils.js';
|
|
21
|
+
export { isGitRepo, captureSnapshot, restoreSnapshot } from './lib/snapshots.js';
|
|
22
|
+
export type { GitSnapshot, RestoreResult } from './lib/snapshots.js';
|
|
23
|
+
export { getSummary, getSummaryPath, loadSummaries, runSummarization, saveSummaries, shouldSummarize, generateChunkSummary, generateSessionSummary, } from './lib/summarizer.js';
|
|
24
|
+
export type { GetSummaryResult, Summary, SummaryFile } from './lib/summarizer.js';
|
|
25
|
+
export { executeRevert } from './lib/revert.js';
|
|
26
|
+
export type { RevertResult, RevertOptions } from './lib/revert.js';
|
|
27
|
+
export { startSharedMcpServer } from './mcp/shared-server.js';
|
|
28
|
+
export type { SharedMcpServerOptions, SharedMcpServerHandle } from './mcp/shared-server.js';
|
|
29
|
+
/** Absolute path to the lightweight stdio→HTTP proxy script for shared MCP server */
|
|
30
|
+
export declare function getProxyPath(): string;
|
|
31
|
+
/** Absolute path to the standalone MCP stdio server (full, non-shared) */
|
|
32
|
+
export declare function getMcpServerPath(): string;
|
|
33
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAChD,YAAY,EAAE,UAAU,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAG1E,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,YAAY,EACV,WAAW,EACX,iBAAiB,EACjB,YAAY,EACZ,iBAAiB,EACjB,aAAa,EACb,YAAY,EACZ,aAAa,EACb,mBAAmB,GACpB,MAAM,wBAAwB,CAAC;AAGhC,OAAO,EACL,cAAc,EACd,wBAAwB,EACxB,kBAAkB,EAClB,eAAe,EACf,iBAAiB,GAClB,MAAM,2BAA2B,CAAC;AACnC,YAAY,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,2BAA2B,CAAC;AAGjF,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,yBAAyB,CAAC;AACxE,YAAY,EAAE,mBAAmB,EAAE,MAAM,yBAAyB,CAAC;AAGnE,OAAO,EACL,gBAAgB,EAChB,mBAAmB,EACnB,yBAAyB,EACzB,oBAAoB,EACpB,iBAAiB,EACjB,cAAc,EACd,cAAc,GACf,MAAM,qBAAqB,CAAC;AAC7B,YAAY,EACV,eAAe,EACf,cAAc,EACd,iBAAiB,EACjB,cAAc,GACf,MAAM,qBAAqB,CAAC;AAG7B,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,YAAY,EAAE,YAAY,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAG1E,OAAO,EAAE,QAAQ,EAAE,yBAAyB,EAAE,MAAM,oBAAoB,CAAC;AACzE,YAAY,EAAE,eAAe,EAAE,gBAAgB,EAAE,MAAM,oBAAoB,CAAC;AAG5E,OAAO,EACL,eAAe,EACf,0BAA0B,EAC1B,oBAAoB,GACrB,MAAM,2BAA2B,CAAC;AACnC,YAAY,EACV,eAAe,EACf,aAAa,EACb,aAAa,EACb,qBAAqB,GACtB,MAAM,2BAA2B,CAAC;AAGnC,OAAO,EACL,gBAAgB,EAChB,gBAAgB,EAChB,YAAY,EACZ,eAAe,EACf,sBAAsB,EACtB,UAAU,EACV,oBAAoB,EACpB,uBAAuB,EACvB,sBAAsB,GACvB,MAAM,iBAAiB,CAAC;AACzB,YAAY,EAAE,aAAa,EAAE,iBAAiB,EAAE,mBAAmB,EAAE,MAAM,iBAAiB,CAAC;AAG7F,OAAO,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAClF,YAAY,EAAE,aAAa,EAAE,qBAAqB,EAAE,MAAM,sBAAsB,CAAC;AAGjF,OAAO,EAAE,SAAS,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AACjF,YAAY,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AAGrE,OAAO,EACL,UAAU,EACV,cAAc,EACd,aAAa,EACb,gBAAgB,EAChB,aAAa,EACb,eAAe,EACf,oBAAoB,EACpB,sBAAsB,GACvB,MAAM,qBAAqB,CAAC;AAC7B,YAAY,EAAE,gBAAgB,EAAE,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAGlF,OAAO,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAChD,YAAY,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAGnE,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAC9D,YAAY,EAAE,sBAAsB,EAAE,qBAAqB,EAAE,MAAM,wBAAwB,CAAC;AAQ5F,qFAAqF;AACrF,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAED,0EAA0E;AAC1E,wBAAgB,gBAAgB,IAAI,MAAM,CAEzC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
// Cumulus - RLM-based CLI chat wrapper for Claude
|
|
2
|
+
// Exports for library usage
|
|
3
|
+
// History
|
|
4
|
+
export { HistoryStore } from './lib/history.js';
|
|
5
|
+
// Content Store
|
|
6
|
+
export { ContentStore } from './lib/content-store.js';
|
|
7
|
+
// Content Detector
|
|
8
|
+
export { analyzeContent, generateHeuristicSummary, generateLLMSummary, generateSummary, detectContentType, } from './lib/content-detector.js';
|
|
9
|
+
// Context Budget
|
|
10
|
+
export { estimateTokens, ContextBudget } from './lib/context-budget.js';
|
|
11
|
+
// Embeddings
|
|
12
|
+
export { cosineSimilarity, embeddingsAvailable, generateMissingEmbeddings, getEmbeddingProvider, getEmbeddingsPath, loadEmbeddings, saveEmbeddings, } from './lib/embeddings.js';
|
|
13
|
+
// Session
|
|
14
|
+
export { SessionManager } from './lib/session.js';
|
|
15
|
+
// Retriever
|
|
16
|
+
export { retrieve, RETRIEVAL_BUDGET_FRACTION } from './lib/retriever.js';
|
|
17
|
+
// Stream Processor
|
|
18
|
+
export { StreamProcessor, shouldExternalizeUserInput, externalizeUserInput, } from './lib/stream-processor.js';
|
|
19
|
+
// Config
|
|
20
|
+
export { loadGlobalConfig, loadThreadConfig, mergeConfigs, resolveFilePath, readAlwaysIncludeFiles, saveConfig, addAlwaysIncludeFile, removeAlwaysIncludeFile, listAlwaysIncludeFiles, } from './lib/config.js';
|
|
21
|
+
// Image Utils
|
|
22
|
+
export { processImagesInMessage, readClipboardImage } from './lib/image-utils.js';
|
|
23
|
+
// Snapshots
|
|
24
|
+
export { isGitRepo, captureSnapshot, restoreSnapshot } from './lib/snapshots.js';
|
|
25
|
+
// Summarizer
|
|
26
|
+
export { getSummary, getSummaryPath, loadSummaries, runSummarization, saveSummaries, shouldSummarize, generateChunkSummary, generateSessionSummary, } from './lib/summarizer.js';
|
|
27
|
+
// Revert
|
|
28
|
+
export { executeRevert } from './lib/revert.js';
|
|
29
|
+
// MCP - Shared server for multi-agent setups
|
|
30
|
+
export { startSharedMcpServer } from './mcp/shared-server.js';
|
|
31
|
+
// MCP paths - for spawning subprocesses via --mcp-config
|
|
32
|
+
import { dirname, join } from 'path';
|
|
33
|
+
import { fileURLToPath } from 'url';
|
|
34
|
+
const __mcp_dirname = dirname(fileURLToPath(import.meta.url));
|
|
35
|
+
/** Absolute path to the lightweight stdio→HTTP proxy script for shared MCP server */
|
|
36
|
+
export function getProxyPath() {
|
|
37
|
+
return join(__mcp_dirname, 'mcp', 'proxy.js');
|
|
38
|
+
}
|
|
39
|
+
/** Absolute path to the standalone MCP stdio server (full, non-shared) */
|
|
40
|
+
export function getMcpServerPath() {
|
|
41
|
+
return join(__mcp_dirname, 'mcp', 'index.js');
|
|
42
|
+
}
|
|
43
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,kDAAkD;AAClD,4BAA4B;AAE5B,UAAU;AACV,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAGhD,gBAAgB;AAChB,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AAYtD,mBAAmB;AACnB,OAAO,EACL,cAAc,EACd,wBAAwB,EACxB,kBAAkB,EAClB,eAAe,EACf,iBAAiB,GAClB,MAAM,2BAA2B,CAAC;AAGnC,iBAAiB;AACjB,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,yBAAyB,CAAC;AAGxE,aAAa;AACb,OAAO,EACL,gBAAgB,EAChB,mBAAmB,EACnB,yBAAyB,EACzB,oBAAoB,EACpB,iBAAiB,EACjB,cAAc,EACd,cAAc,GACf,MAAM,qBAAqB,CAAC;AAQ7B,UAAU;AACV,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAGlD,YAAY;AACZ,OAAO,EAAE,QAAQ,EAAE,yBAAyB,EAAE,MAAM,oBAAoB,CAAC;AAGzE,mBAAmB;AACnB,OAAO,EACL,eAAe,EACf,0BAA0B,EAC1B,oBAAoB,GACrB,MAAM,2BAA2B,CAAC;AAQnC,SAAS;AACT,OAAO,EACL,gBAAgB,EAChB,gBAAgB,EAChB,YAAY,EACZ,eAAe,EACf,sBAAsB,EACtB,UAAU,EACV,oBAAoB,EACpB,uBAAuB,EACvB,sBAAsB,GACvB,MAAM,iBAAiB,CAAC;AAGzB,cAAc;AACd,OAAO,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAGlF,YAAY;AACZ,OAAO,EAAE,SAAS,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAGjF,aAAa;AACb,OAAO,EACL,UAAU,EACV,cAAc,EACd,aAAa,EACb,gBAAgB,EAChB,aAAa,EACb,eAAe,EACf,oBAAoB,EACpB,sBAAsB,GACvB,MAAM,qBAAqB,CAAC;AAG7B,SAAS;AACT,OAAO,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAC;AAGhD,6CAA6C;AAC7C,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAG9D,yDAAyD;AACzD,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AACrC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AAEpC,MAAM,aAAa,GAAG,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;AAE9D,qFAAqF;AACrF,MAAM,UAAU,YAAY;IAC1B,OAAO,IAAI,CAAC,aAAa,EAAE,KAAK,EAAE,UAAU,CAAC,CAAC;AAChD,CAAC;AAED,0EAA0E;AAC1E,MAAM,UAAU,gBAAgB;IAC9B,OAAO,IAAI,CAAC,aAAa,EAAE,KAAK,EAAE,UAAU,CAAC,CAAC;AAChD,CAAC"}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Configuration loading and always-include file management.
|
|
3
|
+
*
|
|
4
|
+
* Handles global and per-thread configuration, including reading
|
|
5
|
+
* files that should always be included in the context window.
|
|
6
|
+
*/
|
|
7
|
+
/** Configuration structure for Cumulus */
|
|
8
|
+
export interface CumulusConfig {
|
|
9
|
+
/** File paths to always include in context */
|
|
10
|
+
alwaysInclude?: string[];
|
|
11
|
+
/** Project directory for this thread (used by callers like Janus to set cwd) */
|
|
12
|
+
projectDir?: string;
|
|
13
|
+
}
|
|
14
|
+
/** Information about a single always-include file */
|
|
15
|
+
export interface AlwaysIncludeFile {
|
|
16
|
+
/** Original path from config */
|
|
17
|
+
path: string;
|
|
18
|
+
/** Absolute resolved path */
|
|
19
|
+
resolvedPath: string;
|
|
20
|
+
/** File contents (may be truncated) */
|
|
21
|
+
content: string;
|
|
22
|
+
/** Token count of content */
|
|
23
|
+
tokens: number;
|
|
24
|
+
/** Whether content was truncated */
|
|
25
|
+
truncated: boolean;
|
|
26
|
+
/** Error message if file couldn't be read */
|
|
27
|
+
error?: string;
|
|
28
|
+
}
|
|
29
|
+
/** Result of reading all always-include files */
|
|
30
|
+
export interface AlwaysIncludeResult {
|
|
31
|
+
/** Information about each file */
|
|
32
|
+
files: AlwaysIncludeFile[];
|
|
33
|
+
/** Total tokens across all files */
|
|
34
|
+
totalTokens: number;
|
|
35
|
+
/** Formatted context string for system prompt */
|
|
36
|
+
formattedContext: string;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Load the global configuration from ~/.cumulus/config.json
|
|
40
|
+
*/
|
|
41
|
+
export declare function loadGlobalConfig(): Promise<CumulusConfig>;
|
|
42
|
+
/**
|
|
43
|
+
* Load thread-specific configuration from ~/.cumulus/threads/{thread}.config.json
|
|
44
|
+
*/
|
|
45
|
+
export declare function loadThreadConfig(threadName: string): Promise<CumulusConfig>;
|
|
46
|
+
/**
|
|
47
|
+
* Merge global and thread configs. Thread config adds to global (doesn't override).
|
|
48
|
+
*/
|
|
49
|
+
export declare function mergeConfigs(global: CumulusConfig, thread: CumulusConfig): CumulusConfig;
|
|
50
|
+
/**
|
|
51
|
+
* Resolve a file path that may use ~ or be relative.
|
|
52
|
+
* @param filePath - The path from config (may use ~, be relative, or absolute)
|
|
53
|
+
* @param cwd - Current working directory for relative paths
|
|
54
|
+
*/
|
|
55
|
+
export declare function resolveFilePath(filePath: string, cwd: string): string;
|
|
56
|
+
/**
|
|
57
|
+
* Read and format all always-include files from config.
|
|
58
|
+
* @param config - Merged configuration
|
|
59
|
+
* @param cwd - Current working directory for relative paths
|
|
60
|
+
*/
|
|
61
|
+
export declare function readAlwaysIncludeFiles(config: CumulusConfig, cwd: string): Promise<AlwaysIncludeResult>;
|
|
62
|
+
/**
|
|
63
|
+
* Save configuration to a file.
|
|
64
|
+
*/
|
|
65
|
+
export declare function saveConfig(config: CumulusConfig, threadName?: string): Promise<void>;
|
|
66
|
+
/**
|
|
67
|
+
* Add a file to the always-include list.
|
|
68
|
+
* @param filePath - Path to add
|
|
69
|
+
* @param threadName - Thread name for thread-specific config, undefined for global
|
|
70
|
+
*/
|
|
71
|
+
export declare function addAlwaysIncludeFile(filePath: string, threadName?: string): Promise<void>;
|
|
72
|
+
/**
|
|
73
|
+
* Remove a file from the always-include list.
|
|
74
|
+
* @param filePath - Path to remove
|
|
75
|
+
* @param threadName - Thread name for thread-specific config, undefined for global
|
|
76
|
+
*/
|
|
77
|
+
export declare function removeAlwaysIncludeFile(filePath: string, threadName?: string): Promise<void>;
|
|
78
|
+
/**
|
|
79
|
+
* List all always-include files from config (without reading them).
|
|
80
|
+
*/
|
|
81
|
+
export declare function listAlwaysIncludeFiles(threadName?: string): Promise<{
|
|
82
|
+
global: string[];
|
|
83
|
+
thread: string[];
|
|
84
|
+
merged: string[];
|
|
85
|
+
}>;
|
|
86
|
+
//# sourceMappingURL=config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAWH,0CAA0C;AAC1C,MAAM,WAAW,aAAa;IAC5B,8CAA8C;IAC9C,aAAa,CAAC,EAAE,MAAM,EAAE,CAAC;IACzB,gFAAgF;IAChF,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,qDAAqD;AACrD,MAAM,WAAW,iBAAiB;IAChC,gCAAgC;IAChC,IAAI,EAAE,MAAM,CAAC;IACb,6BAA6B;IAC7B,YAAY,EAAE,MAAM,CAAC;IACrB,uCAAuC;IACvC,OAAO,EAAE,MAAM,CAAC;IAChB,6BAA6B;IAC7B,MAAM,EAAE,MAAM,CAAC;IACf,oCAAoC;IACpC,SAAS,EAAE,OAAO,CAAC;IACnB,6CAA6C;IAC7C,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,iDAAiD;AACjD,MAAM,WAAW,mBAAmB;IAClC,kCAAkC;IAClC,KAAK,EAAE,iBAAiB,EAAE,CAAC;IAC3B,oCAAoC;IACpC,WAAW,EAAE,MAAM,CAAC;IACpB,iDAAiD;IACjD,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED;;GAEG;AACH,wBAAsB,gBAAgB,IAAI,OAAO,CAAC,aAAa,CAAC,CAG/D;AAED;;GAEG;AACH,wBAAsB,gBAAgB,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,CAAC,CAGjF;AAkDD;;GAEG;AACH,wBAAgB,YAAY,CAAC,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,aAAa,GAAG,aAAa,CA0BxF;AAED;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAgBrE;AAED;;;;GAIG;AACH,wBAAsB,sBAAsB,CAC1C,MAAM,EAAE,aAAa,EACrB,GAAG,EAAE,MAAM,GACV,OAAO,CAAC,mBAAmB,CAAC,CAiD9B;AAyBD;;GAEG;AACH,wBAAsB,UAAU,CAAC,MAAM,EAAE,aAAa,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAY1F;AAED;;;;GAIG;AACH,wBAAsB,oBAAoB,CAAC,QAAQ,EAAE,MAAM,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAU/F;AAED;;;;GAIG;AACH,wBAAsB,uBAAuB,CAC3C,QAAQ,EAAE,MAAM,EAChB,UAAU,CAAC,EAAE,MAAM,GAClB,OAAO,CAAC,IAAI,CAAC,CAWf;AAED;;GAEG;AACH,wBAAsB,sBAAsB,CAAC,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;IACzE,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,MAAM,EAAE,MAAM,EAAE,CAAC;CAClB,CAAC,CAUD"}
|