@pmate/cli 0.24.26 → 0.24.28
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.d.ts +32 -0
- package/dist/index.js +392 -23
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -913,6 +913,7 @@ type ServiceCommandArgs = {
|
|
|
913
913
|
action: "deploy" | "stop";
|
|
914
914
|
namespace: string;
|
|
915
915
|
name: string;
|
|
916
|
+
env?: string;
|
|
916
917
|
baseUrl?: string;
|
|
917
918
|
json: boolean;
|
|
918
919
|
} | {
|
|
@@ -920,6 +921,7 @@ type ServiceCommandArgs = {
|
|
|
920
921
|
action: "init";
|
|
921
922
|
namespace: string;
|
|
922
923
|
name: string;
|
|
924
|
+
env: string;
|
|
923
925
|
cwd?: string;
|
|
924
926
|
baseUrl?: string;
|
|
925
927
|
json: boolean;
|
|
@@ -943,6 +945,36 @@ type ServiceCommandArgs = {
|
|
|
943
945
|
includeSecretValue: boolean;
|
|
944
946
|
baseUrl?: string;
|
|
945
947
|
json: boolean;
|
|
948
|
+
} | {
|
|
949
|
+
type: Command.Service;
|
|
950
|
+
action: "service-env-list";
|
|
951
|
+
appId: string;
|
|
952
|
+
baseUrl?: string;
|
|
953
|
+
json: boolean;
|
|
954
|
+
} | {
|
|
955
|
+
type: Command.Service;
|
|
956
|
+
action: "service-env-get";
|
|
957
|
+
appId: string;
|
|
958
|
+
envName: string;
|
|
959
|
+
baseUrl?: string;
|
|
960
|
+
json: boolean;
|
|
961
|
+
} | {
|
|
962
|
+
type: Command.Service;
|
|
963
|
+
action: "service-env-add";
|
|
964
|
+
appId: string;
|
|
965
|
+
envName: string;
|
|
966
|
+
baseUrl?: string;
|
|
967
|
+
json: boolean;
|
|
968
|
+
} | {
|
|
969
|
+
type: Command.Service;
|
|
970
|
+
action: "service-env-expose";
|
|
971
|
+
appId: string;
|
|
972
|
+
envName: string;
|
|
973
|
+
exposeType?: "https" | "websocket";
|
|
974
|
+
off: boolean;
|
|
975
|
+
domain?: string;
|
|
976
|
+
baseUrl?: string;
|
|
977
|
+
json: boolean;
|
|
946
978
|
} | {
|
|
947
979
|
type: Command.Service;
|
|
948
980
|
action: "env-get";
|
package/dist/index.js
CHANGED
|
@@ -18212,6 +18212,20 @@ var ServiceRegistryClient = class {
|
|
|
18212
18212
|
}
|
|
18213
18213
|
);
|
|
18214
18214
|
}
|
|
18215
|
+
async getServiceEnv(serviceId, envName) {
|
|
18216
|
+
const payload = await this.request(
|
|
18217
|
+
"GET",
|
|
18218
|
+
`/services/by-id/${encodeURIComponent(serviceId)}/envs/${encodeURIComponent(envName)}`
|
|
18219
|
+
);
|
|
18220
|
+
return payload.item;
|
|
18221
|
+
}
|
|
18222
|
+
async appendDeployHistory(serviceId, input) {
|
|
18223
|
+
return this.requestWithBody(
|
|
18224
|
+
"POST",
|
|
18225
|
+
`/services/by-id/${encodeURIComponent(serviceId)}/deploy-history`,
|
|
18226
|
+
input
|
|
18227
|
+
);
|
|
18228
|
+
}
|
|
18215
18229
|
async pullEnv(serviceId, options) {
|
|
18216
18230
|
const pathname = `/services/by-id/${encodeURIComponent(serviceId)}/env/pull`;
|
|
18217
18231
|
const response = await fetch(`${this.resolveBaseUrl()}${pathname}`, {
|
|
@@ -18327,6 +18341,12 @@ var ServiceRuntimeRunner = class {
|
|
|
18327
18341
|
}
|
|
18328
18342
|
async deploy(service, options = {}) {
|
|
18329
18343
|
switch (this.getType(service)) {
|
|
18344
|
+
case "node-api":
|
|
18345
|
+
await this.deployNode(service, options);
|
|
18346
|
+
return;
|
|
18347
|
+
case "node-job":
|
|
18348
|
+
await this.deployScriptManaged(service);
|
|
18349
|
+
return;
|
|
18330
18350
|
case "vite":
|
|
18331
18351
|
await this.deployVite(service, options);
|
|
18332
18352
|
return;
|
|
@@ -18334,14 +18354,14 @@ var ServiceRuntimeRunner = class {
|
|
|
18334
18354
|
await this.deployStatic(service, options);
|
|
18335
18355
|
return;
|
|
18336
18356
|
case "node":
|
|
18337
|
-
await this.deployNode(service);
|
|
18357
|
+
await this.deployNode(service, options);
|
|
18338
18358
|
return;
|
|
18339
18359
|
case "rust":
|
|
18340
18360
|
case "python":
|
|
18341
18361
|
await this.deployScriptManaged(service);
|
|
18342
18362
|
return;
|
|
18343
18363
|
case "fc":
|
|
18344
|
-
await this.deployFc(service);
|
|
18364
|
+
await this.deployFc(service, options);
|
|
18345
18365
|
return;
|
|
18346
18366
|
case "ios":
|
|
18347
18367
|
case "android":
|
|
@@ -18354,6 +18374,7 @@ var ServiceRuntimeRunner = class {
|
|
|
18354
18374
|
}
|
|
18355
18375
|
async stop(service) {
|
|
18356
18376
|
switch (this.getType(service)) {
|
|
18377
|
+
case "node-job":
|
|
18357
18378
|
case "rust":
|
|
18358
18379
|
case "python":
|
|
18359
18380
|
await this.stopScriptManaged(service);
|
|
@@ -18376,6 +18397,12 @@ var ServiceRuntimeRunner = class {
|
|
|
18376
18397
|
case "static":
|
|
18377
18398
|
await this.initStaticLike(service);
|
|
18378
18399
|
return;
|
|
18400
|
+
case "node-api":
|
|
18401
|
+
await this.initServerApp(service, options, { ensurePackageJson: true });
|
|
18402
|
+
return;
|
|
18403
|
+
case "node-job":
|
|
18404
|
+
await this.initServerApp(service, options, { ensurePackageJson: false });
|
|
18405
|
+
return;
|
|
18379
18406
|
case "node":
|
|
18380
18407
|
await this.initServerApp(service, options, { ensurePackageJson: true });
|
|
18381
18408
|
return;
|
|
@@ -18588,7 +18615,7 @@ var ServiceRuntimeRunner = class {
|
|
|
18588
18615
|
}
|
|
18589
18616
|
await AliyunService.uploadDirectory(srcDir, bucketName);
|
|
18590
18617
|
}
|
|
18591
|
-
async deployFc(service) {
|
|
18618
|
+
async deployFc(service, options = {}) {
|
|
18592
18619
|
const fc = this.getFc(service);
|
|
18593
18620
|
this.validateFcConfig(service, fc);
|
|
18594
18621
|
const repoRoot = this.resolveRepoRoot(service);
|
|
@@ -18606,7 +18633,7 @@ var ServiceRuntimeRunner = class {
|
|
|
18606
18633
|
await this.runCommand("pnpm", ["--filter", pkgName, "build"], repoRoot);
|
|
18607
18634
|
const registry = new ServiceRegistryClient();
|
|
18608
18635
|
const appId = `${service.namespace}:${service.name}`;
|
|
18609
|
-
const stage = fc.deployStage ?? "prod";
|
|
18636
|
+
const stage = this.envNameToStage(options.envName ?? fc.deployStage ?? "prod");
|
|
18610
18637
|
const requiredEnv = await this.syncFcRequiredEnv(service, registry, stage);
|
|
18611
18638
|
const resolved = await registry.resolveEnv(appId, {
|
|
18612
18639
|
stage,
|
|
@@ -18704,7 +18731,7 @@ var ServiceRuntimeRunner = class {
|
|
|
18704
18731
|
url: this.buildFcUrl(fc)
|
|
18705
18732
|
});
|
|
18706
18733
|
}
|
|
18707
|
-
async deployNode(service) {
|
|
18734
|
+
async deployNode(service, options = {}) {
|
|
18708
18735
|
const network = this.getNetwork(service);
|
|
18709
18736
|
const server = network.server?.trim();
|
|
18710
18737
|
const repository = network.repository?.trim();
|
|
@@ -18731,7 +18758,7 @@ var ServiceRuntimeRunner = class {
|
|
|
18731
18758
|
`pkg="${appDir}/package.json"`,
|
|
18732
18759
|
`if [ -f "$pkg" ] && node -e 'const fs=require("node:fs"); const p=JSON.parse(fs.readFileSync(process.argv[1],"utf8")); process.exit(p?.scripts?.build ? 0 : 1);' "$pkg"; then (cd "${appDir}" && pnpm run build); fi`
|
|
18733
18760
|
].join("; ");
|
|
18734
|
-
const envSyncCommand = await this.buildNodeEnvSyncCommand(service.id, appDir);
|
|
18761
|
+
const envSyncCommand = await this.buildNodeEnvSyncCommand(service.id, appDir, options.envName);
|
|
18735
18762
|
const command = [
|
|
18736
18763
|
`cd "$HOME"`,
|
|
18737
18764
|
`[ -d "${repoDir}/.git" ] || git clone "${gitUrl}" "${repoDir}"`,
|
|
@@ -18749,13 +18776,13 @@ var ServiceRuntimeRunner = class {
|
|
|
18749
18776
|
].join(" && ");
|
|
18750
18777
|
await this.runRemoteCommand(server, command);
|
|
18751
18778
|
}
|
|
18752
|
-
async buildNodeEnvSyncCommand(serviceId, appDir) {
|
|
18779
|
+
async buildNodeEnvSyncCommand(serviceId, appDir, envName = "prod") {
|
|
18753
18780
|
if (!this.envProvider) {
|
|
18754
18781
|
return void 0;
|
|
18755
18782
|
}
|
|
18756
18783
|
let pulled;
|
|
18757
18784
|
try {
|
|
18758
|
-
pulled = await this.envProvider(serviceId, { stage:
|
|
18785
|
+
pulled = await this.envProvider(serviceId, { stage: this.envNameToStage(envName), format: "dotenv" });
|
|
18759
18786
|
} catch (error) {
|
|
18760
18787
|
if (error instanceof ServiceEnvNotFoundError) {
|
|
18761
18788
|
ui.warn(`No env found for ${serviceId}; skipping .env.local sync.`);
|
|
@@ -18977,6 +19004,12 @@ var ServiceRuntimeRunner = class {
|
|
|
18977
19004
|
}
|
|
18978
19005
|
return payload.data;
|
|
18979
19006
|
}
|
|
19007
|
+
envNameToStage(envName) {
|
|
19008
|
+
if (envName === "dev" || envName === "preview" || envName === "prod") {
|
|
19009
|
+
return envName;
|
|
19010
|
+
}
|
|
19011
|
+
return "preview";
|
|
19012
|
+
}
|
|
18980
19013
|
renderPage(page, options = {}) {
|
|
18981
19014
|
ui.info("Page", {
|
|
18982
19015
|
page: page.page,
|
|
@@ -19758,17 +19791,32 @@ var ServiceCommandHandler = class {
|
|
|
19758
19791
|
}
|
|
19759
19792
|
case "deploy": {
|
|
19760
19793
|
const record = await registry.getService(args.namespace, args.name);
|
|
19761
|
-
await
|
|
19794
|
+
const service = await this.materializeServiceEnv(registry, record, args.env);
|
|
19795
|
+
try {
|
|
19796
|
+
await runtime.deploy(service, { envName: args.env });
|
|
19797
|
+
await this.appendDeployHistory(registry, record.id, args.env, "success");
|
|
19798
|
+
} catch (error) {
|
|
19799
|
+
await this.appendDeployHistory(
|
|
19800
|
+
registry,
|
|
19801
|
+
record.id,
|
|
19802
|
+
args.env,
|
|
19803
|
+
"failed",
|
|
19804
|
+
error instanceof Error ? error.message : String(error)
|
|
19805
|
+
);
|
|
19806
|
+
throw error;
|
|
19807
|
+
}
|
|
19762
19808
|
return;
|
|
19763
19809
|
}
|
|
19764
19810
|
case "stop": {
|
|
19765
19811
|
const record = await registry.getService(args.namespace, args.name);
|
|
19766
|
-
await
|
|
19812
|
+
const service = args.env ? await this.materializeServiceEnv(registry, record, args.env) : record;
|
|
19813
|
+
await runtime.stop(service);
|
|
19767
19814
|
return;
|
|
19768
19815
|
}
|
|
19769
19816
|
case "init": {
|
|
19770
19817
|
const record = await registry.getService(args.namespace, args.name);
|
|
19771
|
-
await
|
|
19818
|
+
const service = await this.materializeServiceEnv(registry, record, args.env);
|
|
19819
|
+
await runtime.init(service, { cwd: args.cwd });
|
|
19772
19820
|
return;
|
|
19773
19821
|
}
|
|
19774
19822
|
case "log": {
|
|
@@ -19901,7 +19949,183 @@ var ServiceCommandHandler = class {
|
|
|
19901
19949
|
this.renderJson(payload, args.json);
|
|
19902
19950
|
return;
|
|
19903
19951
|
}
|
|
19952
|
+
case "service-env-list": {
|
|
19953
|
+
const payload = await this.request(
|
|
19954
|
+
baseUrl,
|
|
19955
|
+
"GET",
|
|
19956
|
+
this.buildServiceEnvBasePath(args.appId)
|
|
19957
|
+
);
|
|
19958
|
+
this.renderJson(payload, true);
|
|
19959
|
+
return;
|
|
19960
|
+
}
|
|
19961
|
+
case "service-env-get": {
|
|
19962
|
+
const payload = await this.request(
|
|
19963
|
+
baseUrl,
|
|
19964
|
+
"GET",
|
|
19965
|
+
`${this.buildServiceEnvBasePath(args.appId)}/${encodeURIComponent(args.envName)}`
|
|
19966
|
+
);
|
|
19967
|
+
this.renderJson(payload, true);
|
|
19968
|
+
return;
|
|
19969
|
+
}
|
|
19970
|
+
case "service-env-add": {
|
|
19971
|
+
const payload = await this.request(
|
|
19972
|
+
baseUrl,
|
|
19973
|
+
"PUT",
|
|
19974
|
+
`${this.buildServiceEnvBasePath(args.appId)}/${encodeURIComponent(args.envName)}`,
|
|
19975
|
+
{
|
|
19976
|
+
name: args.envName
|
|
19977
|
+
}
|
|
19978
|
+
);
|
|
19979
|
+
ui.success(`Updated service env ${args.envName} for ${args.appId}`);
|
|
19980
|
+
this.renderJson(payload, args.json);
|
|
19981
|
+
return;
|
|
19982
|
+
}
|
|
19983
|
+
case "service-env-expose": {
|
|
19984
|
+
const payload = await this.request(
|
|
19985
|
+
baseUrl,
|
|
19986
|
+
"POST",
|
|
19987
|
+
`${this.buildServiceEnvBasePath(args.appId)}/${encodeURIComponent(args.envName)}/expose`,
|
|
19988
|
+
{
|
|
19989
|
+
...args.exposeType ? { type: args.exposeType } : {},
|
|
19990
|
+
...args.domain ? { domain: args.domain } : {},
|
|
19991
|
+
...args.off ? { off: true } : {}
|
|
19992
|
+
}
|
|
19993
|
+
);
|
|
19994
|
+
ui.success(
|
|
19995
|
+
args.off ? `Disabled network for ${args.appId} ${args.envName}` : `Updated network for ${args.appId} ${args.envName}`
|
|
19996
|
+
);
|
|
19997
|
+
this.renderJson(payload, args.json);
|
|
19998
|
+
return;
|
|
19999
|
+
}
|
|
20000
|
+
}
|
|
20001
|
+
}
|
|
20002
|
+
async materializeServiceEnv(registry, service, envName) {
|
|
20003
|
+
if (!envName || !this.isDefinitionStyleService(service)) {
|
|
20004
|
+
return service;
|
|
19904
20005
|
}
|
|
20006
|
+
const env = await registry.getServiceEnv(service.id, envName);
|
|
20007
|
+
return this.buildRuntimeServiceRecord(service, env);
|
|
20008
|
+
}
|
|
20009
|
+
isDefinitionStyleService(service) {
|
|
20010
|
+
return "repository" in service || "type" in service && (service.type === "node-api" || service.type === "node-job") || !("site" in service) && !("network" in service) && !("fc" in service) && !("runtimeType" in service);
|
|
20011
|
+
}
|
|
20012
|
+
buildRuntimeServiceRecord(service, env) {
|
|
20013
|
+
if (!("type" in service)) {
|
|
20014
|
+
return service;
|
|
20015
|
+
}
|
|
20016
|
+
const repository = service.repository?.trim();
|
|
20017
|
+
const dir = service.dir?.trim();
|
|
20018
|
+
const runtime = env.runtime;
|
|
20019
|
+
if (!runtime) {
|
|
20020
|
+
throw new Error(`Missing runtime for ${service.id} env ${env.name}`);
|
|
20021
|
+
}
|
|
20022
|
+
if (!repository) {
|
|
20023
|
+
throw new Error(`Missing service.repository for ${service.id}`);
|
|
20024
|
+
}
|
|
20025
|
+
if (!dir) {
|
|
20026
|
+
throw new Error(`Missing service.dir for ${service.id}`);
|
|
20027
|
+
}
|
|
20028
|
+
if (runtime.type === "ali-oss") {
|
|
20029
|
+
const domainParts = splitPrimaryDomain(env.network?.domain);
|
|
20030
|
+
return {
|
|
20031
|
+
id: service.id,
|
|
20032
|
+
namespace: service.namespace,
|
|
20033
|
+
name: service.name,
|
|
20034
|
+
type: service.type === "static" ? "static" : "vite",
|
|
20035
|
+
site: {
|
|
20036
|
+
exposeType: "static-site",
|
|
20037
|
+
repository,
|
|
20038
|
+
dir,
|
|
20039
|
+
bucket: requireString(runtime.bucket, `runtime.bucket for ${service.id} ${env.name}`),
|
|
20040
|
+
domain: domainParts.domain,
|
|
20041
|
+
...domainParts.subdomain ? { subdomain: domainParts.subdomain } : {}
|
|
20042
|
+
}
|
|
20043
|
+
};
|
|
20044
|
+
}
|
|
20045
|
+
if (runtime.type === "ssh-pm2") {
|
|
20046
|
+
return {
|
|
20047
|
+
id: service.id,
|
|
20048
|
+
namespace: service.namespace,
|
|
20049
|
+
name: runtime.appName?.trim() || service.name,
|
|
20050
|
+
type: service.type === "node-api" ? "node-api" : "node",
|
|
20051
|
+
network: {
|
|
20052
|
+
exposeType: env.network?.type === "websocket" ? "websocket" : env.network ? "rest" : "internal",
|
|
20053
|
+
repository,
|
|
20054
|
+
dir,
|
|
20055
|
+
server: requireString(runtime.server, `runtime.server for ${service.id} ${env.name}`),
|
|
20056
|
+
...runtime.port !== void 0 ? { port: runtime.port } : {},
|
|
20057
|
+
...splitPrimaryDomain(env.network?.domain)
|
|
20058
|
+
}
|
|
20059
|
+
};
|
|
20060
|
+
}
|
|
20061
|
+
if (runtime.type === "ssh-script") {
|
|
20062
|
+
return {
|
|
20063
|
+
id: service.id,
|
|
20064
|
+
namespace: service.namespace,
|
|
20065
|
+
name: service.name,
|
|
20066
|
+
type: service.type === "node-job" ? "node-job" : service.type === "rust" ? "rust" : "python",
|
|
20067
|
+
network: {
|
|
20068
|
+
exposeType: env.network?.type === "websocket" ? "websocket" : env.network ? "rest" : "internal",
|
|
20069
|
+
repository,
|
|
20070
|
+
dir: runtime.cwd?.trim() || dir,
|
|
20071
|
+
server: requireString(runtime.server, `runtime.server for ${service.id} ${env.name}`),
|
|
20072
|
+
...runtime.port !== void 0 ? { port: runtime.port } : {},
|
|
20073
|
+
...splitPrimaryDomain(env.network?.domain)
|
|
20074
|
+
},
|
|
20075
|
+
runner: {
|
|
20076
|
+
script: requireString(runtime.command, `runtime.command for ${service.id} ${env.name}`)
|
|
20077
|
+
}
|
|
20078
|
+
};
|
|
20079
|
+
}
|
|
20080
|
+
if (runtime.type === "fc") {
|
|
20081
|
+
const domainParts = splitPrimaryDomain(env.network?.domain);
|
|
20082
|
+
return {
|
|
20083
|
+
id: service.id,
|
|
20084
|
+
namespace: service.namespace,
|
|
20085
|
+
name: service.name,
|
|
20086
|
+
type: "fc",
|
|
20087
|
+
fc: {
|
|
20088
|
+
provider: runtime.provider ?? "aliyun",
|
|
20089
|
+
region: requireString(runtime.region, `runtime.region for ${service.id} ${env.name}`),
|
|
20090
|
+
repository,
|
|
20091
|
+
dir,
|
|
20092
|
+
functionName: requireString(runtime.functionName, `runtime.functionName for ${service.id} ${env.name}`),
|
|
20093
|
+
...runtime.configFile ? { configFile: runtime.configFile } : {},
|
|
20094
|
+
...runtime.qualifier ? { qualifier: runtime.qualifier } : {},
|
|
20095
|
+
...domainParts.domain ? { domain: domainParts.domain } : {},
|
|
20096
|
+
...domainParts.subdomain ? { subdomain: domainParts.subdomain } : {},
|
|
20097
|
+
deployStage: env.name === "prod" || env.name === "preview" || env.name === "dev" ? env.name : "preview"
|
|
20098
|
+
}
|
|
20099
|
+
};
|
|
20100
|
+
}
|
|
20101
|
+
throw new Error(`Unsupported runtime ${runtime.type} for ${service.id} env ${env.name}`);
|
|
20102
|
+
}
|
|
20103
|
+
async appendDeployHistory(registry, serviceId, environment, status, message) {
|
|
20104
|
+
let lastError;
|
|
20105
|
+
for (let attempt = 1; attempt <= 5; attempt += 1) {
|
|
20106
|
+
try {
|
|
20107
|
+
await registry.appendDeployHistory(serviceId, {
|
|
20108
|
+
environment,
|
|
20109
|
+
status,
|
|
20110
|
+
...message ? { message } : {}
|
|
20111
|
+
});
|
|
20112
|
+
return;
|
|
20113
|
+
} catch (error2) {
|
|
20114
|
+
lastError = error2;
|
|
20115
|
+
if (attempt < 5 && shouldRetryDeployHistoryAppend(error2)) {
|
|
20116
|
+
await sleep3(attempt * 1e3);
|
|
20117
|
+
continue;
|
|
20118
|
+
}
|
|
20119
|
+
break;
|
|
20120
|
+
}
|
|
20121
|
+
}
|
|
20122
|
+
const error = lastError;
|
|
20123
|
+
ui.warn("Failed to append deploy history", {
|
|
20124
|
+
serviceId,
|
|
20125
|
+
environment,
|
|
20126
|
+
status,
|
|
20127
|
+
message: error instanceof Error ? error.message : String(error)
|
|
20128
|
+
});
|
|
19905
20129
|
}
|
|
19906
20130
|
resolveBaseUrl(baseUrl) {
|
|
19907
20131
|
return (baseUrl || process.env.PMATE_APPS_API_BASE_URL || "https://apps-api.pmate.chat").replace(/\/+$/, "");
|
|
@@ -19943,6 +20167,9 @@ var ServiceCommandHandler = class {
|
|
|
19943
20167
|
buildEnvBasePath(appId) {
|
|
19944
20168
|
return `/services/by-id/${encodeURIComponent(appId)}/env`;
|
|
19945
20169
|
}
|
|
20170
|
+
buildServiceEnvBasePath(appId) {
|
|
20171
|
+
return `/services/by-id/${encodeURIComponent(appId)}/envs`;
|
|
20172
|
+
}
|
|
19946
20173
|
buildEnvPath(appId, query) {
|
|
19947
20174
|
const params = new URLSearchParams();
|
|
19948
20175
|
if (query.scope) {
|
|
@@ -20308,6 +20535,33 @@ var ServiceCommandHandler = class {
|
|
|
20308
20535
|
ui.plain(JSON.stringify(value, null, 2));
|
|
20309
20536
|
}
|
|
20310
20537
|
};
|
|
20538
|
+
function requireString(value, field) {
|
|
20539
|
+
if (typeof value !== "string" || !value.trim()) {
|
|
20540
|
+
throw new Error(`Missing ${field}`);
|
|
20541
|
+
}
|
|
20542
|
+
return value.trim();
|
|
20543
|
+
}
|
|
20544
|
+
function splitPrimaryDomain(host) {
|
|
20545
|
+
const normalized = host?.trim();
|
|
20546
|
+
if (!normalized) {
|
|
20547
|
+
return { domain: "pmate.chat" };
|
|
20548
|
+
}
|
|
20549
|
+
const parts = normalized.split(".").filter(Boolean);
|
|
20550
|
+
if (parts.length <= 2) {
|
|
20551
|
+
return { domain: normalized };
|
|
20552
|
+
}
|
|
20553
|
+
return {
|
|
20554
|
+
subdomain: parts.slice(0, -2).join("."),
|
|
20555
|
+
domain: parts.slice(-2).join(".")
|
|
20556
|
+
};
|
|
20557
|
+
}
|
|
20558
|
+
function shouldRetryDeployHistoryAppend(error) {
|
|
20559
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
20560
|
+
return message.includes("status 502") || message.includes("status 503") || message.includes("status 504") || message.includes("fetch failed") || message.includes("ECONNRESET") || message.includes("ETIMEDOUT");
|
|
20561
|
+
}
|
|
20562
|
+
function sleep3(ms) {
|
|
20563
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
20564
|
+
}
|
|
20311
20565
|
|
|
20312
20566
|
// src/commands/VercelCommandHandler.ts
|
|
20313
20567
|
var import_node_child_process12 = require("child_process");
|
|
@@ -22556,10 +22810,14 @@ init_namespacedRef();
|
|
|
22556
22810
|
function parseServiceArgs(tokens) {
|
|
22557
22811
|
const rest = [...tokens];
|
|
22558
22812
|
const rawAction = rest.shift();
|
|
22559
|
-
if (rawAction && looksLikeNamespacedRef(rawAction) && rest[0] === "env") {
|
|
22813
|
+
if (rawAction && looksLikeNamespacedRef(rawAction) && rest[0] === "env-vars") {
|
|
22560
22814
|
rest.shift();
|
|
22561
22815
|
return parseServiceEnvArgs(rawAction, rest);
|
|
22562
22816
|
}
|
|
22817
|
+
if (rawAction && looksLikeNamespacedRef(rawAction) && rest[0] === "env") {
|
|
22818
|
+
rest.shift();
|
|
22819
|
+
return parseServiceEnvDefinitionArgs(rawAction, rest);
|
|
22820
|
+
}
|
|
22563
22821
|
const action = rawAction === "view" ? "view" : rawAction;
|
|
22564
22822
|
if (!action) {
|
|
22565
22823
|
throw new Error("Missing service action. Use: service list|get|view|create|update|rename|delete|deploy|stop|init|log");
|
|
@@ -22629,6 +22887,7 @@ function parseServiceArgs(tokens) {
|
|
|
22629
22887
|
let history = false;
|
|
22630
22888
|
let search;
|
|
22631
22889
|
let follow = false;
|
|
22890
|
+
let env;
|
|
22632
22891
|
while (rest.length > 0) {
|
|
22633
22892
|
const token = rest.shift();
|
|
22634
22893
|
switch (token) {
|
|
@@ -22641,6 +22900,12 @@ function parseServiceArgs(tokens) {
|
|
|
22641
22900
|
}
|
|
22642
22901
|
cwd = requireValue6(rest, token);
|
|
22643
22902
|
break;
|
|
22903
|
+
case "--env":
|
|
22904
|
+
if (action !== "deploy" && action !== "init" && action !== "stop") {
|
|
22905
|
+
throw new Error(`Unknown service ${action} option: ${token}`);
|
|
22906
|
+
}
|
|
22907
|
+
env = requireValue6(rest, token);
|
|
22908
|
+
break;
|
|
22644
22909
|
case "--page":
|
|
22645
22910
|
page = Number.parseInt(requireValue6(rest, token), 10);
|
|
22646
22911
|
break;
|
|
@@ -22668,10 +22933,16 @@ function parseServiceArgs(tokens) {
|
|
|
22668
22933
|
return { type: "service" /* Service */, action, namespace, name, baseUrl, json, page, history, search, follow };
|
|
22669
22934
|
}
|
|
22670
22935
|
if (action === "deploy" || action === "stop") {
|
|
22671
|
-
|
|
22936
|
+
if (action === "deploy" && !env) {
|
|
22937
|
+
throw new Error("Missing required option --env for service deploy");
|
|
22938
|
+
}
|
|
22939
|
+
return { type: "service" /* Service */, action, namespace, name, env, baseUrl, json };
|
|
22672
22940
|
}
|
|
22673
22941
|
if (action === "init") {
|
|
22674
|
-
|
|
22942
|
+
if (!env) {
|
|
22943
|
+
throw new Error("Missing required option --env for service init");
|
|
22944
|
+
}
|
|
22945
|
+
return { type: "service" /* Service */, action, namespace, name, env, cwd, baseUrl, json };
|
|
22675
22946
|
}
|
|
22676
22947
|
return { type: "service" /* Service */, action, namespace, name, baseUrl, json };
|
|
22677
22948
|
}
|
|
@@ -22839,6 +23110,106 @@ function parseBareRenameId3(value, entityName) {
|
|
|
22839
23110
|
function looksLikeNamespacedRef(value) {
|
|
22840
23111
|
return value.includes(":") && !value.startsWith("-");
|
|
22841
23112
|
}
|
|
23113
|
+
function parseServiceEnvDefinitionArgs(appId, tokens) {
|
|
23114
|
+
const rest = [...tokens];
|
|
23115
|
+
const action = rest.shift();
|
|
23116
|
+
if (!action) {
|
|
23117
|
+
throw new Error("Usage: service <ns:service> env list|get|add|expose");
|
|
23118
|
+
}
|
|
23119
|
+
let baseUrl;
|
|
23120
|
+
let json = false;
|
|
23121
|
+
if (action === "list") {
|
|
23122
|
+
while (rest.length > 0) {
|
|
23123
|
+
const token = rest.shift();
|
|
23124
|
+
switch (token) {
|
|
23125
|
+
case "--base-url":
|
|
23126
|
+
baseUrl = requireValue6(rest, token);
|
|
23127
|
+
break;
|
|
23128
|
+
case "--json":
|
|
23129
|
+
json = true;
|
|
23130
|
+
break;
|
|
23131
|
+
default:
|
|
23132
|
+
throw new Error(`Unknown service env list option: ${token}`);
|
|
23133
|
+
}
|
|
23134
|
+
}
|
|
23135
|
+
return { type: "service" /* Service */, action: "service-env-list", appId, baseUrl, json };
|
|
23136
|
+
}
|
|
23137
|
+
if (action === "get" || action === "add") {
|
|
23138
|
+
const envName = rest.shift();
|
|
23139
|
+
if (!envName || envName.startsWith("-")) {
|
|
23140
|
+
throw new Error(`Usage: service <ns:service> env ${action} <env> [--base-url <url>] [--json]`);
|
|
23141
|
+
}
|
|
23142
|
+
while (rest.length > 0) {
|
|
23143
|
+
const token = rest.shift();
|
|
23144
|
+
switch (token) {
|
|
23145
|
+
case "--base-url":
|
|
23146
|
+
baseUrl = requireValue6(rest, token);
|
|
23147
|
+
break;
|
|
23148
|
+
case "--json":
|
|
23149
|
+
json = true;
|
|
23150
|
+
break;
|
|
23151
|
+
default:
|
|
23152
|
+
throw new Error(`Unknown service env ${action} option: ${token}`);
|
|
23153
|
+
}
|
|
23154
|
+
}
|
|
23155
|
+
return {
|
|
23156
|
+
type: "service" /* Service */,
|
|
23157
|
+
action: action === "get" ? "service-env-get" : "service-env-add",
|
|
23158
|
+
appId,
|
|
23159
|
+
envName,
|
|
23160
|
+
baseUrl,
|
|
23161
|
+
json
|
|
23162
|
+
};
|
|
23163
|
+
}
|
|
23164
|
+
if (action === "expose") {
|
|
23165
|
+
const envName = rest.shift();
|
|
23166
|
+
if (!envName || envName.startsWith("-")) {
|
|
23167
|
+
throw new Error("Usage: service <ns:service> env expose <env> [--type https|websocket] [--domain <domain>] [--off]");
|
|
23168
|
+
}
|
|
23169
|
+
let exposeType;
|
|
23170
|
+
let domain;
|
|
23171
|
+
let off = false;
|
|
23172
|
+
while (rest.length > 0) {
|
|
23173
|
+
const token = rest.shift();
|
|
23174
|
+
switch (token) {
|
|
23175
|
+
case "--type": {
|
|
23176
|
+
const value = requireValue6(rest, token);
|
|
23177
|
+
if (value !== "https" && value !== "websocket") {
|
|
23178
|
+
throw new Error("--type must be https or websocket");
|
|
23179
|
+
}
|
|
23180
|
+
exposeType = value;
|
|
23181
|
+
break;
|
|
23182
|
+
}
|
|
23183
|
+
case "--domain":
|
|
23184
|
+
domain = requireValue6(rest, token);
|
|
23185
|
+
break;
|
|
23186
|
+
case "--off":
|
|
23187
|
+
off = true;
|
|
23188
|
+
break;
|
|
23189
|
+
case "--base-url":
|
|
23190
|
+
baseUrl = requireValue6(rest, token);
|
|
23191
|
+
break;
|
|
23192
|
+
case "--json":
|
|
23193
|
+
json = true;
|
|
23194
|
+
break;
|
|
23195
|
+
default:
|
|
23196
|
+
throw new Error(`Unknown service env expose option: ${token}`);
|
|
23197
|
+
}
|
|
23198
|
+
}
|
|
23199
|
+
return {
|
|
23200
|
+
type: "service" /* Service */,
|
|
23201
|
+
action: "service-env-expose",
|
|
23202
|
+
appId,
|
|
23203
|
+
envName,
|
|
23204
|
+
exposeType,
|
|
23205
|
+
domain,
|
|
23206
|
+
off,
|
|
23207
|
+
baseUrl,
|
|
23208
|
+
json
|
|
23209
|
+
};
|
|
23210
|
+
}
|
|
23211
|
+
throw new Error(`Unknown service env action: ${action}`);
|
|
23212
|
+
}
|
|
22842
23213
|
function parseServiceEnvArgs(appId, tokens) {
|
|
22843
23214
|
const rest = [...tokens];
|
|
22844
23215
|
const action = rest.shift();
|
|
@@ -22855,6 +23226,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22855
23226
|
const token = rest.shift();
|
|
22856
23227
|
switch (token) {
|
|
22857
23228
|
case "--scope":
|
|
23229
|
+
case "--env":
|
|
22858
23230
|
scope = requireValue6(rest, token);
|
|
22859
23231
|
break;
|
|
22860
23232
|
case "--include-secret-meta":
|
|
@@ -22886,6 +23258,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22886
23258
|
const token = rest.shift();
|
|
22887
23259
|
switch (token) {
|
|
22888
23260
|
case "--scope":
|
|
23261
|
+
case "--env":
|
|
22889
23262
|
scope = requireValue6(rest, token);
|
|
22890
23263
|
break;
|
|
22891
23264
|
case "--include-secret-value":
|
|
@@ -22901,9 +23274,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22901
23274
|
throw new Error(`Unknown service env get option: ${token}`);
|
|
22902
23275
|
}
|
|
22903
23276
|
}
|
|
22904
|
-
|
|
22905
|
-
throw new Error("Usage: service <ns:app> env get <key> --scope <scope> [--include-secret-value]");
|
|
22906
|
-
}
|
|
23277
|
+
scope = scope ?? "all";
|
|
22907
23278
|
return { type: "service" /* Service */, action: "env-get", appId, key, scope, includeSecretValue, baseUrl, json };
|
|
22908
23279
|
}
|
|
22909
23280
|
if (action === "set") {
|
|
@@ -22922,6 +23293,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22922
23293
|
const token = rest.shift();
|
|
22923
23294
|
switch (token) {
|
|
22924
23295
|
case "--scope":
|
|
23296
|
+
case "--env":
|
|
22925
23297
|
scope = requireValue6(rest, token);
|
|
22926
23298
|
break;
|
|
22927
23299
|
case "--secret":
|
|
@@ -22940,9 +23312,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22940
23312
|
throw new Error(`Unknown service env set option: ${token}`);
|
|
22941
23313
|
}
|
|
22942
23314
|
}
|
|
22943
|
-
|
|
22944
|
-
throw new Error("Usage: service <ns:app> env set <key> [value] --scope <scope> [--secret] [--prompt]");
|
|
22945
|
-
}
|
|
23315
|
+
scope = scope ?? "all";
|
|
22946
23316
|
if (!value && !secret && !prompt) {
|
|
22947
23317
|
throw new Error("Missing env value. Pass a value or use --prompt.");
|
|
22948
23318
|
}
|
|
@@ -22958,6 +23328,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22958
23328
|
const token = rest.shift();
|
|
22959
23329
|
switch (token) {
|
|
22960
23330
|
case "--scope":
|
|
23331
|
+
case "--env":
|
|
22961
23332
|
scope = requireValue6(rest, token);
|
|
22962
23333
|
break;
|
|
22963
23334
|
case "--base-url":
|
|
@@ -22970,9 +23341,7 @@ function parseServiceEnvArgs(appId, tokens) {
|
|
|
22970
23341
|
throw new Error(`Unknown service env unset option: ${token}`);
|
|
22971
23342
|
}
|
|
22972
23343
|
}
|
|
22973
|
-
|
|
22974
|
-
throw new Error("Usage: service <ns:app> env unset <key> --scope <scope>");
|
|
22975
|
-
}
|
|
23344
|
+
scope = scope ?? "all";
|
|
22976
23345
|
return { type: "service" /* Service */, action: "env-unset", appId, key, scope, baseUrl, json };
|
|
22977
23346
|
}
|
|
22978
23347
|
if (action === "resolve") {
|