@guardinstall/cli 0.1.6 → 0.1.9
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/dist/index.js +1 -1
- package/dist/installer.js +45 -21
- package/package.json +3 -3
- package/src/index.ts +1 -1
- package/src/installer.ts +54 -22
package/dist/index.js
CHANGED
|
@@ -39,7 +39,7 @@ const program = new commander_1.Command();
|
|
|
39
39
|
program
|
|
40
40
|
.name('guardinstall')
|
|
41
41
|
.description('A kernel-level behavioral sandbox for npm/pnpm/bun install scripts')
|
|
42
|
-
.version('0.1.
|
|
42
|
+
.version('0.1.9');
|
|
43
43
|
program
|
|
44
44
|
.command('install')
|
|
45
45
|
.description('Run npm install with sandbox protection')
|
package/dist/installer.js
CHANGED
|
@@ -6,7 +6,8 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
exports.runPackageManager = void 0;
|
|
7
7
|
const child_process_1 = require("child_process");
|
|
8
8
|
const chalk_1 = __importDefault(require("chalk"));
|
|
9
|
-
const
|
|
9
|
+
const fs_1 = __importDefault(require("fs"));
|
|
10
|
+
const path_1 = __importDefault(require("path"));
|
|
10
11
|
async function runPackageManager(pm, args) {
|
|
11
12
|
const pmMap = {
|
|
12
13
|
npm: 'npm',
|
|
@@ -14,19 +15,18 @@ async function runPackageManager(pm, args) {
|
|
|
14
15
|
bun: 'bun',
|
|
15
16
|
};
|
|
16
17
|
const command = pmMap[pm] || 'npm';
|
|
17
|
-
// For
|
|
18
|
-
|
|
19
|
-
|
|
18
|
+
// For add, we need to manually add to package.json and run npm install
|
|
19
|
+
if (args.includes('add') && command === 'npm') {
|
|
20
|
+
return runNpmAddWithFallback(args);
|
|
21
|
+
}
|
|
22
|
+
// For install, just run with --ignore-scripts
|
|
20
23
|
const hasIgnoreScripts = args.some(a => a.includes('ignore-scripts'));
|
|
21
24
|
if (!hasIgnoreScripts && (args.includes('install') || args.includes('add'))) {
|
|
22
|
-
// Add --ignore-scripts flag
|
|
23
25
|
args.push('--ignore-scripts');
|
|
24
26
|
}
|
|
25
|
-
// Remove --ignore-scripts from display (it's expected)
|
|
26
27
|
const displayArgs = args.filter(a => a !== '--ignore-scripts');
|
|
27
28
|
console.log(chalk_1.default.gray(`\n📦 Running: ${command} ${displayArgs.join(' ')} (with --ignore-scripts)\n`));
|
|
28
29
|
return new Promise((resolve) => {
|
|
29
|
-
// Use spawn without shell to avoid npm arborist bug triggered by shell escaping
|
|
30
30
|
const proc = (0, child_process_1.spawn)(command, args, {
|
|
31
31
|
stdio: 'inherit',
|
|
32
32
|
shell: false
|
|
@@ -35,20 +35,6 @@ async function runPackageManager(pm, args) {
|
|
|
35
35
|
proc.stdout?.on('data', (d) => { output += d.toString(); });
|
|
36
36
|
proc.stderr?.on('data', (d) => { output += d.toString(); });
|
|
37
37
|
proc.on('close', (code) => {
|
|
38
|
-
// If npm fails with arborist error, try alternative approach
|
|
39
|
-
if (code !== 0 && command === 'npm') {
|
|
40
|
-
console.log(chalk_1.default.yellow('\n⚠️ npm encountered an error, trying with --no-audit --no-fund...\n'));
|
|
41
|
-
try {
|
|
42
|
-
// Try running npm without audit/fund which sometimes triggers arborist issues
|
|
43
|
-
const fallbackArgs = ['install', '--ignore-scripts', '--no-audit', '--no-fund', ...args.filter(a => a !== 'install' && a !== 'add' && a !== '--ignore-scripts')];
|
|
44
|
-
const result = (0, child_process_2.execSync)(`npm ${fallbackArgs.join(' ')}`, { stdio: 'inherit', encoding: 'utf-8' });
|
|
45
|
-
resolve({ success: true, output: result || '' });
|
|
46
|
-
return;
|
|
47
|
-
}
|
|
48
|
-
catch (e) {
|
|
49
|
-
// Fallback failed too
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
38
|
resolve({
|
|
53
39
|
success: code === 0,
|
|
54
40
|
output
|
|
@@ -57,3 +43,41 @@ async function runPackageManager(pm, args) {
|
|
|
57
43
|
});
|
|
58
44
|
}
|
|
59
45
|
exports.runPackageManager = runPackageManager;
|
|
46
|
+
// Workaround for npm arborist bug: manually add to package.json then run npm install
|
|
47
|
+
async function runNpmAddWithFallback(args) {
|
|
48
|
+
const packages = args.filter(a => !a.startsWith('-') && a !== 'add');
|
|
49
|
+
if (packages.length === 0) {
|
|
50
|
+
return { success: false, output: 'No packages specified' };
|
|
51
|
+
}
|
|
52
|
+
console.log(chalk_1.default.gray(`\n📦 Adding packages: ${packages.join(', ')}\n`));
|
|
53
|
+
console.log(chalk_1.default.gray(`Step 1: Adding to package.json...\n`));
|
|
54
|
+
try {
|
|
55
|
+
// Read package.json
|
|
56
|
+
const pkgPath = path_1.default.join(process.cwd(), 'package.json');
|
|
57
|
+
const pkg = JSON.parse(fs_1.default.readFileSync(pkgPath, 'utf-8'));
|
|
58
|
+
// Add packages to dependencies
|
|
59
|
+
if (!pkg.dependencies)
|
|
60
|
+
pkg.dependencies = {};
|
|
61
|
+
for (const pkgName of packages) {
|
|
62
|
+
// Extract package@version if specified
|
|
63
|
+
const match = pkgName.match(/^(@?[^@]+)(@.+)?$/);
|
|
64
|
+
const name = match ? match[1] : pkgName;
|
|
65
|
+
const version = match && match[2] ? match[2] : 'latest';
|
|
66
|
+
pkg.dependencies[name] = version;
|
|
67
|
+
}
|
|
68
|
+
// Write back
|
|
69
|
+
fs_1.default.writeFileSync(pkgPath, JSON.stringify(pkg, null, 2) + '\n');
|
|
70
|
+
console.log(chalk_1.default.gray(`Step 2: Running npm install --ignore-scripts...\n`));
|
|
71
|
+
// Run npm install with --ignore-scripts
|
|
72
|
+
const result = (0, child_process_1.execSync)('npm install --ignore-scripts --no-audit --no-fund', {
|
|
73
|
+
stdio: 'inherit',
|
|
74
|
+
encoding: 'utf-8'
|
|
75
|
+
});
|
|
76
|
+
return { success: true, output: result || '' };
|
|
77
|
+
}
|
|
78
|
+
catch (e) {
|
|
79
|
+
const errorMsg = e instanceof Error ? e.message : String(e);
|
|
80
|
+
console.error(chalk_1.default.red(`Error: ${errorMsg}`));
|
|
81
|
+
return { success: false, output: errorMsg };
|
|
82
|
+
}
|
|
83
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@guardinstall/cli",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.9",
|
|
4
4
|
"description": "CLI wrapper for guardinstall - intercepts and sandboxes install scripts",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"bin": {
|
|
@@ -13,8 +13,8 @@
|
|
|
13
13
|
"test": "jest"
|
|
14
14
|
},
|
|
15
15
|
"dependencies": {
|
|
16
|
-
"@guardinstall/policy-engine": "0.1.
|
|
17
|
-
"@guardinstall/sandbox": "0.1.
|
|
16
|
+
"@guardinstall/policy-engine": "0.1.8",
|
|
17
|
+
"@guardinstall/sandbox": "0.1.8",
|
|
18
18
|
"@npmcli/arborist": "7.5.4",
|
|
19
19
|
"chalk": "4.1.2",
|
|
20
20
|
"commander": "12.1.0"
|
package/src/index.ts
CHANGED
package/src/installer.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
|
-
import { spawn } from 'child_process'
|
|
1
|
+
import { spawn, execSync } from 'child_process'
|
|
2
2
|
import chalk from 'chalk'
|
|
3
|
-
import
|
|
3
|
+
import fs from 'fs'
|
|
4
|
+
import path from 'path'
|
|
4
5
|
|
|
5
6
|
export async function runPackageManager(
|
|
6
7
|
pm: string,
|
|
@@ -14,22 +15,22 @@ export async function runPackageManager(
|
|
|
14
15
|
|
|
15
16
|
const command = pmMap[pm] || 'npm'
|
|
16
17
|
|
|
17
|
-
// For
|
|
18
|
-
|
|
19
|
-
|
|
18
|
+
// For add, we need to manually add to package.json and run npm install
|
|
19
|
+
if (args.includes('add') && command === 'npm') {
|
|
20
|
+
return runNpmAddWithFallback(args)
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
// For install, just run with --ignore-scripts
|
|
20
24
|
const hasIgnoreScripts = args.some(a => a.includes('ignore-scripts'))
|
|
21
25
|
|
|
22
26
|
if (!hasIgnoreScripts && (args.includes('install') || args.includes('add'))) {
|
|
23
|
-
// Add --ignore-scripts flag
|
|
24
27
|
args.push('--ignore-scripts')
|
|
25
28
|
}
|
|
26
29
|
|
|
27
|
-
// Remove --ignore-scripts from display (it's expected)
|
|
28
30
|
const displayArgs = args.filter(a => a !== '--ignore-scripts')
|
|
29
31
|
console.log(chalk.gray(`\n📦 Running: ${command} ${displayArgs.join(' ')} (with --ignore-scripts)\n`))
|
|
30
32
|
|
|
31
33
|
return new Promise((resolve) => {
|
|
32
|
-
// Use spawn without shell to avoid npm arborist bug triggered by shell escaping
|
|
33
34
|
const proc = spawn(command, args, {
|
|
34
35
|
stdio: 'inherit',
|
|
35
36
|
shell: false
|
|
@@ -40,20 +41,6 @@ export async function runPackageManager(
|
|
|
40
41
|
proc.stderr?.on('data', (d: Buffer) => { output += d.toString() })
|
|
41
42
|
|
|
42
43
|
proc.on('close', (code) => {
|
|
43
|
-
// If npm fails with arborist error, try alternative approach
|
|
44
|
-
if (code !== 0 && command === 'npm') {
|
|
45
|
-
console.log(chalk.yellow('\n⚠️ npm encountered an error, trying with --no-audit --no-fund...\n'))
|
|
46
|
-
try {
|
|
47
|
-
// Try running npm without audit/fund which sometimes triggers arborist issues
|
|
48
|
-
const fallbackArgs = ['install', '--ignore-scripts', '--no-audit', '--no-fund', ...args.filter(a => a !== 'install' && a !== 'add' && a !== '--ignore-scripts')]
|
|
49
|
-
const result = execSync(`npm ${fallbackArgs.join(' ')}`, { stdio: 'inherit', encoding: 'utf-8' })
|
|
50
|
-
resolve({ success: true, output: result || '' })
|
|
51
|
-
return
|
|
52
|
-
} catch (e) {
|
|
53
|
-
// Fallback failed too
|
|
54
|
-
}
|
|
55
|
-
}
|
|
56
|
-
|
|
57
44
|
resolve({
|
|
58
45
|
success: code === 0,
|
|
59
46
|
output
|
|
@@ -61,3 +48,48 @@ export async function runPackageManager(
|
|
|
61
48
|
})
|
|
62
49
|
})
|
|
63
50
|
}
|
|
51
|
+
|
|
52
|
+
// Workaround for npm arborist bug: manually add to package.json then run npm install
|
|
53
|
+
async function runNpmAddWithFallback(args: string[]): Promise<{ success: boolean; output: string }> {
|
|
54
|
+
const packages = args.filter(a => !a.startsWith('-') && a !== 'add')
|
|
55
|
+
|
|
56
|
+
if (packages.length === 0) {
|
|
57
|
+
return { success: false, output: 'No packages specified' }
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
console.log(chalk.gray(`\n📦 Adding packages: ${packages.join(', ')}\n`))
|
|
61
|
+
console.log(chalk.gray(`Step 1: Adding to package.json...\n`))
|
|
62
|
+
|
|
63
|
+
try {
|
|
64
|
+
// Read package.json
|
|
65
|
+
const pkgPath = path.join(process.cwd(), 'package.json')
|
|
66
|
+
const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf-8'))
|
|
67
|
+
|
|
68
|
+
// Add packages to dependencies
|
|
69
|
+
if (!pkg.dependencies) pkg.dependencies = {}
|
|
70
|
+
for (const pkgName of packages) {
|
|
71
|
+
// Extract package@version if specified
|
|
72
|
+
const match = pkgName.match(/^(@?[^@]+)(@.+)?$/)
|
|
73
|
+
const name = match ? match[1] : pkgName
|
|
74
|
+
const version = match && match[2] ? match[2] : 'latest'
|
|
75
|
+
pkg.dependencies[name] = version
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
// Write back
|
|
79
|
+
fs.writeFileSync(pkgPath, JSON.stringify(pkg, null, 2) + '\n')
|
|
80
|
+
|
|
81
|
+
console.log(chalk.gray(`Step 2: Running npm install --ignore-scripts...\n`))
|
|
82
|
+
|
|
83
|
+
// Run npm install with --ignore-scripts
|
|
84
|
+
const result = execSync('npm install --ignore-scripts --no-audit --no-fund', {
|
|
85
|
+
stdio: 'inherit',
|
|
86
|
+
encoding: 'utf-8'
|
|
87
|
+
})
|
|
88
|
+
|
|
89
|
+
return { success: true, output: result || '' }
|
|
90
|
+
} catch (e) {
|
|
91
|
+
const errorMsg = e instanceof Error ? e.message : String(e)
|
|
92
|
+
console.error(chalk.red(`Error: ${errorMsg}`))
|
|
93
|
+
return { success: false, output: errorMsg }
|
|
94
|
+
}
|
|
95
|
+
}
|