@factadev/cli 0.2.11 → 0.2.14

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.
@@ -0,0 +1,41 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * Postinstall: ensure platform optional dependency is installed so
4
+ * optionalDependencies auto-link works. If the binary is missing, install it
5
+ * into this package's node_modules (npm sometimes skips optional deps).
6
+ */
7
+ const path = require('path');
8
+ const fs = require('fs');
9
+ const { execSync } = require('child_process');
10
+
11
+ const platform = process.platform;
12
+ const arch = process.arch;
13
+ const platformKey = `${platform}-${arch}`;
14
+ const pkgName = `@factadev/cli-${platformKey}`;
15
+ const binName = platform === 'win32' ? 'nest.exe' : 'nest';
16
+
17
+ const packageRoot = path.resolve(__dirname, '..');
18
+ const binaryPath = path.join(packageRoot, 'node_modules', pkgName, 'bin', binName);
19
+
20
+ if (fs.existsSync(binaryPath)) {
21
+ process.exit(0);
22
+ }
23
+
24
+ let version;
25
+ try {
26
+ const pkgPath = path.join(packageRoot, 'package.json');
27
+ version = require(pkgPath).version;
28
+ } catch (e) {
29
+ process.exit(0);
30
+ }
31
+
32
+ if (!version) process.exit(0);
33
+
34
+ try {
35
+ execSync(`npm install ${pkgName}@${version} --no-save --prefer-offline --no-audit`, {
36
+ cwd: packageRoot,
37
+ stdio: 'inherit',
38
+ });
39
+ } catch (e) {
40
+ // Non-fatal: launcher will prompt or install on first run
41
+ }
package/bin/nest.cjs CHANGED
@@ -1,50 +1,30 @@
1
1
  #!/usr/bin/env node
2
2
  /**
3
- * NEST CLI launcher resolves and runs the platform-specific binary.
4
- * npm install @factadev/cli installs one optional dependency matching this machine
5
- * (os/cpu); this script finds that binary and execs it. No runtime npm install.
3
+ * NEST CLI launcher. Resolves platform binary from optionalDependency
4
+ * (npm may install it in main package node_modules or as global sibling).
6
5
  */
7
- const { execFileSync } = require('child_process');
6
+ const { execFileSync, execSync } = require('child_process');
8
7
  const path = require('path');
9
8
  const fs = require('fs');
10
9
 
11
10
  const platform = process.platform;
12
11
  const arch = process.arch;
13
-
14
12
  const RELEASE_URL = 'https://github.com/Facta-Dev/ctx0_nest/releases';
15
13
 
16
- // Map Node platform/arch to our package suffix (must match @factadev/cli-<name>)
17
- const PLATFORM_MAP = [
18
- { os: 'darwin', cpu: 'arm64', key: 'darwin-arm64' },
19
- { os: 'darwin', cpu: 'x64', key: 'darwin-x64' },
20
- { os: 'linux', cpu: 'arm64', key: 'linux-arm64' },
21
- { os: 'linux', cpu: 'x64', key: 'linux-x64' },
22
- { os: 'win32', cpu: 'x64', key: 'win32-x64' },
23
- ];
24
-
25
- function getPlatformKey() {
26
- const entry = PLATFORM_MAP.find(
27
- (e) => e.os === platform && e.cpu === arch
28
- );
29
- return entry ? entry.key : null;
30
- }
14
+ // Node: darwin|linux|win32, x64|arm64 -> matches our package suffix
15
+ const platformKey = `${platform}-${arch}`;
16
+ const pkgName = `@factadev/cli-${platformKey}`;
17
+ const binName = platform === 'win32' ? 'nest.exe' : 'nest';
31
18
 
32
19
  function getBinaryPath() {
33
- const platformKey = getPlatformKey();
34
- if (!platformKey) return null;
35
-
36
- const pkgName = `@factadev/cli-${platformKey}`;
37
- const binName = platform === 'win32' ? 'nest.exe' : 'nest';
38
-
39
- // Main package root (where this script lives: .../bin/nest.cjs)
40
20
  const mainRoot = path.resolve(__dirname, '..');
41
21
 
42
22
  const candidates = [
43
- // 1. Optional dep nested under main package (npm/yarn typical)
23
+ // 1. Optional dep inside main package (npm install -g @factadev/cli)
44
24
  path.join(mainRoot, 'node_modules', pkgName, 'bin', binName),
45
- // 2. Sibling under same scope (global npm: .../node_modules/@factadev/cli, .../cli-*)
25
+ // 2. Sibling under same scope (global: .../node_modules/@factadev/cli-*)
46
26
  path.join(mainRoot, '..', `cli-${platformKey}`, 'bin', binName),
47
- // 3. Unix global: PREFIX/lib/node_modules/@factadev/cli-*
27
+ // 3. Global Unix
48
28
  path.join(
49
29
  process.env.npm_config_prefix || process.env.PREFIX || '/usr/local',
50
30
  'lib',
@@ -53,16 +33,24 @@ function getBinaryPath() {
53
33
  'bin',
54
34
  binName
55
35
  ),
56
- // 4. Windows global (prefix often = npm dir with node_modules)
36
+ // 4. Global Windows
57
37
  path.join(
58
38
  process.env.npm_config_prefix ||
59
- path.join(process.env.APPDATA || '', 'npm'),
39
+ (process.env.APPDATA ? path.join(process.env.APPDATA, 'npm') : ''),
60
40
  'node_modules',
61
41
  pkgName,
62
42
  'bin',
63
43
  binName
64
44
  ),
65
- ];
45
+ // 5. nvm-style global
46
+ path.join(
47
+ process.env.HOME || '',
48
+ '.nvm', 'versions', 'node',
49
+ 'v' + process.version.split('.')[0].slice(1),
50
+ 'lib', 'node_modules',
51
+ pkgName, 'bin', binName
52
+ ),
53
+ ].filter(Boolean);
66
54
 
67
55
  for (const binPath of candidates) {
68
56
  if (fs.existsSync(binPath)) return binPath;
@@ -71,29 +59,29 @@ function getBinaryPath() {
71
59
  }
72
60
 
73
61
  function main() {
74
- const platformKey = getPlatformKey();
75
- if (!platformKey) {
76
- console.error(
77
- `Unsupported platform: ${platform}-${arch}. Supported: darwin-arm64, darwin-x64, linux-arm64, linux-x64, win32-x64.`
78
- );
79
- console.error(`See ${RELEASE_URL}`);
80
- process.exit(1);
62
+ let binPath = getBinaryPath();
63
+
64
+ if (!binPath) {
65
+ console.log('Platform binary not found. Installing @factadev/cli-' + platformKey + '...');
66
+ try {
67
+ execSync(`npm install -g @factadev/cli-${platformKey}@latest --force`, { stdio: 'inherit' });
68
+ binPath = getBinaryPath();
69
+ } catch (e) {
70
+ console.error('Install failed. Try: npm install -g @factadev/cli @factadev/cli-' + platformKey + ' --force');
71
+ console.error('Or download from:', RELEASE_URL);
72
+ process.exit(1);
73
+ }
81
74
  }
82
75
 
83
- const binPath = getBinaryPath();
84
76
  if (!binPath) {
85
- console.error(
86
- `Platform binary not found for ${platformKey}. Reinstall so npm can fetch the matching optional dependency:`
87
- );
88
- console.error(' npm install -g @factadev/cli');
89
- console.error('Or download the binary manually from:', RELEASE_URL);
77
+ console.error('Binary still missing. Run: npm install -g @factadev/cli @factadev/cli-' + platformKey + ' --force');
90
78
  process.exit(1);
91
79
  }
92
80
 
93
81
  try {
94
82
  execFileSync(binPath, process.argv.slice(2), { stdio: 'inherit' });
95
- } catch (err) {
96
- process.exit(typeof err.status === 'number' ? err.status : 1);
83
+ } catch (e) {
84
+ process.exit(typeof e.status === 'number' ? e.status : 1);
97
85
  }
98
86
  }
99
87
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@factadev/cli",
3
- "version": "0.2.11",
3
+ "version": "0.2.14",
4
4
  "description": "NEST CLI - Enterprise AI coding agent control center. Run Claude Code, Codex, Cursor, Gemini, OpenCode locally and control remotely via web.",
5
5
  "author": "Carlos Matias Baglieri",
6
6
  "license": "AGPL-3.0-only",
@@ -15,15 +15,21 @@
15
15
  "bin": {
16
16
  "nest": "bin/nest.cjs"
17
17
  },
18
+ "scripts": {
19
+ "postinstall": "node -e \"try{require('fs').chmodSync(require('path').join(__dirname,'bin','nest.cjs'),0o755)}catch(e){}\" && node bin/ensure-platform.cjs"
20
+ },
18
21
  "files": [
19
22
  "bin/nest.cjs",
20
- "NOTICE"
23
+ "bin/ensure-platform.cjs",
24
+ "NOTICE",
25
+ "LICENSE",
26
+ "README.md"
21
27
  ],
22
28
  "optionalDependencies": {
23
- "@factadev/cli-darwin-arm64": "0.2.11",
24
- "@factadev/cli-darwin-x64": "0.2.11",
25
- "@factadev/cli-linux-arm64": "0.2.11",
26
- "@factadev/cli-linux-x64": "0.2.11",
27
- "@factadev/cli-win32-x64": "0.2.11"
29
+ "@factadev/cli-darwin-arm64": "0.2.14",
30
+ "@factadev/cli-darwin-x64": "0.2.14",
31
+ "@factadev/cli-linux-arm64": "0.2.14",
32
+ "@factadev/cli-linux-x64": "0.2.14",
33
+ "@factadev/cli-win32-x64": "0.2.14"
28
34
  }
29
35
  }