@specific.dev/cli 0.1.73 → 0.1.75
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/admin/404/index.html +1 -1
- package/dist/admin/404.html +1 -1
- package/dist/admin/__next.!KGRlZmF1bHQp.__PAGE__.txt +1 -1
- package/dist/admin/__next.!KGRlZmF1bHQp.txt +1 -1
- package/dist/admin/__next._full.txt +1 -1
- package/dist/admin/__next._head.txt +1 -1
- package/dist/admin/__next._index.txt +1 -1
- package/dist/admin/__next._tree.txt +1 -1
- package/dist/admin/_not-found/__next._full.txt +1 -1
- package/dist/admin/_not-found/__next._head.txt +1 -1
- package/dist/admin/_not-found/__next._index.txt +1 -1
- package/dist/admin/_not-found/__next._not-found.__PAGE__.txt +1 -1
- package/dist/admin/_not-found/__next._not-found.txt +1 -1
- package/dist/admin/_not-found/__next._tree.txt +1 -1
- package/dist/admin/_not-found/index.html +1 -1
- package/dist/admin/_not-found/index.txt +1 -1
- package/dist/admin/databases/__next.!KGRlZmF1bHQp.databases.__PAGE__.txt +1 -1
- package/dist/admin/databases/__next.!KGRlZmF1bHQp.databases.txt +1 -1
- package/dist/admin/databases/__next.!KGRlZmF1bHQp.txt +1 -1
- package/dist/admin/databases/__next._full.txt +1 -1
- package/dist/admin/databases/__next._head.txt +1 -1
- package/dist/admin/databases/__next._index.txt +1 -1
- package/dist/admin/databases/__next._tree.txt +1 -1
- package/dist/admin/databases/index.html +1 -1
- package/dist/admin/databases/index.txt +1 -1
- package/dist/admin/fullscreen/__next._full.txt +1 -1
- package/dist/admin/fullscreen/__next._head.txt +1 -1
- package/dist/admin/fullscreen/__next._index.txt +1 -1
- package/dist/admin/fullscreen/__next._tree.txt +1 -1
- package/dist/admin/fullscreen/__next.fullscreen.__PAGE__.txt +1 -1
- package/dist/admin/fullscreen/__next.fullscreen.txt +1 -1
- package/dist/admin/fullscreen/databases/__next._full.txt +1 -1
- package/dist/admin/fullscreen/databases/__next._head.txt +1 -1
- package/dist/admin/fullscreen/databases/__next._index.txt +1 -1
- package/dist/admin/fullscreen/databases/__next._tree.txt +1 -1
- package/dist/admin/fullscreen/databases/__next.fullscreen.databases.__PAGE__.txt +1 -1
- package/dist/admin/fullscreen/databases/__next.fullscreen.databases.txt +1 -1
- package/dist/admin/fullscreen/databases/__next.fullscreen.txt +1 -1
- package/dist/admin/fullscreen/databases/index.html +1 -1
- package/dist/admin/fullscreen/databases/index.txt +1 -1
- package/dist/admin/fullscreen/index.html +1 -1
- package/dist/admin/fullscreen/index.txt +1 -1
- package/dist/admin/index.html +1 -1
- package/dist/admin/index.txt +1 -1
- package/dist/admin/mail/__next.!KGRlZmF1bHQp.mail.__PAGE__.txt +1 -1
- package/dist/admin/mail/__next.!KGRlZmF1bHQp.mail.txt +1 -1
- package/dist/admin/mail/__next.!KGRlZmF1bHQp.txt +1 -1
- package/dist/admin/mail/__next._full.txt +1 -1
- package/dist/admin/mail/__next._head.txt +1 -1
- package/dist/admin/mail/__next._index.txt +1 -1
- package/dist/admin/mail/__next._tree.txt +1 -1
- package/dist/admin/mail/index.html +1 -1
- package/dist/admin/mail/index.txt +1 -1
- package/dist/admin/workflows/__next.!KGRlZmF1bHQp.txt +1 -1
- package/dist/admin/workflows/__next.!KGRlZmF1bHQp.workflows.__PAGE__.txt +1 -1
- package/dist/admin/workflows/__next.!KGRlZmF1bHQp.workflows.txt +1 -1
- package/dist/admin/workflows/__next._full.txt +1 -1
- package/dist/admin/workflows/__next._head.txt +1 -1
- package/dist/admin/workflows/__next._index.txt +1 -1
- package/dist/admin/workflows/__next._tree.txt +1 -1
- package/dist/admin/workflows/index.html +1 -1
- package/dist/admin/workflows/index.txt +1 -1
- package/dist/cli.js +201 -357
- package/dist/postinstall.js +1 -1
- package/package.json +1 -1
- /package/dist/admin/_next/static/{2GhRJUspcGN_TKmFF6ihm → ntsk0waJiBFcaeQ8sbm0K}/_buildManifest.js +0 -0
- /package/dist/admin/_next/static/{2GhRJUspcGN_TKmFF6ihm → ntsk0waJiBFcaeQ8sbm0K}/_clientMiddlewareManifest.json +0 -0
- /package/dist/admin/_next/static/{2GhRJUspcGN_TKmFF6ihm → ntsk0waJiBFcaeQ8sbm0K}/_ssgManifest.js +0 -0
package/dist/cli.js
CHANGED
|
@@ -637,19 +637,19 @@ var init_open = __esm({
|
|
|
637
637
|
}
|
|
638
638
|
const subprocess = childProcess3.spawn(command, cliArguments, childProcessOptions);
|
|
639
639
|
if (options2.wait) {
|
|
640
|
-
return new Promise((
|
|
640
|
+
return new Promise((resolve9, reject) => {
|
|
641
641
|
subprocess.once("error", reject);
|
|
642
642
|
subprocess.once("close", (exitCode) => {
|
|
643
643
|
if (!options2.allowNonzeroExitCode && exitCode !== 0) {
|
|
644
644
|
reject(new Error(`Exited with code ${exitCode}`));
|
|
645
645
|
return;
|
|
646
646
|
}
|
|
647
|
-
|
|
647
|
+
resolve9(subprocess);
|
|
648
648
|
});
|
|
649
649
|
});
|
|
650
650
|
}
|
|
651
651
|
if (isFallbackAttempt) {
|
|
652
|
-
return new Promise((
|
|
652
|
+
return new Promise((resolve9, reject) => {
|
|
653
653
|
subprocess.once("error", reject);
|
|
654
654
|
subprocess.once("spawn", () => {
|
|
655
655
|
subprocess.once("close", (exitCode) => {
|
|
@@ -659,17 +659,17 @@ var init_open = __esm({
|
|
|
659
659
|
return;
|
|
660
660
|
}
|
|
661
661
|
subprocess.unref();
|
|
662
|
-
|
|
662
|
+
resolve9(subprocess);
|
|
663
663
|
});
|
|
664
664
|
});
|
|
665
665
|
});
|
|
666
666
|
}
|
|
667
667
|
subprocess.unref();
|
|
668
|
-
return new Promise((
|
|
668
|
+
return new Promise((resolve9, reject) => {
|
|
669
669
|
subprocess.once("error", reject);
|
|
670
670
|
subprocess.once("spawn", () => {
|
|
671
671
|
subprocess.off("error", reject);
|
|
672
|
-
|
|
672
|
+
resolve9(subprocess);
|
|
673
673
|
});
|
|
674
674
|
});
|
|
675
675
|
};
|
|
@@ -183485,7 +183485,11 @@ function caInstalledInTrustStore() {
|
|
|
183485
183485
|
} else if (platform6 === "linux") {
|
|
183486
183486
|
const trustPaths = [
|
|
183487
183487
|
"/usr/local/share/ca-certificates/specific-local-ca.crt",
|
|
183488
|
-
|
|
183488
|
+
// Debian/Ubuntu
|
|
183489
|
+
"/etc/pki/ca-trust/source/anchors/specific-local-ca.crt",
|
|
183490
|
+
// RHEL/Fedora
|
|
183491
|
+
"/etc/ca-certificates/trust-source/anchors/specific-local-ca.crt"
|
|
183492
|
+
// Arch
|
|
183489
183493
|
];
|
|
183490
183494
|
for (const trustPath of trustPaths) {
|
|
183491
183495
|
if (fs.existsSync(trustPath)) {
|
|
@@ -183609,6 +183613,11 @@ function getCAInstallCommands(certPath) {
|
|
|
183609
183613
|
`cp "${certPath}" /etc/pki/ca-trust/source/anchors/specific-local-ca.crt`,
|
|
183610
183614
|
"update-ca-trust extract"
|
|
183611
183615
|
];
|
|
183616
|
+
} else if (fs.existsSync("/etc/ca-certificates/trust-source/anchors")) {
|
|
183617
|
+
return [
|
|
183618
|
+
`cp "${certPath}" /etc/ca-certificates/trust-source/anchors/specific-local-ca.crt`,
|
|
183619
|
+
"trust extract-compat"
|
|
183620
|
+
];
|
|
183612
183621
|
}
|
|
183613
183622
|
throw new Error("Could not detect Linux certificate trust mechanism");
|
|
183614
183623
|
}
|
|
@@ -184046,7 +184055,7 @@ async function pollUntilToken(deviceAuth, isCancelled) {
|
|
|
184046
184055
|
return null;
|
|
184047
184056
|
}
|
|
184048
184057
|
function sleep(ms) {
|
|
184049
|
-
return new Promise((
|
|
184058
|
+
return new Promise((resolve9) => setTimeout(resolve9, ms));
|
|
184050
184059
|
}
|
|
184051
184060
|
|
|
184052
184061
|
// src/lib/auth/login.tsx
|
|
@@ -184063,7 +184072,7 @@ function LoginUI({
|
|
|
184063
184072
|
return /* @__PURE__ */ React.createElement(Box, { flexDirection: "column", gap: 1 }, isReauthentication && /* @__PURE__ */ React.createElement(Text, { color: "yellow" }, "Session expired. Please log in again."), /* @__PURE__ */ React.createElement(Text, { bold: true }, "Log in to Specific"), state.phase === "waiting-for-browser" ? /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Box, { flexDirection: "column" }, /* @__PURE__ */ React.createElement(Text, null, "Your authentication code:", " ", /* @__PURE__ */ React.createElement(Text, { color: "cyan", bold: true }, state.userCode))), /* @__PURE__ */ React.createElement(Box, null, /* @__PURE__ */ React.createElement(Text, { color: "blue" }, /* @__PURE__ */ React.createElement(Spinner, { type: "dots" })), /* @__PURE__ */ React.createElement(Text, null, " Waiting for authentication in browser...")), /* @__PURE__ */ React.createElement(Text, { dimColor: true }, "If the browser didn't open, visit: ", state.verificationUri)) : /* @__PURE__ */ React.createElement(Box, null, /* @__PURE__ */ React.createElement(Text, { color: "blue" }, /* @__PURE__ */ React.createElement(Spinner, { type: "dots" })), /* @__PURE__ */ React.createElement(Text, null, " Initiating login...")));
|
|
184064
184073
|
}
|
|
184065
184074
|
function performLogin(options2 = {}) {
|
|
184066
|
-
return new Promise((
|
|
184075
|
+
return new Promise((resolve9) => {
|
|
184067
184076
|
let currentState = { phase: "initiating" };
|
|
184068
184077
|
let flowHandle;
|
|
184069
184078
|
const instance = render(
|
|
@@ -184103,14 +184112,14 @@ function performLogin(options2 = {}) {
|
|
|
184103
184112
|
process.off("SIGINT", handleExit);
|
|
184104
184113
|
process.off("SIGTERM", handleExit);
|
|
184105
184114
|
instance.unmount();
|
|
184106
|
-
|
|
184115
|
+
resolve9({ success: true, userEmail: newState.email });
|
|
184107
184116
|
}, 100);
|
|
184108
184117
|
} else if (newState.phase === "error") {
|
|
184109
184118
|
setTimeout(() => {
|
|
184110
184119
|
process.off("SIGINT", handleExit);
|
|
184111
184120
|
process.off("SIGTERM", handleExit);
|
|
184112
184121
|
instance.unmount();
|
|
184113
|
-
|
|
184122
|
+
resolve9({ success: false, error: new Error(newState.message) });
|
|
184114
184123
|
}, 100);
|
|
184115
184124
|
}
|
|
184116
184125
|
}
|
|
@@ -184362,9 +184371,12 @@ var ApiClient = class {
|
|
|
184362
184371
|
}
|
|
184363
184372
|
return response.json();
|
|
184364
184373
|
}
|
|
184365
|
-
async createProject(name) {
|
|
184374
|
+
async createProject(name, organizationId) {
|
|
184366
184375
|
const url = `${this.baseUrl}/projects`;
|
|
184367
184376
|
const requestBody = { name };
|
|
184377
|
+
if (organizationId) {
|
|
184378
|
+
requestBody.organizationId = organizationId;
|
|
184379
|
+
}
|
|
184368
184380
|
writeLog("api", `POST ${url}`);
|
|
184369
184381
|
writeLog("api", `Request body: ${JSON.stringify(requestBody)}`);
|
|
184370
184382
|
const response = await fetch(url, {
|
|
@@ -184399,6 +184411,31 @@ var ApiClient = class {
|
|
|
184399
184411
|
}
|
|
184400
184412
|
return response.json();
|
|
184401
184413
|
}
|
|
184414
|
+
async listOrganizations() {
|
|
184415
|
+
const url = `${this.baseUrl}/user/organizations`;
|
|
184416
|
+
writeLog("api", `GET ${url}`);
|
|
184417
|
+
const response = await fetch(url, {
|
|
184418
|
+
headers: await this.authHeaders()
|
|
184419
|
+
});
|
|
184420
|
+
writeLog("api", `Response: ${response.status} ${response.statusText}`);
|
|
184421
|
+
if (!response.ok) {
|
|
184422
|
+
let errorBody;
|
|
184423
|
+
try {
|
|
184424
|
+
const error = await response.json();
|
|
184425
|
+
errorBody = JSON.stringify(error);
|
|
184426
|
+
writeLog("api:error", `API error: ${error.error} (${error.code})`);
|
|
184427
|
+
throw new Error(`Failed to list organizations: ${error.error} (${error.code})`);
|
|
184428
|
+
} catch (e) {
|
|
184429
|
+
if (e instanceof Error && e.message.startsWith("Failed to list organizations")) {
|
|
184430
|
+
throw e;
|
|
184431
|
+
}
|
|
184432
|
+
errorBody = await response.text();
|
|
184433
|
+
writeLog("api:error", `Failed to parse error response: ${errorBody}`);
|
|
184434
|
+
throw new Error(`Failed to list organizations: ${response.statusText}`);
|
|
184435
|
+
}
|
|
184436
|
+
}
|
|
184437
|
+
return response.json();
|
|
184438
|
+
}
|
|
184402
184439
|
async getMe(signal) {
|
|
184403
184440
|
const url = `${this.baseUrl}/users/me`;
|
|
184404
184441
|
writeLog("api", `GET ${url}`);
|
|
@@ -184587,7 +184624,7 @@ function trackEvent(event, properties) {
|
|
|
184587
184624
|
event,
|
|
184588
184625
|
properties: {
|
|
184589
184626
|
...properties,
|
|
184590
|
-
cli_version: "0.1.
|
|
184627
|
+
cli_version: "0.1.75",
|
|
184591
184628
|
platform: process.platform,
|
|
184592
184629
|
node_version: process.version,
|
|
184593
184630
|
project_id: getProjectId()
|
|
@@ -186048,10 +186085,10 @@ async function downloadFile(url, destPath, onProgress) {
|
|
|
186048
186085
|
});
|
|
186049
186086
|
}
|
|
186050
186087
|
}
|
|
186051
|
-
await new Promise((
|
|
186088
|
+
await new Promise((resolve9, reject) => {
|
|
186052
186089
|
fileStream.end((err) => {
|
|
186053
186090
|
if (err) reject(err);
|
|
186054
|
-
else
|
|
186091
|
+
else resolve9();
|
|
186055
186092
|
});
|
|
186056
186093
|
});
|
|
186057
186094
|
fs13.renameSync(partPath, destPath);
|
|
@@ -186277,13 +186314,13 @@ async function runReshapeCheck(migrationsDir) {
|
|
|
186277
186314
|
try {
|
|
186278
186315
|
const binary = await ensureBinary(reshapeBinary);
|
|
186279
186316
|
const reshapePath = binary.executables["reshape"];
|
|
186280
|
-
return new Promise((
|
|
186317
|
+
return new Promise((resolve9) => {
|
|
186281
186318
|
execFile7(reshapePath, ["check", "--dirs", migrationsDir], (err, _stdout, stderr) => {
|
|
186282
186319
|
if (err) {
|
|
186283
186320
|
const errorMsg = stderr.trim() || err.message;
|
|
186284
|
-
|
|
186321
|
+
resolve9({ success: false, error: errorMsg });
|
|
186285
186322
|
} else {
|
|
186286
|
-
|
|
186323
|
+
resolve9({ success: true });
|
|
186287
186324
|
}
|
|
186288
186325
|
});
|
|
186289
186326
|
});
|
|
@@ -187252,7 +187289,7 @@ var NodeFsHandler = class {
|
|
|
187252
187289
|
this._addToNodeFs(path30, initialAdd, wh, depth + 1);
|
|
187253
187290
|
}
|
|
187254
187291
|
}).on(EV.ERROR, this._boundHandleError);
|
|
187255
|
-
return new Promise((
|
|
187292
|
+
return new Promise((resolve9, reject) => {
|
|
187256
187293
|
if (!stream)
|
|
187257
187294
|
return reject();
|
|
187258
187295
|
stream.once(STR_END, () => {
|
|
@@ -187261,7 +187298,7 @@ var NodeFsHandler = class {
|
|
|
187261
187298
|
return;
|
|
187262
187299
|
}
|
|
187263
187300
|
const wasThrottled = throttler ? throttler.clear() : false;
|
|
187264
|
-
|
|
187301
|
+
resolve9(void 0);
|
|
187265
187302
|
previous.getChildren().filter((item) => {
|
|
187266
187303
|
return item !== directory && !current.has(item);
|
|
187267
187304
|
}).forEach((item) => {
|
|
@@ -188325,7 +188362,7 @@ async function startStorage(storage, port, dataDir) {
|
|
|
188325
188362
|
};
|
|
188326
188363
|
}
|
|
188327
188364
|
async function runCommand(command, args, env2) {
|
|
188328
|
-
return new Promise((
|
|
188365
|
+
return new Promise((resolve9, reject) => {
|
|
188329
188366
|
const proc = spawn(command, args, {
|
|
188330
188367
|
stdio: ["ignore", "pipe", "pipe"],
|
|
188331
188368
|
env: env2
|
|
@@ -188336,7 +188373,7 @@ async function runCommand(command, args, env2) {
|
|
|
188336
188373
|
});
|
|
188337
188374
|
proc.on("close", (code) => {
|
|
188338
188375
|
if (code === 0) {
|
|
188339
|
-
|
|
188376
|
+
resolve9();
|
|
188340
188377
|
} else {
|
|
188341
188378
|
reject(new Error(`Command failed with code ${code}: ${stderr}`));
|
|
188342
188379
|
}
|
|
@@ -188345,7 +188382,7 @@ async function runCommand(command, args, env2) {
|
|
|
188345
188382
|
});
|
|
188346
188383
|
}
|
|
188347
188384
|
async function createPostgresDatabase(postgresPath, dataDir, dbName, env2) {
|
|
188348
|
-
return new Promise((
|
|
188385
|
+
return new Promise((resolve9, reject) => {
|
|
188349
188386
|
const proc = spawn(
|
|
188350
188387
|
postgresPath,
|
|
188351
188388
|
["--single", "-D", dataDir, "postgres"],
|
|
@@ -188359,7 +188396,7 @@ async function createPostgresDatabase(postgresPath, dataDir, dbName, env2) {
|
|
|
188359
188396
|
stderr += data.toString();
|
|
188360
188397
|
});
|
|
188361
188398
|
proc.on("close", (code) => {
|
|
188362
|
-
|
|
188399
|
+
resolve9();
|
|
188363
188400
|
});
|
|
188364
188401
|
proc.on("error", reject);
|
|
188365
188402
|
proc.stdin?.write(`CREATE DATABASE "${dbName}";
|
|
@@ -188379,33 +188416,33 @@ async function waitForTcpPort(host, port, timeoutMs = 3e4) {
|
|
|
188379
188416
|
throw new Error(`Port ${port} did not become available within timeout`);
|
|
188380
188417
|
}
|
|
188381
188418
|
function checkTcpPort(host, port) {
|
|
188382
|
-
return new Promise((
|
|
188419
|
+
return new Promise((resolve9) => {
|
|
188383
188420
|
const socket = new net.Socket();
|
|
188384
188421
|
socket.setTimeout(1e3);
|
|
188385
188422
|
socket.on("connect", () => {
|
|
188386
188423
|
socket.destroy();
|
|
188387
|
-
|
|
188424
|
+
resolve9(true);
|
|
188388
188425
|
});
|
|
188389
188426
|
socket.on("timeout", () => {
|
|
188390
188427
|
socket.destroy();
|
|
188391
|
-
|
|
188428
|
+
resolve9(false);
|
|
188392
188429
|
});
|
|
188393
188430
|
socket.on("error", () => {
|
|
188394
188431
|
socket.destroy();
|
|
188395
|
-
|
|
188432
|
+
resolve9(false);
|
|
188396
188433
|
});
|
|
188397
188434
|
socket.connect(port, host);
|
|
188398
188435
|
});
|
|
188399
188436
|
}
|
|
188400
188437
|
async function stopProcess(proc) {
|
|
188401
|
-
return new Promise((
|
|
188438
|
+
return new Promise((resolve9) => {
|
|
188402
188439
|
if (proc.killed || proc.exitCode !== null) {
|
|
188403
|
-
|
|
188440
|
+
resolve9();
|
|
188404
188441
|
return;
|
|
188405
188442
|
}
|
|
188406
188443
|
proc.once("exit", () => {
|
|
188407
188444
|
clearTimeout(forceKillTimeout);
|
|
188408
|
-
|
|
188445
|
+
resolve9();
|
|
188409
188446
|
});
|
|
188410
188447
|
proc.kill("SIGTERM");
|
|
188411
188448
|
const forceKillTimeout = setTimeout(() => {
|
|
@@ -188416,7 +188453,7 @@ async function stopProcess(proc) {
|
|
|
188416
188453
|
});
|
|
188417
188454
|
}
|
|
188418
188455
|
function sleep2(ms) {
|
|
188419
|
-
return new Promise((
|
|
188456
|
+
return new Promise((resolve9) => setTimeout(resolve9, ms));
|
|
188420
188457
|
}
|
|
188421
188458
|
|
|
188422
188459
|
// src/lib/dev/service-runner.ts
|
|
@@ -188900,14 +188937,14 @@ function startService(service, resources, secrets, configs, endpointPorts, servi
|
|
|
188900
188937
|
ports: endpointPorts,
|
|
188901
188938
|
process: child,
|
|
188902
188939
|
async stop() {
|
|
188903
|
-
return new Promise((
|
|
188940
|
+
return new Promise((resolve9) => {
|
|
188904
188941
|
if (child.killed || child.exitCode !== null) {
|
|
188905
|
-
|
|
188942
|
+
resolve9();
|
|
188906
188943
|
return;
|
|
188907
188944
|
}
|
|
188908
188945
|
child.once("exit", () => {
|
|
188909
188946
|
clearTimeout(forceKillTimeout);
|
|
188910
|
-
|
|
188947
|
+
resolve9();
|
|
188911
188948
|
});
|
|
188912
188949
|
const pid = child.pid;
|
|
188913
188950
|
if (pid) {
|
|
@@ -189001,7 +189038,7 @@ var InstanceStateManager = class {
|
|
|
189001
189038
|
}
|
|
189002
189039
|
continue;
|
|
189003
189040
|
}
|
|
189004
|
-
await new Promise((
|
|
189041
|
+
await new Promise((resolve9) => setTimeout(resolve9, 100));
|
|
189005
189042
|
} else {
|
|
189006
189043
|
throw e;
|
|
189007
189044
|
}
|
|
@@ -189334,7 +189371,7 @@ async function startHttpProxy(services, certificate, getState, instanceKey = "de
|
|
|
189334
189371
|
handleRequest
|
|
189335
189372
|
);
|
|
189336
189373
|
httpsServer.on("upgrade", handleUpgrade);
|
|
189337
|
-
return new Promise((
|
|
189374
|
+
return new Promise((resolve9, reject) => {
|
|
189338
189375
|
let httpStarted = false;
|
|
189339
189376
|
let httpsStarted = false;
|
|
189340
189377
|
let failed = false;
|
|
@@ -189345,7 +189382,7 @@ async function startHttpProxy(services, certificate, getState, instanceKey = "de
|
|
|
189345
189382
|
"proxy",
|
|
189346
189383
|
`HTTP/HTTPS proxy started on ports ${HTTP_PORT}/${HTTPS_PORT}`
|
|
189347
189384
|
);
|
|
189348
|
-
|
|
189385
|
+
resolve9({
|
|
189349
189386
|
httpPort: HTTP_PORT,
|
|
189350
189387
|
httpsPort: HTTPS_PORT,
|
|
189351
189388
|
updateServices,
|
|
@@ -189357,13 +189394,13 @@ async function startHttpProxy(services, certificate, getState, instanceKey = "de
|
|
|
189357
189394
|
writeLog("proxy", "Certificate updated");
|
|
189358
189395
|
},
|
|
189359
189396
|
async stop() {
|
|
189360
|
-
return new Promise((
|
|
189397
|
+
return new Promise((resolve10) => {
|
|
189361
189398
|
let closed = 0;
|
|
189362
189399
|
const onClose = () => {
|
|
189363
189400
|
closed++;
|
|
189364
189401
|
if (closed === 2) {
|
|
189365
189402
|
clearTimeout(forceCloseTimeout);
|
|
189366
|
-
|
|
189403
|
+
resolve10();
|
|
189367
189404
|
}
|
|
189368
189405
|
};
|
|
189369
189406
|
httpServer.close(onClose);
|
|
@@ -189371,7 +189408,7 @@ async function startHttpProxy(services, certificate, getState, instanceKey = "de
|
|
|
189371
189408
|
const forceCloseTimeout = setTimeout(() => {
|
|
189372
189409
|
httpServer.closeAllConnections?.();
|
|
189373
189410
|
httpsServer.closeAllConnections?.();
|
|
189374
|
-
|
|
189411
|
+
resolve10();
|
|
189375
189412
|
}, 2e3);
|
|
189376
189413
|
});
|
|
189377
189414
|
}
|
|
@@ -189599,7 +189636,7 @@ function serveFileContent(res, filePath, contentType, statusCode = 200) {
|
|
|
189599
189636
|
}
|
|
189600
189637
|
}
|
|
189601
189638
|
async function startAdminServer(getState) {
|
|
189602
|
-
return new Promise((
|
|
189639
|
+
return new Promise((resolve9, reject) => {
|
|
189603
189640
|
const server = http.createServer((req, res) => {
|
|
189604
189641
|
const url = new URL(req.url || "/", "http://localhost");
|
|
189605
189642
|
res.setHeader("Access-Control-Allow-Origin", "*");
|
|
@@ -189631,7 +189668,7 @@ async function startAdminServer(getState) {
|
|
|
189631
189668
|
}
|
|
189632
189669
|
const port = addr.port;
|
|
189633
189670
|
writeLog("admin", `Admin API server started on port ${port}`);
|
|
189634
|
-
|
|
189671
|
+
resolve9({
|
|
189635
189672
|
port,
|
|
189636
189673
|
stop: () => new Promise((res, rej) => {
|
|
189637
189674
|
server.close((err) => err ? rej(err) : res());
|
|
@@ -189792,33 +189829,33 @@ async function waitForTcpPort2(host, port, timeoutMs = 3e4) {
|
|
|
189792
189829
|
throw new Error(`Electric port ${port} did not become available within timeout`);
|
|
189793
189830
|
}
|
|
189794
189831
|
function checkTcpPort2(host, port) {
|
|
189795
|
-
return new Promise((
|
|
189832
|
+
return new Promise((resolve9) => {
|
|
189796
189833
|
const socket = new net2.Socket();
|
|
189797
189834
|
socket.setTimeout(1e3);
|
|
189798
189835
|
socket.on("connect", () => {
|
|
189799
189836
|
socket.destroy();
|
|
189800
|
-
|
|
189837
|
+
resolve9(true);
|
|
189801
189838
|
});
|
|
189802
189839
|
socket.on("timeout", () => {
|
|
189803
189840
|
socket.destroy();
|
|
189804
|
-
|
|
189841
|
+
resolve9(false);
|
|
189805
189842
|
});
|
|
189806
189843
|
socket.on("error", () => {
|
|
189807
189844
|
socket.destroy();
|
|
189808
|
-
|
|
189845
|
+
resolve9(false);
|
|
189809
189846
|
});
|
|
189810
189847
|
socket.connect(port, host);
|
|
189811
189848
|
});
|
|
189812
189849
|
}
|
|
189813
189850
|
async function stopProcess2(proc) {
|
|
189814
|
-
return new Promise((
|
|
189851
|
+
return new Promise((resolve9) => {
|
|
189815
189852
|
if (proc.killed || proc.exitCode !== null) {
|
|
189816
|
-
|
|
189853
|
+
resolve9();
|
|
189817
189854
|
return;
|
|
189818
189855
|
}
|
|
189819
189856
|
proc.once("exit", () => {
|
|
189820
189857
|
clearTimeout(forceKillTimeout);
|
|
189821
|
-
|
|
189858
|
+
resolve9();
|
|
189822
189859
|
});
|
|
189823
189860
|
proc.kill("SIGTERM");
|
|
189824
189861
|
const forceKillTimeout = setTimeout(() => {
|
|
@@ -189829,7 +189866,7 @@ async function stopProcess2(proc) {
|
|
|
189829
189866
|
});
|
|
189830
189867
|
}
|
|
189831
189868
|
function sleep3(ms) {
|
|
189832
|
-
return new Promise((
|
|
189869
|
+
return new Promise((resolve9) => setTimeout(resolve9, ms));
|
|
189833
189870
|
}
|
|
189834
189871
|
|
|
189835
189872
|
// src/lib/dev/mail-manager.ts
|
|
@@ -189924,20 +189961,20 @@ async function startMailServer(mail, smtpPort, apiPort) {
|
|
|
189924
189961
|
res.writeHead(404);
|
|
189925
189962
|
res.end();
|
|
189926
189963
|
});
|
|
189927
|
-
await new Promise((
|
|
189928
|
-
smtpServer.listen(smtpPort, "127.0.0.1", () =>
|
|
189964
|
+
await new Promise((resolve9, reject) => {
|
|
189965
|
+
smtpServer.listen(smtpPort, "127.0.0.1", () => resolve9());
|
|
189929
189966
|
smtpServer.on("error", reject);
|
|
189930
189967
|
});
|
|
189931
|
-
await new Promise((
|
|
189932
|
-
httpServer.listen(apiPort, "127.0.0.1", () =>
|
|
189968
|
+
await new Promise((resolve9, reject) => {
|
|
189969
|
+
httpServer.listen(apiPort, "127.0.0.1", () => resolve9());
|
|
189933
189970
|
httpServer.on("error", reject);
|
|
189934
189971
|
});
|
|
189935
189972
|
const stop = async () => {
|
|
189936
|
-
await new Promise((
|
|
189937
|
-
smtpServer.close(() =>
|
|
189973
|
+
await new Promise((resolve9) => {
|
|
189974
|
+
smtpServer.close(() => resolve9());
|
|
189938
189975
|
});
|
|
189939
|
-
await new Promise((
|
|
189940
|
-
httpServer.close(() =>
|
|
189976
|
+
await new Promise((resolve9) => {
|
|
189977
|
+
httpServer.close(() => resolve9());
|
|
189941
189978
|
});
|
|
189942
189979
|
};
|
|
189943
189980
|
const resource = {
|
|
@@ -190041,33 +190078,33 @@ async function waitForTcpPort3(host, port, timeoutMs = 3e4) {
|
|
|
190041
190078
|
);
|
|
190042
190079
|
}
|
|
190043
190080
|
function checkTcpPort3(host, port) {
|
|
190044
|
-
return new Promise((
|
|
190081
|
+
return new Promise((resolve9) => {
|
|
190045
190082
|
const socket = new net3.Socket();
|
|
190046
190083
|
socket.setTimeout(1e3);
|
|
190047
190084
|
socket.on("connect", () => {
|
|
190048
190085
|
socket.destroy();
|
|
190049
|
-
|
|
190086
|
+
resolve9(true);
|
|
190050
190087
|
});
|
|
190051
190088
|
socket.on("timeout", () => {
|
|
190052
190089
|
socket.destroy();
|
|
190053
|
-
|
|
190090
|
+
resolve9(false);
|
|
190054
190091
|
});
|
|
190055
190092
|
socket.on("error", () => {
|
|
190056
190093
|
socket.destroy();
|
|
190057
|
-
|
|
190094
|
+
resolve9(false);
|
|
190058
190095
|
});
|
|
190059
190096
|
socket.connect(port, host);
|
|
190060
190097
|
});
|
|
190061
190098
|
}
|
|
190062
190099
|
async function stopProcess3(proc) {
|
|
190063
|
-
return new Promise((
|
|
190100
|
+
return new Promise((resolve9) => {
|
|
190064
190101
|
if (proc.killed || proc.exitCode !== null) {
|
|
190065
|
-
|
|
190102
|
+
resolve9();
|
|
190066
190103
|
return;
|
|
190067
190104
|
}
|
|
190068
190105
|
proc.once("exit", () => {
|
|
190069
190106
|
clearTimeout(forceKillTimeout);
|
|
190070
|
-
|
|
190107
|
+
resolve9();
|
|
190071
190108
|
});
|
|
190072
190109
|
proc.kill("SIGTERM");
|
|
190073
190110
|
const forceKillTimeout = setTimeout(() => {
|
|
@@ -190078,7 +190115,7 @@ async function stopProcess3(proc) {
|
|
|
190078
190115
|
});
|
|
190079
190116
|
}
|
|
190080
190117
|
function sleep4(ms) {
|
|
190081
|
-
return new Promise((
|
|
190118
|
+
return new Promise((resolve9) => setTimeout(resolve9, ms));
|
|
190082
190119
|
}
|
|
190083
190120
|
|
|
190084
190121
|
// src/lib/dev/sync-detector.ts
|
|
@@ -190443,38 +190480,38 @@ async function waitForTcpPort4(host, port, timeoutMs = 3e4) {
|
|
|
190443
190480
|
if (isOpen) {
|
|
190444
190481
|
return;
|
|
190445
190482
|
}
|
|
190446
|
-
await new Promise((
|
|
190483
|
+
await new Promise((resolve9) => setTimeout(resolve9, 100));
|
|
190447
190484
|
}
|
|
190448
190485
|
throw new Error(`Temporal port ${port} did not become available within timeout`);
|
|
190449
190486
|
}
|
|
190450
190487
|
function checkTcpPort4(host, port) {
|
|
190451
|
-
return new Promise((
|
|
190488
|
+
return new Promise((resolve9) => {
|
|
190452
190489
|
const socket = new net4.Socket();
|
|
190453
190490
|
socket.setTimeout(1e3);
|
|
190454
190491
|
socket.on("connect", () => {
|
|
190455
190492
|
socket.destroy();
|
|
190456
|
-
|
|
190493
|
+
resolve9(true);
|
|
190457
190494
|
});
|
|
190458
190495
|
socket.on("timeout", () => {
|
|
190459
190496
|
socket.destroy();
|
|
190460
|
-
|
|
190497
|
+
resolve9(false);
|
|
190461
190498
|
});
|
|
190462
190499
|
socket.on("error", () => {
|
|
190463
190500
|
socket.destroy();
|
|
190464
|
-
|
|
190501
|
+
resolve9(false);
|
|
190465
190502
|
});
|
|
190466
190503
|
socket.connect(port, host);
|
|
190467
190504
|
});
|
|
190468
190505
|
}
|
|
190469
190506
|
async function stopProcess4(proc) {
|
|
190470
|
-
return new Promise((
|
|
190507
|
+
return new Promise((resolve9) => {
|
|
190471
190508
|
if (proc.killed || proc.exitCode !== null) {
|
|
190472
|
-
|
|
190509
|
+
resolve9();
|
|
190473
190510
|
return;
|
|
190474
190511
|
}
|
|
190475
190512
|
proc.once("exit", () => {
|
|
190476
190513
|
clearTimeout(forceKillTimeout);
|
|
190477
|
-
|
|
190514
|
+
resolve9();
|
|
190478
190515
|
});
|
|
190479
190516
|
proc.kill("SIGTERM");
|
|
190480
190517
|
const forceKillTimeout = setTimeout(() => {
|
|
@@ -190949,7 +190986,7 @@ var ProxyRegistryManager = class {
|
|
|
190949
190986
|
* This catches cases where the owner process is alive but the proxy has crashed.
|
|
190950
190987
|
*/
|
|
190951
190988
|
isProxyListening(port, timeoutMs = 1e3) {
|
|
190952
|
-
return new Promise((
|
|
190989
|
+
return new Promise((resolve9) => {
|
|
190953
190990
|
const socket = new net6.Socket();
|
|
190954
190991
|
let resolved = false;
|
|
190955
190992
|
const cleanup = () => {
|
|
@@ -190961,15 +190998,15 @@ var ProxyRegistryManager = class {
|
|
|
190961
190998
|
socket.setTimeout(timeoutMs);
|
|
190962
190999
|
socket.on("connect", () => {
|
|
190963
191000
|
cleanup();
|
|
190964
|
-
|
|
191001
|
+
resolve9(true);
|
|
190965
191002
|
});
|
|
190966
191003
|
socket.on("timeout", () => {
|
|
190967
191004
|
cleanup();
|
|
190968
|
-
|
|
191005
|
+
resolve9(false);
|
|
190969
191006
|
});
|
|
190970
191007
|
socket.on("error", () => {
|
|
190971
191008
|
cleanup();
|
|
190972
|
-
|
|
191009
|
+
resolve9(false);
|
|
190973
191010
|
});
|
|
190974
191011
|
socket.connect(port, "127.0.0.1");
|
|
190975
191012
|
});
|
|
@@ -191020,7 +191057,7 @@ var ProxyRegistryManager = class {
|
|
|
191020
191057
|
}
|
|
191021
191058
|
continue;
|
|
191022
191059
|
}
|
|
191023
|
-
await new Promise((
|
|
191060
|
+
await new Promise((resolve9) => setTimeout(resolve9, 100));
|
|
191024
191061
|
} else {
|
|
191025
191062
|
throw e;
|
|
191026
191063
|
}
|
|
@@ -192697,186 +192734,6 @@ import Spinner5 from "ink-spinner";
|
|
|
192697
192734
|
import * as fs26 from "fs";
|
|
192698
192735
|
import * as path23 from "path";
|
|
192699
192736
|
|
|
192700
|
-
// src/lib/deploy/build-tester.ts
|
|
192701
|
-
import { spawn as spawn6 } from "child_process";
|
|
192702
|
-
import { existsSync as existsSync22 } from "fs";
|
|
192703
|
-
import { join as join23, resolve as resolve7 } from "path";
|
|
192704
|
-
function getDependencyInstallCommand(build, projectDir) {
|
|
192705
|
-
if (!build.base) return null;
|
|
192706
|
-
switch (build.base) {
|
|
192707
|
-
case "node":
|
|
192708
|
-
if (existsSync22(join23(projectDir, "pnpm-lock.yaml"))) {
|
|
192709
|
-
return "pnpm install --frozen-lockfile";
|
|
192710
|
-
} else if (existsSync22(join23(projectDir, "yarn.lock"))) {
|
|
192711
|
-
return "yarn install --frozen-lockfile";
|
|
192712
|
-
} else if (existsSync22(join23(projectDir, "package-lock.json"))) {
|
|
192713
|
-
return "npm ci";
|
|
192714
|
-
} else if (existsSync22(join23(projectDir, "package.json"))) {
|
|
192715
|
-
return "npm install";
|
|
192716
|
-
}
|
|
192717
|
-
return null;
|
|
192718
|
-
case "python":
|
|
192719
|
-
if (existsSync22(join23(projectDir, "poetry.lock"))) {
|
|
192720
|
-
return "poetry install --no-interaction";
|
|
192721
|
-
} else if (existsSync22(join23(projectDir, "Pipfile.lock"))) {
|
|
192722
|
-
return "pipenv install --deploy";
|
|
192723
|
-
} else if (existsSync22(join23(projectDir, "Pipfile"))) {
|
|
192724
|
-
return "pipenv install";
|
|
192725
|
-
} else if (existsSync22(join23(projectDir, "pyproject.toml"))) {
|
|
192726
|
-
return "pip install .";
|
|
192727
|
-
} else if (existsSync22(join23(projectDir, "requirements.txt"))) {
|
|
192728
|
-
return "pip install -r requirements.txt";
|
|
192729
|
-
}
|
|
192730
|
-
return null;
|
|
192731
|
-
case "go":
|
|
192732
|
-
return "go mod download";
|
|
192733
|
-
case "rust":
|
|
192734
|
-
case "java":
|
|
192735
|
-
return null;
|
|
192736
|
-
default:
|
|
192737
|
-
return null;
|
|
192738
|
-
}
|
|
192739
|
-
}
|
|
192740
|
-
function runCommand2(command, projectDir, buildName) {
|
|
192741
|
-
return new Promise((resolve10) => {
|
|
192742
|
-
const stdout = [];
|
|
192743
|
-
const stderr = [];
|
|
192744
|
-
writeLog("build-test", `[${buildName}] Running: ${command}`);
|
|
192745
|
-
const child = spawn6(command, {
|
|
192746
|
-
shell: true,
|
|
192747
|
-
cwd: projectDir,
|
|
192748
|
-
env: { ...process.env },
|
|
192749
|
-
stdio: ["ignore", "pipe", "pipe"]
|
|
192750
|
-
});
|
|
192751
|
-
child.stdout?.on("data", (data) => {
|
|
192752
|
-
const text = data.toString();
|
|
192753
|
-
stdout.push(text);
|
|
192754
|
-
for (const line of text.split("\n")) {
|
|
192755
|
-
if (line.trim()) {
|
|
192756
|
-
writeLog(`build-test:${buildName}`, line);
|
|
192757
|
-
}
|
|
192758
|
-
}
|
|
192759
|
-
});
|
|
192760
|
-
child.stderr?.on("data", (data) => {
|
|
192761
|
-
const text = data.toString();
|
|
192762
|
-
stderr.push(text);
|
|
192763
|
-
for (const line of text.split("\n")) {
|
|
192764
|
-
if (line.trim()) {
|
|
192765
|
-
writeLog(`build-test:${buildName}`, line);
|
|
192766
|
-
}
|
|
192767
|
-
}
|
|
192768
|
-
});
|
|
192769
|
-
child.on("error", (err) => {
|
|
192770
|
-
writeLog("build-test:error", `[${buildName}] Failed to start: ${err.message}`);
|
|
192771
|
-
resolve10({
|
|
192772
|
-
success: false,
|
|
192773
|
-
output: `Failed to start command: ${err.message}`
|
|
192774
|
-
});
|
|
192775
|
-
});
|
|
192776
|
-
child.on("exit", (code) => {
|
|
192777
|
-
const output = [...stdout, ...stderr].join("");
|
|
192778
|
-
if (code === 0) {
|
|
192779
|
-
writeLog("build-test", `[${buildName}] Command succeeded (exit code 0)`);
|
|
192780
|
-
resolve10({ success: true, output });
|
|
192781
|
-
} else {
|
|
192782
|
-
writeLog("build-test:error", `[${buildName}] Command failed with exit code ${code}`);
|
|
192783
|
-
resolve10({
|
|
192784
|
-
success: false,
|
|
192785
|
-
output: output || `Exit code: ${code}`
|
|
192786
|
-
});
|
|
192787
|
-
}
|
|
192788
|
-
});
|
|
192789
|
-
});
|
|
192790
|
-
}
|
|
192791
|
-
async function testBuild(build, projectDir) {
|
|
192792
|
-
const startTime = Date.now();
|
|
192793
|
-
if (build.dockerfile) {
|
|
192794
|
-
writeLog("build-test", `Skipping test for build "${build.name}" (custom Dockerfile)`);
|
|
192795
|
-
return {
|
|
192796
|
-
buildName: build.name,
|
|
192797
|
-
success: true,
|
|
192798
|
-
output: "Skipped: custom Dockerfile build",
|
|
192799
|
-
durationMs: Date.now() - startTime
|
|
192800
|
-
};
|
|
192801
|
-
}
|
|
192802
|
-
const outputs = [];
|
|
192803
|
-
const workDir = build.root ? resolve7(projectDir, build.root) : projectDir;
|
|
192804
|
-
writeLog("build-test", `Starting test for build "${build.name}" (base: ${build.base}, workDir: ${workDir})`);
|
|
192805
|
-
const depsCommand = getDependencyInstallCommand(build, workDir);
|
|
192806
|
-
if (depsCommand) {
|
|
192807
|
-
writeLog("build-test", `[${build.name}] Installing dependencies...`);
|
|
192808
|
-
const depsResult = await runCommand2(depsCommand, workDir, build.name);
|
|
192809
|
-
outputs.push(`[${depsCommand}]
|
|
192810
|
-
${depsResult.output}`);
|
|
192811
|
-
if (!depsResult.success) {
|
|
192812
|
-
const duration2 = Date.now() - startTime;
|
|
192813
|
-
writeLog("build-test:error", `[${build.name}] Dependency installation failed after ${duration2}ms`);
|
|
192814
|
-
return {
|
|
192815
|
-
buildName: build.name,
|
|
192816
|
-
success: false,
|
|
192817
|
-
output: outputs.join("\n\n"),
|
|
192818
|
-
durationMs: duration2
|
|
192819
|
-
};
|
|
192820
|
-
}
|
|
192821
|
-
writeLog("build-test", `[${build.name}] Dependencies installed successfully`);
|
|
192822
|
-
} else {
|
|
192823
|
-
writeLog("build-test", `[${build.name}] No dependency installation needed for base "${build.base}"`);
|
|
192824
|
-
}
|
|
192825
|
-
if (build.command) {
|
|
192826
|
-
writeLog("build-test", `[${build.name}] Running build command...`);
|
|
192827
|
-
const buildResult = await runCommand2(build.command, workDir, build.name);
|
|
192828
|
-
outputs.push(`[${build.command}]
|
|
192829
|
-
${buildResult.output}`);
|
|
192830
|
-
if (!buildResult.success) {
|
|
192831
|
-
const duration2 = Date.now() - startTime;
|
|
192832
|
-
writeLog("build-test:error", `[${build.name}] Build command failed after ${duration2}ms`);
|
|
192833
|
-
return {
|
|
192834
|
-
buildName: build.name,
|
|
192835
|
-
success: false,
|
|
192836
|
-
output: outputs.join("\n\n"),
|
|
192837
|
-
durationMs: duration2
|
|
192838
|
-
};
|
|
192839
|
-
}
|
|
192840
|
-
writeLog("build-test", `[${build.name}] Build command completed successfully`);
|
|
192841
|
-
} else {
|
|
192842
|
-
writeLog("build-test", `[${build.name}] No build command defined, skipping`);
|
|
192843
|
-
}
|
|
192844
|
-
const duration = Date.now() - startTime;
|
|
192845
|
-
writeLog("build-test", `[${build.name}] Build test passed in ${duration}ms`);
|
|
192846
|
-
return {
|
|
192847
|
-
buildName: build.name,
|
|
192848
|
-
success: true,
|
|
192849
|
-
output: outputs.join("\n\n"),
|
|
192850
|
-
durationMs: duration
|
|
192851
|
-
};
|
|
192852
|
-
}
|
|
192853
|
-
async function testAllBuilds(builds, projectDir) {
|
|
192854
|
-
if (builds.length === 0) {
|
|
192855
|
-
writeLog("build-test", "No builds to test");
|
|
192856
|
-
return { results: [], allPassed: true };
|
|
192857
|
-
}
|
|
192858
|
-
writeLog("build-test", `Testing ${builds.length} build(s) in parallel: ${builds.map((b) => b.name).join(", ")}`);
|
|
192859
|
-
writeLog("build-test", `Project directory: ${projectDir}`);
|
|
192860
|
-
const results = await Promise.all(
|
|
192861
|
-
builds.map((build) => testBuild(build, projectDir))
|
|
192862
|
-
);
|
|
192863
|
-
const passed = results.filter((r) => r.success).length;
|
|
192864
|
-
const failed = results.filter((r) => !r.success).length;
|
|
192865
|
-
const totalDuration = results.reduce((sum, r) => sum + r.durationMs, 0);
|
|
192866
|
-
if (failed > 0) {
|
|
192867
|
-
writeLog("build-test:error", `Build tests completed: ${passed} passed, ${failed} failed`);
|
|
192868
|
-
for (const result of results.filter((r) => !r.success)) {
|
|
192869
|
-
writeLog("build-test:error", `Failed build: ${result.buildName}`);
|
|
192870
|
-
}
|
|
192871
|
-
} else {
|
|
192872
|
-
writeLog("build-test", `All ${passed} build(s) passed (total: ${totalDuration}ms)`);
|
|
192873
|
-
}
|
|
192874
|
-
return {
|
|
192875
|
-
results,
|
|
192876
|
-
allPassed: results.every((r) => r.success)
|
|
192877
|
-
};
|
|
192878
|
-
}
|
|
192879
|
-
|
|
192880
192737
|
// src/lib/tarball/create.ts
|
|
192881
192738
|
import { execSync as execSync4 } from "child_process";
|
|
192882
192739
|
import * as fs25 from "fs";
|
|
@@ -193017,7 +192874,6 @@ function PhaseIndicator({
|
|
|
193017
192874
|
showSpinner = true
|
|
193018
192875
|
}) {
|
|
193019
192876
|
const phases = [
|
|
193020
|
-
"testing-builds",
|
|
193021
192877
|
"creating-tarball",
|
|
193022
192878
|
"creating-deployment",
|
|
193023
192879
|
"uploading",
|
|
@@ -193047,22 +192903,35 @@ function PhaseIndicator({
|
|
|
193047
192903
|
}
|
|
193048
192904
|
return /* @__PURE__ */ React7.createElement(Text7, null, /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, " ", "\u25CB"), " ", /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, label));
|
|
193049
192905
|
}
|
|
192906
|
+
function buildSelectorItems(projects, organizations) {
|
|
192907
|
+
const items = [];
|
|
192908
|
+
for (const org of organizations) {
|
|
192909
|
+
items.push({ type: "header", orgName: org.name });
|
|
192910
|
+
items.push({ type: "new", orgId: org.id });
|
|
192911
|
+
const orgProjects = projects.filter((p) => p.organizationId === org.id);
|
|
192912
|
+
for (const project of orgProjects) {
|
|
192913
|
+
items.push({ type: "project", project });
|
|
192914
|
+
}
|
|
192915
|
+
}
|
|
192916
|
+
return items;
|
|
192917
|
+
}
|
|
193050
192918
|
function ProjectSelector({
|
|
193051
192919
|
projects,
|
|
192920
|
+
organizations,
|
|
193052
192921
|
selectedIndex,
|
|
193053
192922
|
onSelect,
|
|
193054
192923
|
onUp,
|
|
193055
192924
|
onDown
|
|
193056
192925
|
}) {
|
|
192926
|
+
const items = buildSelectorItems(projects, organizations);
|
|
192927
|
+
const selectableIndices = items.map((item, index) => item.type !== "header" ? index : -1).filter((i) => i >= 0);
|
|
193057
192928
|
useInput5((input, key) => {
|
|
193058
192929
|
if (key.return) {
|
|
193059
|
-
|
|
193060
|
-
|
|
193061
|
-
|
|
193062
|
-
|
|
193063
|
-
|
|
193064
|
-
onSelect(project);
|
|
193065
|
-
}
|
|
192930
|
+
const item = items[selectedIndex];
|
|
192931
|
+
if (item?.type === "new") {
|
|
192932
|
+
onSelect({ type: "new", orgId: item.orgId });
|
|
192933
|
+
} else if (item?.type === "project") {
|
|
192934
|
+
onSelect(item.project);
|
|
193066
192935
|
}
|
|
193067
192936
|
} else if (key.upArrow) {
|
|
193068
192937
|
onUp();
|
|
@@ -193070,11 +192939,16 @@ function ProjectSelector({
|
|
|
193070
192939
|
onDown();
|
|
193071
192940
|
}
|
|
193072
192941
|
});
|
|
193073
|
-
|
|
193074
|
-
|
|
193075
|
-
|
|
193076
|
-
|
|
193077
|
-
|
|
192942
|
+
return /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column", gap: 1 }, /* @__PURE__ */ React7.createElement(Text7, { bold: true }, "Select a project to deploy:"), /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column" }, items.map((item, index) => {
|
|
192943
|
+
if (item.type === "header") {
|
|
192944
|
+
return /* @__PURE__ */ React7.createElement(Text7, { key: `header-${item.orgName}` }, index > 0 ? "\n" : "", /* @__PURE__ */ React7.createElement(Text7, { bold: true }, item.orgName));
|
|
192945
|
+
}
|
|
192946
|
+
const isSelected = index === selectedIndex;
|
|
192947
|
+
if (item.type === "new") {
|
|
192948
|
+
return /* @__PURE__ */ React7.createElement(Text7, { key: `new-${item.orgId}` }, isSelected ? /* @__PURE__ */ React7.createElement(Text7, { color: "cyan" }, " ", "> ") : /* @__PURE__ */ React7.createElement(Text7, null, " "), /* @__PURE__ */ React7.createElement(Text7, { color: "green" }, "Create new project"));
|
|
192949
|
+
}
|
|
192950
|
+
return /* @__PURE__ */ React7.createElement(Text7, { key: item.project.id }, isSelected ? /* @__PURE__ */ React7.createElement(Text7, { color: "cyan" }, " ", "> ") : /* @__PURE__ */ React7.createElement(Text7, null, " "), /* @__PURE__ */ React7.createElement(Text7, null, item.project.name, " ", /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, "(", item.project.id, ")")));
|
|
192951
|
+
})), /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, "Use arrow keys to navigate, Enter to select"));
|
|
193078
192952
|
}
|
|
193079
192953
|
function NameInput({ onSubmit, onCancel }) {
|
|
193080
192954
|
const [value, setValue] = useState6("");
|
|
@@ -193129,7 +193003,7 @@ function formatErrorCode(code) {
|
|
|
193129
193003
|
function StructuredError({ error }) {
|
|
193130
193004
|
return /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column" }, /* @__PURE__ */ React7.createElement(Text7, { color: "red", bold: true }, formatErrorCode(error.code), ": ", error.message), error.resource && /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, "Resource: ", error.resource), error.output && /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column", marginTop: 1 }, /* @__PURE__ */ React7.createElement(Text7, { bold: true }, "Output:"), /* @__PURE__ */ React7.createElement(Text7, null, error.output)));
|
|
193131
193005
|
}
|
|
193132
|
-
function DeployUI({ environment, config
|
|
193006
|
+
function DeployUI({ environment, config }) {
|
|
193133
193007
|
const { exit } = useApp3();
|
|
193134
193008
|
const [state, setState] = useState6({ phase: "checking-auth" });
|
|
193135
193009
|
const clientRef = React7.useRef(null);
|
|
@@ -193140,7 +193014,7 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193140
193014
|
const projectId = readProjectId(projectDir);
|
|
193141
193015
|
if (isLoggedIn()) {
|
|
193142
193016
|
setState({
|
|
193143
|
-
phase: "
|
|
193017
|
+
phase: "creating-tarball",
|
|
193144
193018
|
projectId
|
|
193145
193019
|
});
|
|
193146
193020
|
} else {
|
|
@@ -193197,7 +193071,7 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193197
193071
|
const successResponse = response;
|
|
193198
193072
|
await saveCredentialsFromToken(successResponse);
|
|
193199
193073
|
setState(
|
|
193200
|
-
(s) => s.projectId ? { phase: "
|
|
193074
|
+
(s) => s.projectId ? { phase: "creating-tarball", projectId: s.projectId } : { phase: "loading-projects" }
|
|
193201
193075
|
);
|
|
193202
193076
|
}
|
|
193203
193077
|
};
|
|
@@ -193221,12 +193095,18 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193221
193095
|
async function loadProjects() {
|
|
193222
193096
|
try {
|
|
193223
193097
|
const client2 = new ApiClient();
|
|
193224
|
-
const { projects: projects2 } = await
|
|
193098
|
+
const [{ projects: projects2 }, { organizations }] = await Promise.all([
|
|
193099
|
+
client2.listProjects(),
|
|
193100
|
+
client2.listOrganizations()
|
|
193101
|
+
]);
|
|
193225
193102
|
if (cancelled) return;
|
|
193103
|
+
const items = buildSelectorItems(projects2, organizations);
|
|
193104
|
+
const firstSelectable = items.findIndex((item) => item.type !== "header");
|
|
193226
193105
|
setState({
|
|
193227
193106
|
phase: "selecting-project",
|
|
193228
193107
|
projects: projects2,
|
|
193229
|
-
|
|
193108
|
+
organizations,
|
|
193109
|
+
selectedIndex: firstSelectable >= 0 ? firstSelectable : 0
|
|
193230
193110
|
});
|
|
193231
193111
|
} catch (err) {
|
|
193232
193112
|
if (cancelled) return;
|
|
@@ -193243,13 +193123,14 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193243
193123
|
}, [state.phase]);
|
|
193244
193124
|
const handleProjectSelect = useCallback(
|
|
193245
193125
|
(project) => {
|
|
193246
|
-
if (project === "new") {
|
|
193247
|
-
setState((s) => ({ ...s, phase: "entering-name" }));
|
|
193126
|
+
if ("type" in project && project.type === "new") {
|
|
193127
|
+
setState((s) => ({ ...s, phase: "entering-name", selectedOrganizationId: project.orgId }));
|
|
193248
193128
|
} else {
|
|
193249
|
-
|
|
193129
|
+
const proj = project;
|
|
193130
|
+
writeProjectId(proj.id);
|
|
193250
193131
|
setState({
|
|
193251
|
-
phase: "
|
|
193252
|
-
projectId:
|
|
193132
|
+
phase: "creating-tarball",
|
|
193133
|
+
projectId: proj.id
|
|
193253
193134
|
});
|
|
193254
193135
|
}
|
|
193255
193136
|
},
|
|
@@ -193267,11 +193148,11 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193267
193148
|
async function createProject() {
|
|
193268
193149
|
try {
|
|
193269
193150
|
const client2 = new ApiClient();
|
|
193270
|
-
const project = await client2.createProject(state.newProjectName);
|
|
193151
|
+
const project = await client2.createProject(state.newProjectName, state.selectedOrganizationId);
|
|
193271
193152
|
if (cancelled) return;
|
|
193272
193153
|
writeProjectId(project.id);
|
|
193273
193154
|
setState({
|
|
193274
|
-
phase: "
|
|
193155
|
+
phase: "creating-tarball",
|
|
193275
193156
|
projectId: project.id
|
|
193276
193157
|
});
|
|
193277
193158
|
} catch (err) {
|
|
@@ -193432,43 +193313,11 @@ function DeployUI({ environment, config, skipBuildTest }) {
|
|
|
193432
193313
|
})();
|
|
193433
193314
|
}, [state]);
|
|
193434
193315
|
useEffect4(() => {
|
|
193435
|
-
if (state.phase !== "
|
|
193316
|
+
if (state.phase !== "creating-tarball" || !state.projectId) return;
|
|
193436
193317
|
let cancelled = false;
|
|
193437
|
-
async function
|
|
193318
|
+
async function runDeploy() {
|
|
193438
193319
|
const projectDir = process.cwd();
|
|
193439
193320
|
const builds = config.builds || [];
|
|
193440
|
-
if (!skipBuildTest && builds.length > 0) {
|
|
193441
|
-
writeLog("deploy", `Testing ${builds.length} build(s) locally`);
|
|
193442
|
-
try {
|
|
193443
|
-
const results = await testAllBuilds(builds, projectDir);
|
|
193444
|
-
if (cancelled) return;
|
|
193445
|
-
if (!results.allPassed) {
|
|
193446
|
-
const failures = results.results.filter((r) => !r.success);
|
|
193447
|
-
const errorMsg = failures.map((f) => `Build "${f.buildName}" failed:
|
|
193448
|
-
${f.output}`).join("\n\n");
|
|
193449
|
-
writeLog("deploy:error", errorMsg);
|
|
193450
|
-
setState({
|
|
193451
|
-
phase: "error",
|
|
193452
|
-
error: `Build test failed:
|
|
193453
|
-
${errorMsg}`
|
|
193454
|
-
});
|
|
193455
|
-
return;
|
|
193456
|
-
}
|
|
193457
|
-
writeLog("deploy", "All builds passed local testing");
|
|
193458
|
-
} catch (err) {
|
|
193459
|
-
if (cancelled) return;
|
|
193460
|
-
const errorMsg = `Build test failed: ${err instanceof Error ? err.message : String(err)}`;
|
|
193461
|
-
writeLog("deploy:error", errorMsg);
|
|
193462
|
-
setState({
|
|
193463
|
-
phase: "error",
|
|
193464
|
-
error: errorMsg
|
|
193465
|
-
});
|
|
193466
|
-
return;
|
|
193467
|
-
}
|
|
193468
|
-
} else {
|
|
193469
|
-
writeLog("deploy", skipBuildTest ? "Skipping build tests (--skip-build-test)" : "No builds to test");
|
|
193470
|
-
}
|
|
193471
|
-
setState((s) => ({ ...s, phase: "creating-tarball" }));
|
|
193472
193321
|
writeLog("deploy", `Starting deployment to "${environment}"`);
|
|
193473
193322
|
writeLog("deploy", `Project directory: ${projectDir}`);
|
|
193474
193323
|
const client2 = new ApiClient();
|
|
@@ -193534,11 +193383,11 @@ ${errorMsg}`
|
|
|
193534
193383
|
writeLog("deploy", "Deployment in pending state, waiting for builds to complete");
|
|
193535
193384
|
setState((s) => ({ ...s, phase: "pending", deployment: deployment2 }));
|
|
193536
193385
|
}
|
|
193537
|
-
|
|
193386
|
+
runDeploy();
|
|
193538
193387
|
return () => {
|
|
193539
193388
|
cancelled = true;
|
|
193540
193389
|
};
|
|
193541
|
-
}, [state.projectId, environment, config.builds
|
|
193390
|
+
}, [state.projectId, environment, config.builds]);
|
|
193542
193391
|
useEffect4(() => {
|
|
193543
193392
|
if (state.phase !== "pending" || !state.deployment) return;
|
|
193544
193393
|
let pollInterval;
|
|
@@ -193732,7 +193581,7 @@ ${errorMsg}`
|
|
|
193732
193581
|
};
|
|
193733
193582
|
}, [state.phase, state.deployment?.id]);
|
|
193734
193583
|
useEffect4(() => {
|
|
193735
|
-
if (state.phase === "
|
|
193584
|
+
if (state.phase === "creating-tarball") {
|
|
193736
193585
|
trackEvent("deploy_started", { environment });
|
|
193737
193586
|
}
|
|
193738
193587
|
}, [state.phase, environment]);
|
|
@@ -193775,24 +193624,28 @@ ${errorMsg}`
|
|
|
193775
193624
|
if (phase === "loading-projects") {
|
|
193776
193625
|
return /* @__PURE__ */ React7.createElement(Box7, null, /* @__PURE__ */ React7.createElement(Text7, { color: "blue" }, /* @__PURE__ */ React7.createElement(Spinner5, { type: "dots" })), /* @__PURE__ */ React7.createElement(Text7, null, " Loading projects..."));
|
|
193777
193626
|
}
|
|
193778
|
-
if (phase === "selecting-project" && projects && selectedIndex !== void 0) {
|
|
193627
|
+
if (phase === "selecting-project" && projects && state.organizations && selectedIndex !== void 0) {
|
|
193628
|
+
const selectorItems = buildSelectorItems(projects, state.organizations);
|
|
193629
|
+
const selectableIndices = selectorItems.map((item, index) => item.type !== "header" ? index : -1).filter((i) => i >= 0);
|
|
193779
193630
|
return /* @__PURE__ */ React7.createElement(
|
|
193780
193631
|
ProjectSelector,
|
|
193781
193632
|
{
|
|
193782
193633
|
projects,
|
|
193634
|
+
organizations: state.organizations,
|
|
193783
193635
|
selectedIndex,
|
|
193784
193636
|
onSelect: handleProjectSelect,
|
|
193785
|
-
onUp: () => setState((s) =>
|
|
193786
|
-
|
|
193787
|
-
|
|
193788
|
-
|
|
193789
|
-
|
|
193790
|
-
|
|
193791
|
-
|
|
193792
|
-
|
|
193793
|
-
|
|
193794
|
-
)
|
|
193795
|
-
|
|
193637
|
+
onUp: () => setState((s) => {
|
|
193638
|
+
const idx = s.selectedIndex ?? 0;
|
|
193639
|
+
const currentPos = selectableIndices.indexOf(idx);
|
|
193640
|
+
const prevPos = Math.max(0, currentPos - 1);
|
|
193641
|
+
return { ...s, selectedIndex: selectableIndices[prevPos] ?? idx };
|
|
193642
|
+
}),
|
|
193643
|
+
onDown: () => setState((s) => {
|
|
193644
|
+
const idx = s.selectedIndex ?? 0;
|
|
193645
|
+
const currentPos = selectableIndices.indexOf(idx);
|
|
193646
|
+
const nextPos = Math.min(selectableIndices.length - 1, currentPos + 1);
|
|
193647
|
+
return { ...s, selectedIndex: selectableIndices[nextPos] ?? idx };
|
|
193648
|
+
})
|
|
193796
193649
|
}
|
|
193797
193650
|
);
|
|
193798
193651
|
}
|
|
@@ -193827,13 +193680,6 @@ ${errorMsg}`
|
|
|
193827
193680
|
return "Preparing";
|
|
193828
193681
|
};
|
|
193829
193682
|
return /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column", gap: 1 }, /* @__PURE__ */ React7.createElement(Text7, null, /* @__PURE__ */ React7.createElement(Text7, { bold: true, color: "cyan" }, "Deploying to ", environment), deployment && /* @__PURE__ */ React7.createElement(Text7, { dimColor: true }, " (", deployment.id, ")")), /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column" }, /* @__PURE__ */ React7.createElement(
|
|
193830
|
-
PhaseIndicator,
|
|
193831
|
-
{
|
|
193832
|
-
phase: "testing-builds",
|
|
193833
|
-
currentPhase: displayPhase,
|
|
193834
|
-
label: "Testing builds locally"
|
|
193835
|
-
}
|
|
193836
|
-
), /* @__PURE__ */ React7.createElement(
|
|
193837
193683
|
PhaseIndicator,
|
|
193838
193684
|
{
|
|
193839
193685
|
phase: "creating-tarball",
|
|
@@ -193887,7 +193733,7 @@ ${errorMsg}`
|
|
|
193887
193733
|
}
|
|
193888
193734
|
), phase === "error" && /* @__PURE__ */ React7.createElement(Box7, { marginTop: 1, flexDirection: "column" }, deployment?.error ? /* @__PURE__ */ React7.createElement(StructuredError, { error: deployment.error }) : /* @__PURE__ */ React7.createElement(Text7, { color: "red", bold: true }, error), buildOutput && /* @__PURE__ */ React7.createElement(Box7, { flexDirection: "column", marginTop: 1 }, /* @__PURE__ */ React7.createElement(Text7, { bold: true }, "Build output:"), /* @__PURE__ */ React7.createElement(Text7, null, buildOutput))), phase === "success" && /* @__PURE__ */ React7.createElement(Box7, { marginTop: 1, flexDirection: "column" }, /* @__PURE__ */ React7.createElement(Text7, { color: "green" }, "Deployment successful!"), deployment?.publicUrls && Object.keys(deployment.publicUrls).length > 0 && /* @__PURE__ */ React7.createElement(Box7, { marginTop: 1, flexDirection: "column" }, /* @__PURE__ */ React7.createElement(Text7, { bold: true }, "Public URLs:"), Object.entries(deployment.publicUrls).map(([name, url]) => /* @__PURE__ */ React7.createElement(Text7, { key: name }, " ", name, ": ", /* @__PURE__ */ React7.createElement(Text7, { color: "cyan" }, url))))));
|
|
193889
193735
|
}
|
|
193890
|
-
async function deployCommand(environment
|
|
193736
|
+
async function deployCommand(environment) {
|
|
193891
193737
|
const configPath = path23.join(process.cwd(), "specific.hcl");
|
|
193892
193738
|
if (!fs26.existsSync(configPath)) {
|
|
193893
193739
|
console.error("Error: No specific.hcl found in current directory");
|
|
@@ -193902,21 +193748,19 @@ async function deployCommand(environment, options2) {
|
|
|
193902
193748
|
process.exit(1);
|
|
193903
193749
|
}
|
|
193904
193750
|
const env2 = environment || "prod";
|
|
193905
|
-
const skipBuildTest = options2?.skipBuildTest ?? false;
|
|
193906
193751
|
render5(
|
|
193907
193752
|
/* @__PURE__ */ React7.createElement(
|
|
193908
193753
|
DeployUI,
|
|
193909
193754
|
{
|
|
193910
193755
|
environment: env2,
|
|
193911
|
-
config
|
|
193912
|
-
skipBuildTest
|
|
193756
|
+
config
|
|
193913
193757
|
}
|
|
193914
193758
|
)
|
|
193915
193759
|
);
|
|
193916
193760
|
}
|
|
193917
193761
|
|
|
193918
193762
|
// src/commands/exec.tsx
|
|
193919
|
-
import { spawn as
|
|
193763
|
+
import { spawn as spawn6 } from "child_process";
|
|
193920
193764
|
import * as fs27 from "fs";
|
|
193921
193765
|
import * as path24 from "path";
|
|
193922
193766
|
async function execCommand(serviceName, command, instanceKey = "default") {
|
|
@@ -194077,7 +193921,7 @@ async function execCommand(serviceName, command, instanceKey = "default") {
|
|
|
194077
193921
|
effectiveCwd = path24.resolve(process.cwd(), build.root);
|
|
194078
193922
|
}
|
|
194079
193923
|
}
|
|
194080
|
-
child =
|
|
193924
|
+
child = spawn6(command[0], command.slice(1), {
|
|
194081
193925
|
cwd: effectiveCwd,
|
|
194082
193926
|
env: {
|
|
194083
193927
|
...process.env,
|
|
@@ -194101,7 +193945,7 @@ async function execCommand(serviceName, command, instanceKey = "default") {
|
|
|
194101
193945
|
}
|
|
194102
193946
|
|
|
194103
193947
|
// src/commands/psql.tsx
|
|
194104
|
-
import { spawn as
|
|
193948
|
+
import { spawn as spawn7 } from "child_process";
|
|
194105
193949
|
import * as fs28 from "fs";
|
|
194106
193950
|
import * as path25 from "path";
|
|
194107
193951
|
async function psqlCommand(databaseName, instanceKey = "default", extraArgs = []) {
|
|
@@ -194224,7 +194068,7 @@ async function psqlCommand(databaseName, instanceKey = "default", extraArgs = []
|
|
|
194224
194068
|
};
|
|
194225
194069
|
process.on("SIGINT", () => handleSignal("SIGINT"));
|
|
194226
194070
|
process.on("SIGTERM", () => handleSignal("SIGTERM"));
|
|
194227
|
-
child =
|
|
194071
|
+
child = spawn7(psqlPath, ["-h", dbState.host, "-p", String(dbState.port), "-U", dbState.user, "-d", dbState.dbName, ...extraArgs], {
|
|
194228
194072
|
cwd: process.cwd(),
|
|
194229
194073
|
env: {
|
|
194230
194074
|
...process.env,
|
|
@@ -194249,7 +194093,7 @@ async function psqlCommand(databaseName, instanceKey = "default", extraArgs = []
|
|
|
194249
194093
|
}
|
|
194250
194094
|
|
|
194251
194095
|
// src/commands/reshape.tsx
|
|
194252
|
-
import { spawn as
|
|
194096
|
+
import { spawn as spawn8 } from "child_process";
|
|
194253
194097
|
import * as fs29 from "fs";
|
|
194254
194098
|
import * as path26 from "path";
|
|
194255
194099
|
var VALID_ACTIONS = ["start", "complete", "status", "abort", "check"];
|
|
@@ -194427,7 +194271,7 @@ async function reshapeCommand(action, databaseName, instanceKey = "default") {
|
|
|
194427
194271
|
};
|
|
194428
194272
|
process.on("SIGINT", () => handleSignal("SIGINT"));
|
|
194429
194273
|
process.on("SIGTERM", () => handleSignal("SIGTERM"));
|
|
194430
|
-
child =
|
|
194274
|
+
child = spawn8(reshapePath, reshapeArgs, {
|
|
194431
194275
|
cwd: process.cwd(),
|
|
194432
194276
|
env: {
|
|
194433
194277
|
...process.env,
|
|
@@ -194704,7 +194548,7 @@ function compareVersions(a, b) {
|
|
|
194704
194548
|
return 0;
|
|
194705
194549
|
}
|
|
194706
194550
|
async function checkForUpdate() {
|
|
194707
|
-
const currentVersion = "0.1.
|
|
194551
|
+
const currentVersion = "0.1.75";
|
|
194708
194552
|
const response = await fetch(`${BINARIES_BASE_URL}/latest?t=${Date.now()}`);
|
|
194709
194553
|
if (!response.ok) {
|
|
194710
194554
|
throw new Error(`Failed to check for updates: HTTP ${response.status}`);
|
|
@@ -194754,7 +194598,7 @@ async function performUpdate(version, onProgress) {
|
|
|
194754
194598
|
}
|
|
194755
194599
|
|
|
194756
194600
|
// src/lib/background-update.ts
|
|
194757
|
-
import { spawn as
|
|
194601
|
+
import { spawn as spawn9 } from "child_process";
|
|
194758
194602
|
import * as fs32 from "fs";
|
|
194759
194603
|
import * as path29 from "path";
|
|
194760
194604
|
import * as os10 from "os";
|
|
@@ -194783,7 +194627,7 @@ function maybeStartBackgroundUpdate() {
|
|
|
194783
194627
|
if (process.env.SPECIFIC_BACKGROUND_UPDATE === "1") return;
|
|
194784
194628
|
if (isRateLimited()) return;
|
|
194785
194629
|
if (!isBinaryWritable()) return;
|
|
194786
|
-
const child =
|
|
194630
|
+
const child = spawn9(process.execPath, [], {
|
|
194787
194631
|
detached: true,
|
|
194788
194632
|
stdio: "ignore",
|
|
194789
194633
|
env: {
|
|
@@ -194903,7 +194747,7 @@ function updateCommand() {
|
|
|
194903
194747
|
var program = new Command();
|
|
194904
194748
|
var env = "production";
|
|
194905
194749
|
var envLabel = env !== "production" ? `[${env.toUpperCase()}] ` : "";
|
|
194906
|
-
program.name("specific").description(`${envLabel}Infrastructure-as-code for coding agents`).version("0.1.
|
|
194750
|
+
program.name("specific").description(`${envLabel}Infrastructure-as-code for coding agents`).version("0.1.75").enablePositionalOptions();
|
|
194907
194751
|
program.command("init").description("Initialize project for use with a coding agent").option("--agent <name...>", "Agents to configure (cursor, claude, codex, other)").action((options2) => initCommand(options2));
|
|
194908
194752
|
program.command("docs [topic]").description("Fetch LLM-optimized documentation").action(docsCommand);
|
|
194909
194753
|
program.command("check").description("Validate specific.hcl configuration").action(checkCommand);
|
|
@@ -194911,8 +194755,8 @@ program.command("dev").description("Start local development environment").option
|
|
|
194911
194755
|
const key = options2.key ?? getDefaultKey();
|
|
194912
194756
|
devCommand(key, options2.tunnel ?? false);
|
|
194913
194757
|
});
|
|
194914
|
-
program.command("deploy [environment]").description("Deploy to Specific infrastructure").
|
|
194915
|
-
deployCommand(environment
|
|
194758
|
+
program.command("deploy [environment]").description("Deploy to Specific infrastructure").action((environment) => {
|
|
194759
|
+
deployCommand(environment);
|
|
194916
194760
|
});
|
|
194917
194761
|
program.command("exec <service> [args...]").description("Run a one-off command with service environment").option("-k, --key <key>", "Dev environment namespace (auto-detected from git worktree if not specified)").passThroughOptions().action(async (service, args, options2) => {
|
|
194918
194762
|
const filteredArgs = args[0] === "--" ? args.slice(1) : args;
|