juggernaut-bedrock 4.0.0 → 4.0.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/bin/.gitkeep +0 -0
- package/install.js +42 -61
- package/package.json +3 -3
package/bin/.gitkeep
ADDED
|
File without changes
|
package/install.js
CHANGED
|
@@ -3,11 +3,16 @@
|
|
|
3
3
|
const https = require("https");
|
|
4
4
|
const fs = require("fs");
|
|
5
5
|
const path = require("path");
|
|
6
|
-
const
|
|
6
|
+
const { Readable } = require("stream");
|
|
7
7
|
const crypto = require("crypto");
|
|
8
8
|
|
|
9
9
|
const REPO = "jpvelasco/juggernaut";
|
|
10
10
|
const BIN_DIR = path.join(__dirname, "bin");
|
|
11
|
+
const ALLOWED_HOSTS = new Set([
|
|
12
|
+
"github.com",
|
|
13
|
+
"api.github.com",
|
|
14
|
+
"release-assets.githubusercontent.com"
|
|
15
|
+
]);
|
|
11
16
|
|
|
12
17
|
function getPlatform() {
|
|
13
18
|
const osMap = { darwin: "darwin", linux: "linux", win32: "windows" };
|
|
@@ -20,12 +25,23 @@ function getPlatform() {
|
|
|
20
25
|
return { os: p, arch: a, platform: `${p}_${a}` };
|
|
21
26
|
}
|
|
22
27
|
|
|
23
|
-
function
|
|
28
|
+
function httpsGetBuffer(url) {
|
|
29
|
+
const parsed = new URL(url);
|
|
30
|
+
if (!ALLOWED_HOSTS.has(parsed.hostname)) {
|
|
31
|
+
throw new Error(`URL host not allowed: ${parsed.hostname}`);
|
|
32
|
+
}
|
|
24
33
|
return new Promise((resolve, reject) => {
|
|
25
34
|
https
|
|
26
35
|
.get(url, { headers: { "User-Agent": "juggernaut-npm-installer/1.0" } }, (res) => {
|
|
27
36
|
if (res.statusCode === 301 || res.statusCode === 302) {
|
|
28
|
-
|
|
37
|
+
const location = res.headers.location;
|
|
38
|
+
const redirectParsed = new URL(location);
|
|
39
|
+
if (!ALLOWED_HOSTS.has(redirectParsed.hostname)) {
|
|
40
|
+
reject(new Error(`Redirect host not allowed: ${redirectParsed.hostname}`));
|
|
41
|
+
return;
|
|
42
|
+
}
|
|
43
|
+
httpsGetBuffer(location).then(resolve).catch(reject);
|
|
44
|
+
return;
|
|
29
45
|
}
|
|
30
46
|
const chunks = [];
|
|
31
47
|
res.on("data", (chunk) => chunks.push(chunk));
|
|
@@ -36,27 +52,8 @@ function httpsGet(url) {
|
|
|
36
52
|
});
|
|
37
53
|
}
|
|
38
54
|
|
|
39
|
-
function downloadFile(url, dest) {
|
|
40
|
-
return new Promise((resolve, reject) => {
|
|
41
|
-
const file = fs.createWriteStream(dest);
|
|
42
|
-
function fetch(fetchUrl) {
|
|
43
|
-
https
|
|
44
|
-
.get(fetchUrl, { headers: { "User-Agent": "juggernaut-npm-installer/1.0" } }, (res) => {
|
|
45
|
-
if (res.statusCode === 301 || res.statusCode === 302) {
|
|
46
|
-
return fetch(res.headers.location);
|
|
47
|
-
}
|
|
48
|
-
res.pipe(file);
|
|
49
|
-
file.on("finish", () => file.close(resolve));
|
|
50
|
-
file.on("error", reject);
|
|
51
|
-
})
|
|
52
|
-
.on("error", reject);
|
|
53
|
-
}
|
|
54
|
-
fetch(url);
|
|
55
|
-
});
|
|
56
|
-
}
|
|
57
|
-
|
|
58
55
|
async function getLatestVersion() {
|
|
59
|
-
const data = await
|
|
56
|
+
const data = await httpsGetBuffer(`https://api.github.com/repos/${REPO}/releases/latest`);
|
|
60
57
|
const release = JSON.parse(data.toString());
|
|
61
58
|
return release.tag_name.replace(/^v/, "");
|
|
62
59
|
}
|
|
@@ -68,49 +65,33 @@ async function main() {
|
|
|
68
65
|
const archive = `juggernaut_${platform}.${ext}`;
|
|
69
66
|
const baseUrl = `https://github.com/${REPO}/releases/download/v${version}`;
|
|
70
67
|
|
|
71
|
-
|
|
72
|
-
const
|
|
73
|
-
const
|
|
74
|
-
|
|
75
|
-
try {
|
|
76
|
-
console.log(`Downloading Juggernaut v${version} (${platform})...`);
|
|
77
|
-
await downloadFile(`${baseUrl}/${archive}`, archivePath);
|
|
78
|
-
await downloadFile(`${baseUrl}/checksums.txt`, checksumPath);
|
|
79
|
-
|
|
80
|
-
// Verify checksum.
|
|
81
|
-
const checksums = fs.readFileSync(checksumPath, "utf8");
|
|
82
|
-
const line = checksums.split("\n").find((l) => l.includes(archive));
|
|
83
|
-
if (!line) throw new Error(`Checksum not found for ${archive}`);
|
|
84
|
-
const expected = line.trim().split(/\s+/)[0].toLowerCase();
|
|
85
|
-
const actual = crypto
|
|
86
|
-
.createHash("sha256")
|
|
87
|
-
.update(fs.readFileSync(archivePath))
|
|
88
|
-
.digest("hex")
|
|
89
|
-
.toLowerCase();
|
|
90
|
-
if (actual !== expected) {
|
|
91
|
-
throw new Error(`Checksum mismatch for ${archive}\n expected: ${expected}\n got: ${actual}`);
|
|
92
|
-
}
|
|
68
|
+
console.log(`Downloading Juggernaut v${version} (${platform})...`);
|
|
69
|
+
const archiveBuf = await httpsGetBuffer(`${baseUrl}/${archive}`);
|
|
70
|
+
const checksumsBuf = await httpsGetBuffer(`${baseUrl}/checksums.txt`);
|
|
93
71
|
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
await tar.x({ file: archivePath, cwd: BIN_DIR });
|
|
103
|
-
fs.chmodSync(path.join(BIN_DIR, "juggernaut"), 0o755);
|
|
104
|
-
}
|
|
72
|
+
const checksums = checksumsBuf.toString("utf8");
|
|
73
|
+
const line = checksums.split("\n").find((l) => l.includes(archive));
|
|
74
|
+
if (!line) throw new Error(`Checksum not found for ${archive}`);
|
|
75
|
+
const expected = line.trim().split(/\s+/)[0].toLowerCase();
|
|
76
|
+
const actual = crypto.createHash("sha256").update(archiveBuf).digest("hex").toLowerCase();
|
|
77
|
+
if (actual !== expected) {
|
|
78
|
+
throw new Error(`Checksum mismatch for ${archive}\n expected: ${expected}\n got: ${actual}`);
|
|
79
|
+
}
|
|
105
80
|
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
81
|
+
if (ext === "zip") {
|
|
82
|
+
const AdmZip = require("adm-zip");
|
|
83
|
+
const zip = new AdmZip(archiveBuf);
|
|
84
|
+
zip.extractEntryTo("juggernaut.exe", BIN_DIR, false, true);
|
|
85
|
+
} else {
|
|
86
|
+
const tar = require("tar");
|
|
87
|
+
await tar.x({ cwd: BIN_DIR, mode: 0o700, strict: true }, Readable.from(archiveBuf));
|
|
110
88
|
}
|
|
89
|
+
|
|
90
|
+
console.log(`Juggernaut v${version} installed successfully.`);
|
|
91
|
+
console.log(`Run: juggernaut apply`);
|
|
111
92
|
}
|
|
112
93
|
|
|
113
94
|
main().catch((err) => {
|
|
114
95
|
console.error("Installation failed:", err.message);
|
|
115
96
|
process.exit(1);
|
|
116
|
-
});
|
|
97
|
+
});
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "juggernaut-bedrock",
|
|
3
|
-
"version": "4.0.
|
|
3
|
+
"version": "4.0.1",
|
|
4
4
|
"description": "Configure Claude Code to use Amazon Bedrock — cross-platform installer",
|
|
5
5
|
"bin": {
|
|
6
6
|
"juggernaut": "./bin/juggernaut"
|
|
@@ -9,8 +9,8 @@
|
|
|
9
9
|
"postinstall": "node install.js"
|
|
10
10
|
},
|
|
11
11
|
"dependencies": {
|
|
12
|
-
"tar": "
|
|
13
|
-
"adm-zip": "
|
|
12
|
+
"tar": "7.5.16",
|
|
13
|
+
"adm-zip": "0.5.17"
|
|
14
14
|
},
|
|
15
15
|
"os": ["darwin", "linux", "win32"],
|
|
16
16
|
"cpu": ["x64", "arm64"],
|