@doquflow/cli 1.3.1 → 1.5.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.
@@ -202,6 +202,7 @@ async function run(opts = {}) {
202
202
  const lintWikiTool = loadTool('lint-wiki', 'lintWiki');
203
203
  const queryWikiTool = loadTool('query-wiki', 'queryWiki');
204
204
  const wikiSearchTool = loadTool('wiki-search', 'wikiSearch');
205
+ const buildGraphTool = loadTool('build-graph', 'buildGraph');
205
206
  // ── 3. Express app ──────────────────────────────────────────────────────
206
207
  const app = (0, express_1.default)();
207
208
  app.use((0, cors_1.default)());
@@ -296,6 +297,17 @@ async function run(opts = {}) {
296
297
  }
297
298
  return res.status(404).json({ error: `Page not found: ${pageId}` });
298
299
  });
300
+ app.get('/api/graph', async (req, res) => {
301
+ const projectPath = req.query.path;
302
+ if (!projectPath)
303
+ return res.status(400).json({ error: 'path required' });
304
+ try {
305
+ return res.json(await buildGraphTool({ project_path: projectPath }));
306
+ }
307
+ catch (e) {
308
+ return res.status(500).json({ error: e.message });
309
+ }
310
+ });
299
311
  app.get('/api/health', async (req, res) => {
300
312
  const projectPath = req.query.path;
301
313
  if (!projectPath)
@@ -0,0 +1,114 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.run = run;
37
+ const child_process_1 = require("child_process");
38
+ const net = __importStar(require("net"));
39
+ // eslint-disable-next-line @typescript-eslint/no-var-requires
40
+ const { version: currentVersion } = require('../../package.json');
41
+ const PKG = '@doquflow/cli';
42
+ const DEFAULT_PORT = 48821;
43
+ function fetchLatestVersion() {
44
+ try {
45
+ const out = (0, child_process_1.execSync)(`npm view ${PKG} version`, { stdio: ['ignore', 'pipe', 'pipe'] })
46
+ .toString()
47
+ .trim();
48
+ if (!/^\d+\.\d+\.\d+/.test(out))
49
+ throw new Error(`unexpected npm output: ${out}`);
50
+ return out;
51
+ }
52
+ catch (e) {
53
+ throw new Error(`Could not fetch latest version from npm registry: ${e.message}`);
54
+ }
55
+ }
56
+ function compareSemver(a, b) {
57
+ const pa = a.split('.').map(n => parseInt(n, 10));
58
+ const pb = b.split('.').map(n => parseInt(n, 10));
59
+ for (let i = 0; i < 3; i++) {
60
+ if ((pa[i] ?? 0) > (pb[i] ?? 0))
61
+ return 1;
62
+ if ((pa[i] ?? 0) < (pb[i] ?? 0))
63
+ return -1;
64
+ }
65
+ return 0;
66
+ }
67
+ function isPortInUse(port) {
68
+ return new Promise(resolve => {
69
+ const sock = net.createConnection({ port, host: '127.0.0.1' });
70
+ sock.once('connect', () => { sock.end(); resolve(true); });
71
+ sock.once('error', () => resolve(false));
72
+ });
73
+ }
74
+ async function run(opts = {}) {
75
+ console.log(`DocuFlow update`);
76
+ console.log(` Current: ${currentVersion}`);
77
+ let latest;
78
+ try {
79
+ latest = fetchLatestVersion();
80
+ }
81
+ catch (e) {
82
+ console.error(`✗ ${e.message}`);
83
+ process.exit(1);
84
+ }
85
+ console.log(` Latest: ${latest}`);
86
+ const cmp = compareSemver(latest, currentVersion);
87
+ if (opts.check) {
88
+ if (cmp > 0)
89
+ console.log(`\n→ Update available. Run \`docuflow update\` to install.`);
90
+ else
91
+ console.log(`\n✓ You are on the latest version.`);
92
+ return;
93
+ }
94
+ if (cmp <= 0 && !opts.force) {
95
+ console.log(`\n✓ Already on the latest version. Use --force to reinstall.`);
96
+ return;
97
+ }
98
+ console.log(`\nInstalling ${PKG}@${latest} globally…`);
99
+ const result = (0, child_process_1.spawnSync)('npm', ['install', '-g', `${PKG}@latest`], { stdio: 'inherit' });
100
+ if (result.status !== 0) {
101
+ console.error(`✗ npm install failed (exit ${result.status}). Try with sudo if this is a permissions issue.`);
102
+ process.exit(result.status ?? 1);
103
+ }
104
+ console.log(`\n✓ Updated to ${latest}.`);
105
+ console.log(` This refreshed the CLI, bundled UI (ui-dist), and the @doquflow/server dependency.`);
106
+ const stale = await isPortInUse(DEFAULT_PORT);
107
+ if (stale) {
108
+ console.log('');
109
+ console.log(`⚠ A DocuFlow server is still running on port ${DEFAULT_PORT} — it is the OLD version.`);
110
+ console.log(` Stop and restart it to use the new code:`);
111
+ console.log(` lsof -ti:${DEFAULT_PORT} | xargs kill`);
112
+ console.log(` docuflow ui`);
113
+ }
114
+ }
package/dist/index.js CHANGED
@@ -123,6 +123,13 @@ else if (cmd === 'review') {
123
123
  failOnCritical: hasFlag('--fail-on-critical'),
124
124
  quiet: hasFlag('--quiet', '-q'),
125
125
  }));
126
+ // ── update — reinstall latest @doquflow/cli globally ─────────────────────────
127
+ }
128
+ else if (cmd === 'update' || cmd === 'upgrade') {
129
+ Promise.resolve().then(() => __importStar(require('./commands/update'))).then(m => m.run({
130
+ check: hasFlag('--check'),
131
+ force: hasFlag('--force'),
132
+ }));
126
133
  }
127
134
  else {
128
135
  console.log(`DocuFlow v${version}`);
@@ -164,6 +171,10 @@ else {
164
171
  console.log(' review --ai Append Copilot AI review to deterministic findings');
165
172
  console.log(' review --fail-on-critical Exit 1 if critical findings are detected');
166
173
  console.log(' review --quiet Compact output for CI/scripting');
174
+ console.log(' update Reinstall latest @doquflow/cli globally (refreshes UI + server)');
175
+ console.log(' update --check Check whether a newer version is published (no install)');
176
+ console.log(' update --force Reinstall even when already on the latest version');
177
+ console.log(' upgrade Alias for "update"');
167
178
  console.log('');
168
179
  console.log('Options:');
169
180
  console.log(' --version, -v Print version number');
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@doquflow/cli",
3
- "version": "1.3.1",
3
+ "version": "1.5.0",
4
4
  "description": "CLI for setting up Docuflow in your project",
5
5
  "author": "Docuflow <hello@doquflows.dev>",
6
6
  "license": "MIT",
@@ -31,7 +31,7 @@
31
31
  "build": "tsc && node -e \"const fs=require('fs'),p=require('path'),src=p.join(process.cwd(),'../ui/dist'),dst=p.join(process.cwd(),'ui-dist');if(!fs.existsSync(src)){console.log('Warning: packages/ui/dist not found — run npm run build:ui first');process.exit(0)}fs.mkdirSync(dst,{recursive:true});fs.cpSync(src,dst,{recursive:true,force:true});console.log(' ✓ ui-dist synced from packages/ui/dist ('+(fs.readdirSync(dst).length)+' files at root)')\""
32
32
  },
33
33
  "dependencies": {
34
- "@doquflow/server": "1.3.1",
34
+ "@doquflow/server": "1.5.0",
35
35
  "cors": "^2.8.5",
36
36
  "express": "^4.19.2"
37
37
  },