@iflow-mcp/joungminsung-opendocuments 0.2.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 +144 -0
- package/dist/commands/ask.d.ts +3 -0
- package/dist/commands/ask.d.ts.map +1 -0
- package/dist/commands/ask.js +99 -0
- package/dist/commands/ask.js.map +1 -0
- package/dist/commands/auth.d.ts +3 -0
- package/dist/commands/auth.d.ts.map +1 -0
- package/dist/commands/auth.js +87 -0
- package/dist/commands/auth.js.map +1 -0
- package/dist/commands/completion.d.ts +3 -0
- package/dist/commands/completion.d.ts.map +1 -0
- package/dist/commands/completion.js +88 -0
- package/dist/commands/completion.js.map +1 -0
- package/dist/commands/config-cmd.d.ts +3 -0
- package/dist/commands/config-cmd.d.ts.map +1 -0
- package/dist/commands/config-cmd.js +61 -0
- package/dist/commands/config-cmd.js.map +1 -0
- package/dist/commands/connector.d.ts +3 -0
- package/dist/commands/connector.d.ts.map +1 -0
- package/dist/commands/connector.js +84 -0
- package/dist/commands/connector.js.map +1 -0
- package/dist/commands/doctor.d.ts +3 -0
- package/dist/commands/doctor.d.ts.map +1 -0
- package/dist/commands/doctor.js +151 -0
- package/dist/commands/doctor.js.map +1 -0
- package/dist/commands/document.d.ts +3 -0
- package/dist/commands/document.d.ts.map +1 -0
- package/dist/commands/document.js +78 -0
- package/dist/commands/document.js.map +1 -0
- package/dist/commands/export-cmd.d.ts +3 -0
- package/dist/commands/export-cmd.d.ts.map +1 -0
- package/dist/commands/export-cmd.js +44 -0
- package/dist/commands/export-cmd.js.map +1 -0
- package/dist/commands/import-cmd.d.ts +3 -0
- package/dist/commands/import-cmd.d.ts.map +1 -0
- package/dist/commands/import-cmd.js +39 -0
- package/dist/commands/import-cmd.js.map +1 -0
- package/dist/commands/index-cmd.d.ts +3 -0
- package/dist/commands/index-cmd.d.ts.map +1 -0
- package/dist/commands/index-cmd.js +76 -0
- package/dist/commands/index-cmd.js.map +1 -0
- package/dist/commands/init.d.ts +3 -0
- package/dist/commands/init.d.ts.map +1 -0
- package/dist/commands/init.js +408 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/plugin.d.ts +3 -0
- package/dist/commands/plugin.d.ts.map +1 -0
- package/dist/commands/plugin.js +296 -0
- package/dist/commands/plugin.js.map +1 -0
- package/dist/commands/search.d.ts +3 -0
- package/dist/commands/search.d.ts.map +1 -0
- package/dist/commands/search.js +40 -0
- package/dist/commands/search.js.map +1 -0
- package/dist/commands/start.d.ts +3 -0
- package/dist/commands/start.d.ts.map +1 -0
- package/dist/commands/start.js +120 -0
- package/dist/commands/start.js.map +1 -0
- package/dist/commands/stop.d.ts +3 -0
- package/dist/commands/stop.d.ts.map +1 -0
- package/dist/commands/stop.js +55 -0
- package/dist/commands/stop.js.map +1 -0
- package/dist/commands/upgrade.d.ts +3 -0
- package/dist/commands/upgrade.d.ts.map +1 -0
- package/dist/commands/upgrade.js +16 -0
- package/dist/commands/upgrade.js.map +1 -0
- package/dist/commands/workspace.d.ts +3 -0
- package/dist/commands/workspace.d.ts.map +1 -0
- package/dist/commands/workspace.js +85 -0
- package/dist/commands/workspace.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +43 -0
- package/dist/index.js.map +1 -0
- package/dist/utils/bootstrap.d.ts +4 -0
- package/dist/utils/bootstrap.d.ts.map +1 -0
- package/dist/utils/bootstrap.js +17 -0
- package/dist/utils/bootstrap.js.map +1 -0
- package/package.json +53 -0
|
@@ -0,0 +1,296 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { log } from 'opendocuments-core';
|
|
3
|
+
import chalk from 'chalk';
|
|
4
|
+
import { writeFileSync, mkdirSync, existsSync } from 'node:fs';
|
|
5
|
+
import { join } from 'node:path';
|
|
6
|
+
import { getContext, shutdownContext } from '../utils/bootstrap.js';
|
|
7
|
+
export function pluginCommand() {
|
|
8
|
+
const cmd = new Command('plugin')
|
|
9
|
+
.description('Manage and develop plugins');
|
|
10
|
+
cmd.command('list')
|
|
11
|
+
.description('List installed plugins with health status')
|
|
12
|
+
.action(async () => {
|
|
13
|
+
const ctx = await getContext();
|
|
14
|
+
try {
|
|
15
|
+
const plugins = ctx.registry.listAll();
|
|
16
|
+
if (plugins.length === 0) {
|
|
17
|
+
log.info('No plugins installed');
|
|
18
|
+
return;
|
|
19
|
+
}
|
|
20
|
+
log.heading('Installed Plugins');
|
|
21
|
+
for (const p of plugins) {
|
|
22
|
+
const plugin = ctx.registry.get(p.name);
|
|
23
|
+
let healthIcon = chalk.dim('[--]');
|
|
24
|
+
if (plugin?.healthCheck) {
|
|
25
|
+
try {
|
|
26
|
+
const h = await plugin.healthCheck();
|
|
27
|
+
healthIcon = h.healthy ? chalk.green('[ok]') : chalk.red('[!!]');
|
|
28
|
+
}
|
|
29
|
+
catch {
|
|
30
|
+
healthIcon = chalk.red('[!!]');
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
log.dim(` ${healthIcon} ${p.name.padEnd(40)} ${p.type.padEnd(12)} v${p.version}`);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
finally {
|
|
37
|
+
await shutdownContext();
|
|
38
|
+
}
|
|
39
|
+
});
|
|
40
|
+
cmd.command('create <name>')
|
|
41
|
+
.description('Scaffold a new plugin project')
|
|
42
|
+
.option('--type <type>', 'Plugin type: connector, parser, model, middleware', 'parser')
|
|
43
|
+
.action(async (name, opts) => {
|
|
44
|
+
const dir = join(process.cwd(), name);
|
|
45
|
+
if (existsSync(dir)) {
|
|
46
|
+
log.fail(`Directory ${name} already exists`);
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
log.heading('Plugin Scaffold');
|
|
50
|
+
log.info(`Creating ${opts.type} plugin: ${name}`);
|
|
51
|
+
mkdirSync(dir, { recursive: true });
|
|
52
|
+
mkdirSync(join(dir, 'src'));
|
|
53
|
+
mkdirSync(join(dir, 'tests'));
|
|
54
|
+
// package.json
|
|
55
|
+
writeFileSync(join(dir, 'package.json'), JSON.stringify({
|
|
56
|
+
name,
|
|
57
|
+
version: '0.1.0',
|
|
58
|
+
type: 'module',
|
|
59
|
+
main: './dist/index.js',
|
|
60
|
+
types: './dist/index.d.ts',
|
|
61
|
+
exports: { '.': { import: './dist/index.js', types: './dist/index.d.ts' } },
|
|
62
|
+
scripts: {
|
|
63
|
+
build: 'tsc',
|
|
64
|
+
test: 'vitest run',
|
|
65
|
+
typecheck: 'tsc --noEmit',
|
|
66
|
+
},
|
|
67
|
+
dependencies: { 'opendocuments-core': '^0.1.0' },
|
|
68
|
+
devDependencies: { typescript: '^5.5.0', vitest: '^2.1.0' },
|
|
69
|
+
peerDependencies: { 'opendocuments-core': '^0.1.0' },
|
|
70
|
+
}, null, 2) + '\n');
|
|
71
|
+
// tsconfig.json
|
|
72
|
+
writeFileSync(join(dir, 'tsconfig.json'), JSON.stringify({
|
|
73
|
+
compilerOptions: {
|
|
74
|
+
target: 'ES2022', module: 'ESNext', moduleResolution: 'bundler',
|
|
75
|
+
declaration: true, strict: true, esModuleInterop: true, skipLibCheck: true,
|
|
76
|
+
outDir: 'dist', rootDir: 'src',
|
|
77
|
+
},
|
|
78
|
+
include: ['src/**/*'],
|
|
79
|
+
exclude: ['tests/**/*', 'dist'],
|
|
80
|
+
}, null, 2) + '\n');
|
|
81
|
+
// vitest.config.ts
|
|
82
|
+
writeFileSync(join(dir, 'vitest.config.ts'), `import { defineConfig } from 'vitest/config'\nexport default defineConfig({ test: { globals: true, include: ['tests/**/*.test.ts'] } })\n`);
|
|
83
|
+
// Generate src/index.ts based on type
|
|
84
|
+
const templates = {
|
|
85
|
+
parser: `import type { ParserPlugin, RawDocument, ParsedChunk, PluginContext, HealthStatus } from 'opendocuments-core'
|
|
86
|
+
|
|
87
|
+
export class MyParser implements ParserPlugin {
|
|
88
|
+
name = '${name}'
|
|
89
|
+
type = 'parser' as const
|
|
90
|
+
version = '0.1.0'
|
|
91
|
+
coreVersion = '^0.1.0'
|
|
92
|
+
supportedTypes = ['.ext'] // TODO: set your file extensions
|
|
93
|
+
|
|
94
|
+
async setup(_ctx: PluginContext): Promise<void> {}
|
|
95
|
+
async healthCheck(): Promise<HealthStatus> { return { healthy: true } }
|
|
96
|
+
|
|
97
|
+
async *parse(raw: RawDocument): AsyncIterable<ParsedChunk> {
|
|
98
|
+
const content = typeof raw.content === 'string' ? raw.content : raw.content.toString('utf-8')
|
|
99
|
+
if (!content.trim()) return
|
|
100
|
+
yield { content: content.trim(), chunkType: 'semantic', headingHierarchy: [] }
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
export default MyParser
|
|
105
|
+
`,
|
|
106
|
+
connector: `import type { ConnectorPlugin, DiscoveredDocument, DocumentRef, RawDocument, PluginContext, HealthStatus } from 'opendocuments-core'
|
|
107
|
+
|
|
108
|
+
export class MyConnector implements ConnectorPlugin {
|
|
109
|
+
name = '${name}'
|
|
110
|
+
type = 'connector' as const
|
|
111
|
+
version = '0.1.0'
|
|
112
|
+
coreVersion = '^0.1.0'
|
|
113
|
+
|
|
114
|
+
async setup(_ctx: PluginContext): Promise<void> {}
|
|
115
|
+
async healthCheck(): Promise<HealthStatus> { return { healthy: true } }
|
|
116
|
+
|
|
117
|
+
async *discover(): AsyncIterable<DiscoveredDocument> {
|
|
118
|
+
// TODO: yield discovered documents
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
async fetch(ref: DocumentRef): Promise<RawDocument> {
|
|
122
|
+
// TODO: fetch document content
|
|
123
|
+
return { sourceId: ref.sourceId, title: ref.sourcePath, content: '' }
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
export default MyConnector
|
|
128
|
+
`,
|
|
129
|
+
model: `import type { ModelPlugin, PluginContext, HealthStatus, GenerateOpts, EmbeddingResult } from 'opendocuments-core'
|
|
130
|
+
|
|
131
|
+
export class MyModel implements ModelPlugin {
|
|
132
|
+
name = '${name}'
|
|
133
|
+
type = 'model' as const
|
|
134
|
+
version = '0.1.0'
|
|
135
|
+
coreVersion = '^0.1.0'
|
|
136
|
+
capabilities = { llm: false, embedding: false, reranker: false, vision: false }
|
|
137
|
+
|
|
138
|
+
async setup(_ctx: PluginContext): Promise<void> {}
|
|
139
|
+
async healthCheck(): Promise<HealthStatus> { return { healthy: true } }
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
export default MyModel
|
|
143
|
+
`,
|
|
144
|
+
middleware: `import type { MiddlewarePlugin, PluginContext, HealthStatus, PipelineStage } from 'opendocuments-core'
|
|
145
|
+
|
|
146
|
+
export class MyMiddleware implements MiddlewarePlugin {
|
|
147
|
+
name = '${name}'
|
|
148
|
+
type = 'middleware' as const
|
|
149
|
+
version = '0.1.0'
|
|
150
|
+
coreVersion = '^0.1.0'
|
|
151
|
+
hooks = [
|
|
152
|
+
{
|
|
153
|
+
stage: 'after:parse' as PipelineStage,
|
|
154
|
+
handler: async (data: unknown) => {
|
|
155
|
+
// TODO: process data
|
|
156
|
+
return data
|
|
157
|
+
},
|
|
158
|
+
},
|
|
159
|
+
]
|
|
160
|
+
|
|
161
|
+
async setup(_ctx: PluginContext): Promise<void> {}
|
|
162
|
+
async healthCheck(): Promise<HealthStatus> { return { healthy: true } }
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
export default MyMiddleware
|
|
166
|
+
`,
|
|
167
|
+
};
|
|
168
|
+
writeFileSync(join(dir, 'src', 'index.ts'), templates[opts.type] || templates.parser);
|
|
169
|
+
// Generate test
|
|
170
|
+
writeFileSync(join(dir, 'tests', 'index.test.ts'), `import { describe, it, expect } from 'vitest'
|
|
171
|
+
// Note: .js extension is resolved to .ts by vitest's TypeScript support
|
|
172
|
+
import Plugin from '../src/index.js'
|
|
173
|
+
|
|
174
|
+
describe('${name}', () => {
|
|
175
|
+
it('has correct metadata', () => {
|
|
176
|
+
const plugin = typeof Plugin === 'function' ? new Plugin() : Plugin
|
|
177
|
+
expect(plugin.name).toBe('${name}')
|
|
178
|
+
expect(plugin.type).toBe('${opts.type}')
|
|
179
|
+
})
|
|
180
|
+
|
|
181
|
+
it('reports healthy', async () => {
|
|
182
|
+
const plugin = typeof Plugin === 'function' ? new Plugin() : Plugin
|
|
183
|
+
if (plugin.setup) await plugin.setup({ config: {}, dataDir: '/tmp', log: console } as any)
|
|
184
|
+
if (plugin.healthCheck) {
|
|
185
|
+
const h = await plugin.healthCheck()
|
|
186
|
+
expect(h.healthy).toBe(true)
|
|
187
|
+
}
|
|
188
|
+
})
|
|
189
|
+
})
|
|
190
|
+
`);
|
|
191
|
+
// README
|
|
192
|
+
writeFileSync(join(dir, 'README.md'), `# ${name}\n\nOpenDocuments ${opts.type} plugin.\n\n## Development\n\n\`\`\`bash\nnpm install\nnpm run build\nnpm run test\n\`\`\`\n`);
|
|
193
|
+
log.ok(`Created ${dir}/`);
|
|
194
|
+
log.arrow(`cd ${name} && npm install && npm run test`);
|
|
195
|
+
});
|
|
196
|
+
cmd.command('publish')
|
|
197
|
+
.description('Publish plugin to npm')
|
|
198
|
+
.action(async () => {
|
|
199
|
+
const { execSync } = await import('node:child_process');
|
|
200
|
+
log.heading('Publishing Plugin');
|
|
201
|
+
try {
|
|
202
|
+
execSync('npm publish --access public', { stdio: 'inherit' });
|
|
203
|
+
log.ok('Published successfully');
|
|
204
|
+
}
|
|
205
|
+
catch {
|
|
206
|
+
log.fail('Publish failed. Check npm login and package.json');
|
|
207
|
+
}
|
|
208
|
+
});
|
|
209
|
+
cmd.command('search <query>')
|
|
210
|
+
.description('Search for OpenDocuments plugins on npm')
|
|
211
|
+
.action(async (query) => {
|
|
212
|
+
const { execSync } = await import('node:child_process');
|
|
213
|
+
try {
|
|
214
|
+
const result = execSync(`npm search opendocuments-plugin ${query} --json 2>/dev/null || echo "[]"`, { encoding: 'utf-8' });
|
|
215
|
+
const packages = JSON.parse(result);
|
|
216
|
+
if (packages.length === 0) {
|
|
217
|
+
log.info('No plugins found');
|
|
218
|
+
return;
|
|
219
|
+
}
|
|
220
|
+
log.heading(`Search Results (${packages.length})`);
|
|
221
|
+
for (const pkg of packages.slice(0, 10)) {
|
|
222
|
+
log.ok(`${pkg.name.padEnd(40)} ${pkg.description || ''}`);
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
catch {
|
|
226
|
+
log.info('No plugins found');
|
|
227
|
+
}
|
|
228
|
+
});
|
|
229
|
+
cmd.command('test')
|
|
230
|
+
.description('Run plugin tests')
|
|
231
|
+
.action(async () => {
|
|
232
|
+
const { execSync } = await import('node:child_process');
|
|
233
|
+
try {
|
|
234
|
+
execSync('npx vitest run', { stdio: 'inherit' });
|
|
235
|
+
}
|
|
236
|
+
catch {
|
|
237
|
+
process.exit(1);
|
|
238
|
+
}
|
|
239
|
+
});
|
|
240
|
+
cmd.command('dev')
|
|
241
|
+
.description('Start plugin dev mode (watch)')
|
|
242
|
+
.action(async () => {
|
|
243
|
+
const { execSync } = await import('node:child_process');
|
|
244
|
+
try {
|
|
245
|
+
execSync('npx tsc --watch', { stdio: 'inherit' });
|
|
246
|
+
}
|
|
247
|
+
catch { }
|
|
248
|
+
});
|
|
249
|
+
cmd.command('add <name>').description('Install a plugin').action(async (name) => {
|
|
250
|
+
const { execSync } = await import('node:child_process');
|
|
251
|
+
log.wait(`Installing ${name}...`);
|
|
252
|
+
try {
|
|
253
|
+
execSync(`npm install ${name}`, { stdio: 'inherit' });
|
|
254
|
+
log.ok(`${name} installed. Restart server to activate.`);
|
|
255
|
+
}
|
|
256
|
+
catch {
|
|
257
|
+
log.fail(`Failed to install ${name}`);
|
|
258
|
+
}
|
|
259
|
+
});
|
|
260
|
+
cmd.command('remove <name>').description('Remove a plugin').action(async (name) => {
|
|
261
|
+
const { execSync } = await import('node:child_process');
|
|
262
|
+
log.wait(`Removing ${name}...`);
|
|
263
|
+
try {
|
|
264
|
+
execSync(`npm uninstall ${name}`, { stdio: 'inherit' });
|
|
265
|
+
log.ok(`${name} removed. Restart server to apply.`);
|
|
266
|
+
}
|
|
267
|
+
catch {
|
|
268
|
+
log.fail(`Failed to remove ${name}`);
|
|
269
|
+
}
|
|
270
|
+
});
|
|
271
|
+
cmd.command('update [name]').description('Update plugins').action(async (name) => {
|
|
272
|
+
const { execSync } = await import('node:child_process');
|
|
273
|
+
if (name) {
|
|
274
|
+
log.wait(`Updating ${name}...`);
|
|
275
|
+
try {
|
|
276
|
+
execSync(`npm update ${name}`, { stdio: 'inherit' });
|
|
277
|
+
log.ok('Updated');
|
|
278
|
+
}
|
|
279
|
+
catch {
|
|
280
|
+
log.fail('Failed');
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
else {
|
|
284
|
+
log.wait('Updating all plugins...');
|
|
285
|
+
try {
|
|
286
|
+
execSync('npm update', { stdio: 'inherit' });
|
|
287
|
+
log.ok('All plugins updated');
|
|
288
|
+
}
|
|
289
|
+
catch {
|
|
290
|
+
log.fail('Failed');
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
});
|
|
294
|
+
return cmd;
|
|
295
|
+
}
|
|
296
|
+
//# sourceMappingURL=plugin.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugin.js","sourceRoot":"","sources":["../../src/commands/plugin.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"search.d.ts","sourceRoot":"","sources":["../../src/commands/search.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAKnC,wBAAgB,aAAa,YA4B5B"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { log } from 'opendocuments-core';
|
|
3
|
+
import chalk from 'chalk';
|
|
4
|
+
import { getContext, shutdownContext } from '../utils/bootstrap.js';
|
|
5
|
+
export function searchCommand() {
|
|
6
|
+
return new Command('search')
|
|
7
|
+
.description('Search indexed documents (no LLM generation)')
|
|
8
|
+
.argument('<query>', 'Search query')
|
|
9
|
+
.option('--top <n>', 'Number of results', '5')
|
|
10
|
+
.option('--type <type>', 'Chunk type filter: semantic, code-ast, table')
|
|
11
|
+
.action(async (query, opts) => {
|
|
12
|
+
const ctx = await getContext();
|
|
13
|
+
try {
|
|
14
|
+
const embedder = ctx.registry.getModels().find(m => m.capabilities.embedding);
|
|
15
|
+
if (!embedder?.embed) {
|
|
16
|
+
log.fail('No embedding model configured');
|
|
17
|
+
return;
|
|
18
|
+
}
|
|
19
|
+
const embedResult = await embedder.embed([query]);
|
|
20
|
+
const results = await ctx.store.searchChunks(embedResult.dense[0], parseInt(opts.top));
|
|
21
|
+
if (results.length === 0) {
|
|
22
|
+
log.info('No results found');
|
|
23
|
+
return;
|
|
24
|
+
}
|
|
25
|
+
log.heading(`Search Results (${results.length})`);
|
|
26
|
+
for (const [i, r] of results.entries()) {
|
|
27
|
+
console.log(chalk.cyan(` ${i + 1}.`), chalk.dim(`[${(r.score * 100).toFixed(0)}%]`), chalk.white(r.sourcePath));
|
|
28
|
+
if (r.headingHierarchy.length > 0) {
|
|
29
|
+
log.dim(` ${r.headingHierarchy.join(' > ')}`);
|
|
30
|
+
}
|
|
31
|
+
log.dim(` ${r.content.substring(0, 150).replace(/\n/g, ' ')}...`);
|
|
32
|
+
log.blank();
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
finally {
|
|
36
|
+
await shutdownContext();
|
|
37
|
+
}
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=search.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"search.js","sourceRoot":"","sources":["../../src/commands/search.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,GAAG,EAAE,MAAM,oBAAoB,CAAA;AACxC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAA;AAEnE,MAAM,UAAU,aAAa;IAC3B,OAAO,IAAI,OAAO,CAAC,QAAQ,CAAC;SACzB,WAAW,CAAC,8CAA8C,CAAC;SAC3D,QAAQ,CAAC,SAAS,EAAE,cAAc,CAAC;SACnC,MAAM,CAAC,WAAW,EAAE,mBAAmB,EAAE,GAAG,CAAC;SAC7C,MAAM,CAAC,eAAe,EAAE,8CAA8C,CAAC;SACvE,MAAM,CAAC,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,EAAE;QAC5B,MAAM,GAAG,GAAG,MAAM,UAAU,EAAE,CAAA;QAC9B,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,GAAG,CAAC,QAAQ,CAAC,SAAS,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,YAAY,CAAC,SAAS,CAAC,CAAA;YAC7E,IAAI,CAAC,QAAQ,EAAE,KAAK,EAAE,CAAC;gBAAC,GAAG,CAAC,IAAI,CAAC,+BAA+B,CAAC,CAAC;gBAAC,OAAM;YAAC,CAAC;YAE3E,MAAM,WAAW,GAAG,MAAM,QAAQ,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,CAAA;YACjD,MAAM,OAAO,GAAG,MAAM,GAAG,CAAC,KAAK,CAAC,YAAY,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,QAAQ,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,CAAA;YAEtF,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBAAC,GAAG,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;gBAAC,OAAM;YAAC,CAAC;YAElE,GAAG,CAAC,OAAO,CAAC,mBAAmB,OAAO,CAAC,MAAM,GAAG,CAAC,CAAA;YACjD,KAAK,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,IAAI,OAAO,CAAC,OAAO,EAAE,EAAE,CAAC;gBACvC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAA;gBAChH,IAAI,CAAC,CAAC,gBAAgB,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;oBAClC,GAAG,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC,gBAAgB,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,CAAA;gBACnD,CAAC;gBACD,GAAG,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,KAAK,CAAC,CAAA;gBACrE,GAAG,CAAC,KAAK,EAAE,CAAA;YACb,CAAC;QACH,CAAC;gBAAS,CAAC;YAAC,MAAM,eAAe,EAAE,CAAA;QAAC,CAAC;IACvC,CAAC,CAAC,CAAA;AACN,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"start.d.ts","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAiDnC,wBAAgB,YAAY,YAmE3B"}
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { log } from 'opendocuments-core';
|
|
3
|
+
import { bootstrap, createApp, startMCPServer } from 'opendocuments-server';
|
|
4
|
+
import { serve } from '@hono/node-server';
|
|
5
|
+
import { resolve, dirname, join } from 'node:path';
|
|
6
|
+
import { homedir } from 'node:os';
|
|
7
|
+
import { existsSync, writeFileSync, mkdirSync, unlinkSync } from 'node:fs';
|
|
8
|
+
import { fileURLToPath } from 'node:url';
|
|
9
|
+
function findWebDistDir() {
|
|
10
|
+
// Try monorepo path: packages/web/dist relative to cwd
|
|
11
|
+
const monorepoPath = resolve(process.cwd(), 'packages/web/dist');
|
|
12
|
+
if (existsSync(monorepoPath))
|
|
13
|
+
return monorepoPath;
|
|
14
|
+
// Try relative to this file's location (dist/commands/start.js -> ../../../web/dist)
|
|
15
|
+
try {
|
|
16
|
+
const thisDir = dirname(fileURLToPath(import.meta.url));
|
|
17
|
+
const relativePath = resolve(thisDir, '../../../web/dist');
|
|
18
|
+
if (existsSync(relativePath))
|
|
19
|
+
return relativePath;
|
|
20
|
+
}
|
|
21
|
+
catch { }
|
|
22
|
+
// Try to find via require.resolve for npm-installed case
|
|
23
|
+
try {
|
|
24
|
+
// @ts-ignore
|
|
25
|
+
const webPkg = require.resolve('@opendocuments/web/package.json');
|
|
26
|
+
const webDist = resolve(dirname(webPkg), 'dist');
|
|
27
|
+
if (existsSync(webDist))
|
|
28
|
+
return webDist;
|
|
29
|
+
}
|
|
30
|
+
catch { }
|
|
31
|
+
return null;
|
|
32
|
+
}
|
|
33
|
+
function printBootstrapHelp(errorMessage) {
|
|
34
|
+
const msg = errorMessage.toLowerCase();
|
|
35
|
+
log.blank();
|
|
36
|
+
log.info('Troubleshooting suggestions:');
|
|
37
|
+
if (msg.includes('econnrefused') || msg.includes('connect') || msg.includes('ollama')) {
|
|
38
|
+
log.arrow('Ollama may not be running. Start it with: ollama serve');
|
|
39
|
+
log.arrow('Install Ollama from: https://ollama.com/download');
|
|
40
|
+
}
|
|
41
|
+
if (msg.includes('model') || msg.includes('not found')) {
|
|
42
|
+
log.arrow('The requested model may not be installed. Pull it with: ollama pull <model-name>');
|
|
43
|
+
}
|
|
44
|
+
if (msg.includes('config') || msg.includes('validation') || msg.includes('parse')) {
|
|
45
|
+
log.arrow('Check your configuration file for syntax errors or invalid values.');
|
|
46
|
+
}
|
|
47
|
+
log.arrow('Run diagnostics with: opendocuments doctor');
|
|
48
|
+
}
|
|
49
|
+
export function startCommand() {
|
|
50
|
+
return new Command('start')
|
|
51
|
+
.description('Start OpenDocuments server')
|
|
52
|
+
.option('-p, --port <port>', 'Port number', '3000')
|
|
53
|
+
.option('--mcp-only', 'Start MCP server only (stdio mode)')
|
|
54
|
+
.option('--no-web', 'Disable web UI static serving')
|
|
55
|
+
.action(async (opts) => {
|
|
56
|
+
log.heading('OpenDocuments Server');
|
|
57
|
+
if (opts.mcpOnly) {
|
|
58
|
+
log.wait('Starting MCP server (stdio mode)...');
|
|
59
|
+
let ctx;
|
|
60
|
+
try {
|
|
61
|
+
ctx = await bootstrap();
|
|
62
|
+
}
|
|
63
|
+
catch (err) {
|
|
64
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
65
|
+
log.fail(`Failed to bootstrap: ${message}`);
|
|
66
|
+
printBootstrapHelp(message);
|
|
67
|
+
process.exit(1);
|
|
68
|
+
}
|
|
69
|
+
await startMCPServer(ctx);
|
|
70
|
+
return;
|
|
71
|
+
}
|
|
72
|
+
log.wait('Bootstrapping...');
|
|
73
|
+
let ctx;
|
|
74
|
+
try {
|
|
75
|
+
ctx = await bootstrap();
|
|
76
|
+
}
|
|
77
|
+
catch (err) {
|
|
78
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
79
|
+
log.fail(`Failed to bootstrap: ${message}`);
|
|
80
|
+
printBootstrapHelp(message);
|
|
81
|
+
process.exit(1);
|
|
82
|
+
}
|
|
83
|
+
// Find web UI dist directory (unless disabled)
|
|
84
|
+
let webDir;
|
|
85
|
+
if (opts.web !== false) {
|
|
86
|
+
const found = findWebDistDir();
|
|
87
|
+
webDir = found ?? undefined;
|
|
88
|
+
}
|
|
89
|
+
const app = createApp(ctx, { webDir });
|
|
90
|
+
const port = parseInt(opts.port);
|
|
91
|
+
// Write PID file for `opendocuments stop`
|
|
92
|
+
const pidDir = join(homedir(), '.opendocuments');
|
|
93
|
+
const pidFile = join(pidDir, 'server.pid');
|
|
94
|
+
mkdirSync(pidDir, { recursive: true });
|
|
95
|
+
writeFileSync(pidFile, String(process.pid));
|
|
96
|
+
serve({ fetch: app.fetch, port }, () => {
|
|
97
|
+
log.ok(`Server running at http://localhost:${port}`);
|
|
98
|
+
log.arrow(`API: http://localhost:${port}/api/v1`);
|
|
99
|
+
if (webDir) {
|
|
100
|
+
log.ok(`Web UI: http://localhost:${port}`);
|
|
101
|
+
}
|
|
102
|
+
else {
|
|
103
|
+
log.info('Web UI not found (run: cd packages/web && npm run build)');
|
|
104
|
+
}
|
|
105
|
+
log.dim('Press Ctrl+C to stop');
|
|
106
|
+
});
|
|
107
|
+
process.on('SIGINT', async () => {
|
|
108
|
+
log.blank();
|
|
109
|
+
log.wait('Shutting down...');
|
|
110
|
+
try {
|
|
111
|
+
unlinkSync(pidFile);
|
|
112
|
+
}
|
|
113
|
+
catch { }
|
|
114
|
+
await ctx.shutdown();
|
|
115
|
+
log.ok('Goodbye');
|
|
116
|
+
process.exit(0);
|
|
117
|
+
});
|
|
118
|
+
});
|
|
119
|
+
}
|
|
120
|
+
//# sourceMappingURL=start.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"start.js","sourceRoot":"","sources":["../../src/commands/start.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stop.d.ts","sourceRoot":"","sources":["../../src/commands/stop.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAMnC,wBAAgB,WAAW,YAwC1B"}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { log } from 'opendocuments-core';
|
|
3
|
+
import { readFileSync, existsSync, unlinkSync } from 'node:fs';
|
|
4
|
+
import { join } from 'node:path';
|
|
5
|
+
import { homedir } from 'node:os';
|
|
6
|
+
export function stopCommand() {
|
|
7
|
+
return new Command('stop')
|
|
8
|
+
.description('Stop the OpenDocuments server')
|
|
9
|
+
.action(async () => {
|
|
10
|
+
const pidFile = join(homedir(), '.opendocuments', 'server.pid');
|
|
11
|
+
if (!existsSync(pidFile)) {
|
|
12
|
+
log.info('No running server found (no PID file at ' + pidFile + ')');
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
let pid;
|
|
16
|
+
try {
|
|
17
|
+
pid = parseInt(readFileSync(pidFile, 'utf-8').trim());
|
|
18
|
+
if (isNaN(pid)) {
|
|
19
|
+
log.fail('Invalid PID file content');
|
|
20
|
+
unlinkSync(pidFile);
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
catch (err) {
|
|
25
|
+
log.fail(`Failed to read PID file: ${err.message}`);
|
|
26
|
+
return;
|
|
27
|
+
}
|
|
28
|
+
try {
|
|
29
|
+
// Check if process exists first
|
|
30
|
+
process.kill(pid, 0);
|
|
31
|
+
}
|
|
32
|
+
catch {
|
|
33
|
+
log.info(`Server process (PID ${pid}) is not running. Cleaning up PID file.`);
|
|
34
|
+
try {
|
|
35
|
+
unlinkSync(pidFile);
|
|
36
|
+
}
|
|
37
|
+
catch { }
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
try {
|
|
41
|
+
process.kill(pid, 'SIGTERM');
|
|
42
|
+
log.ok(`Server (PID ${pid}) stopped`);
|
|
43
|
+
}
|
|
44
|
+
catch (err) {
|
|
45
|
+
log.fail(`Failed to stop server: ${err.message}`);
|
|
46
|
+
}
|
|
47
|
+
finally {
|
|
48
|
+
try {
|
|
49
|
+
unlinkSync(pidFile);
|
|
50
|
+
}
|
|
51
|
+
catch { }
|
|
52
|
+
}
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
//# sourceMappingURL=stop.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stop.js","sourceRoot":"","sources":["../../src/commands/stop.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,GAAG,EAAE,MAAM,oBAAoB,CAAA;AACxC,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,SAAS,CAAA;AAC9D,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAChC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAA;AAEjC,MAAM,UAAU,WAAW;IACzB,OAAO,IAAI,OAAO,CAAC,MAAM,CAAC;SACvB,WAAW,CAAC,+BAA+B,CAAC;SAC5C,MAAM,CAAC,KAAK,IAAI,EAAE;QACjB,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,EAAE,EAAE,gBAAgB,EAAE,YAAY,CAAC,CAAA;QAC/D,IAAI,CAAC,UAAU,CAAC,OAAO,CAAC,EAAE,CAAC;YACzB,GAAG,CAAC,IAAI,CAAC,0CAA0C,GAAG,OAAO,GAAG,GAAG,CAAC,CAAA;YACpE,OAAM;QACR,CAAC;QACD,IAAI,GAAW,CAAA;QACf,IAAI,CAAC;YACH,GAAG,GAAG,QAAQ,CAAC,YAAY,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC,IAAI,EAAE,CAAC,CAAA;YACrD,IAAI,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC;gBACf,GAAG,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAA;gBACpC,UAAU,CAAC,OAAO,CAAC,CAAA;gBACnB,OAAM;YACR,CAAC;QACH,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,GAAG,CAAC,IAAI,CAAC,4BAA6B,GAAa,CAAC,OAAO,EAAE,CAAC,CAAA;YAC9D,OAAM;QACR,CAAC;QAED,IAAI,CAAC;YACH,gCAAgC;YAChC,OAAO,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,CAAA;QACtB,CAAC;QAAC,MAAM,CAAC;YACP,GAAG,CAAC,IAAI,CAAC,uBAAuB,GAAG,yCAAyC,CAAC,CAAA;YAC7E,IAAI,CAAC;gBAAC,UAAU,CAAC,OAAO,CAAC,CAAA;YAAC,CAAC;YAAC,MAAM,CAAC,CAAA,CAAC;YACpC,OAAM;QACR,CAAC;QAED,IAAI,CAAC;YACH,OAAO,CAAC,IAAI,CAAC,GAAG,EAAE,SAAS,CAAC,CAAA;YAC5B,GAAG,CAAC,EAAE,CAAC,eAAe,GAAG,WAAW,CAAC,CAAA;QACvC,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,GAAG,CAAC,IAAI,CAAC,0BAA2B,GAAa,CAAC,OAAO,EAAE,CAAC,CAAA;QAC9D,CAAC;gBAAS,CAAC;YACT,IAAI,CAAC;gBAAC,UAAU,CAAC,OAAO,CAAC,CAAA;YAAC,CAAC;YAAC,MAAM,CAAC,CAAA,CAAC;QACtC,CAAC;IACH,CAAC,CAAC,CAAA;AACN,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"upgrade.d.ts","sourceRoot":"","sources":["../../src/commands/upgrade.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAGnC,wBAAgB,cAAc,YAW7B"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { Command } from 'commander';
|
|
2
|
+
import { log } from 'opendocuments-core';
|
|
3
|
+
export function upgradeCommand() {
|
|
4
|
+
return new Command('upgrade').description('Upgrade OpenDocuments to latest version').action(async () => {
|
|
5
|
+
const { execSync } = await import('node:child_process');
|
|
6
|
+
log.heading('Upgrading OpenDocuments');
|
|
7
|
+
try {
|
|
8
|
+
execSync('npm install -g @opendocuments/cli@latest', { stdio: 'inherit' });
|
|
9
|
+
log.ok('Upgrade complete');
|
|
10
|
+
}
|
|
11
|
+
catch (err) {
|
|
12
|
+
log.fail('Upgrade failed. Try: npm install -g @opendocuments/cli@latest');
|
|
13
|
+
}
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
//# sourceMappingURL=upgrade.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"upgrade.js","sourceRoot":"","sources":["../../src/commands/upgrade.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,GAAG,EAAE,MAAM,oBAAoB,CAAA;AAExC,MAAM,UAAU,cAAc;IAC5B,OAAO,IAAI,OAAO,CAAC,SAAS,CAAC,CAAC,WAAW,CAAC,yCAAyC,CAAC,CAAC,MAAM,CAAC,KAAK,IAAI,EAAE;QACrG,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,oBAAoB,CAAC,CAAA;QACvD,GAAG,CAAC,OAAO,CAAC,yBAAyB,CAAC,CAAA;QACtC,IAAI,CAAC;YACH,QAAQ,CAAC,0CAA0C,EAAE,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,CAAA;YAC1E,GAAG,CAAC,EAAE,CAAC,kBAAkB,CAAC,CAAA;QAC5B,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,GAAG,CAAC,IAAI,CAAC,+DAA+D,CAAC,CAAA;QAC3E,CAAC;IACH,CAAC,CAAC,CAAA;AACJ,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"workspace.d.ts","sourceRoot":"","sources":["../../src/commands/workspace.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAoBnC,wBAAgB,gBAAgB,YA8C/B"}
|