@phala/cloud 0.2.0 → 0.2.1-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/actions/cvms/commit_cvm_provision.d.ts +69 -21
- package/dist/actions/cvms/get_cvm_list.d.ts +16 -16
- package/dist/actions/cvms/provision_cvm.d.ts +132 -50
- package/dist/actions/index.d.ts +1 -1
- package/dist/actions/kms/get_kms_list.d.ts +4 -4
- package/dist/actions/list-instance-types.d.ts +295 -90
- package/dist/create-client.d.ts +21 -7
- package/dist/index.js +164 -48
- package/dist/index.mjs +154 -44
- package/dist/utils/errors.d.ts +137 -20
- package/dist/utils/index.d.ts +1 -1
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -12,8 +12,11 @@ var ApiErrorSchema = z.object({
|
|
|
12
12
|
z.object({
|
|
13
13
|
msg: z.string(),
|
|
14
14
|
type: z.string().optional(),
|
|
15
|
-
ctx: z.record(z.unknown()).optional()
|
|
16
|
-
|
|
15
|
+
ctx: z.record(z.unknown()).optional(),
|
|
16
|
+
loc: z.array(z.union([z.string(), z.number()])).optional(),
|
|
17
|
+
input: z.unknown().optional()
|
|
18
|
+
}).passthrough()
|
|
19
|
+
// Allow additional fields
|
|
17
20
|
),
|
|
18
21
|
z.record(z.unknown())
|
|
19
22
|
]).optional(),
|
|
@@ -116,6 +119,9 @@ var UnknownError = class extends PhalaCloudError {
|
|
|
116
119
|
}
|
|
117
120
|
};
|
|
118
121
|
function extractFieldPath(loc) {
|
|
122
|
+
if (!loc || !Array.isArray(loc)) {
|
|
123
|
+
return "unknown";
|
|
124
|
+
}
|
|
119
125
|
const filtered = loc.filter((part) => {
|
|
120
126
|
if (typeof part === "string") {
|
|
121
127
|
return !["body", "query", "path", "header"].includes(part);
|
|
@@ -131,12 +137,21 @@ function parseValidationErrors(detail) {
|
|
|
131
137
|
message: typeof detail === "string" ? detail : "Validation error"
|
|
132
138
|
};
|
|
133
139
|
}
|
|
134
|
-
const errors = detail.map(
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
+
const errors = detail.map(
|
|
141
|
+
(item, index) => {
|
|
142
|
+
const field = extractFieldPath(item.loc);
|
|
143
|
+
let displayField = field;
|
|
144
|
+
if (field === "unknown" && item.type) {
|
|
145
|
+
displayField = item.type === "missing" ? "required field" : item.type;
|
|
146
|
+
}
|
|
147
|
+
return {
|
|
148
|
+
field: displayField,
|
|
149
|
+
message: item.msg,
|
|
150
|
+
type: item.type,
|
|
151
|
+
context: item.ctx
|
|
152
|
+
};
|
|
153
|
+
}
|
|
154
|
+
);
|
|
140
155
|
const count = errors.length;
|
|
141
156
|
const message = count === 1 ? `Validation failed: ${errors[0].message}` : `Validation failed (${count} issue${count > 1 ? "s" : ""})`;
|
|
142
157
|
return { errors, message };
|
|
@@ -179,13 +194,21 @@ function parseApiError(requestError) {
|
|
|
179
194
|
const status = requestError.status ?? 0;
|
|
180
195
|
const statusText = requestError.statusText ?? "Unknown Error";
|
|
181
196
|
const detail = requestError.detail;
|
|
197
|
+
const structured = parseStructuredError(detail);
|
|
198
|
+
if (structured) {
|
|
199
|
+
return new ResourceError(structured.message, {
|
|
200
|
+
status,
|
|
201
|
+
statusText,
|
|
202
|
+
detail,
|
|
203
|
+
errorCode: structured.error_code,
|
|
204
|
+
structuredDetails: structured.details,
|
|
205
|
+
suggestions: structured.suggestions,
|
|
206
|
+
links: structured.links
|
|
207
|
+
});
|
|
208
|
+
}
|
|
182
209
|
const errorType = categorizeErrorType(status);
|
|
183
210
|
const message = extractPrimaryMessage(status, detail, requestError.message);
|
|
184
|
-
const commonData = {
|
|
185
|
-
status,
|
|
186
|
-
statusText,
|
|
187
|
-
detail
|
|
188
|
-
};
|
|
211
|
+
const commonData = { status, statusText, detail };
|
|
189
212
|
if (errorType === "validation" && Array.isArray(detail)) {
|
|
190
213
|
const { errors } = parseValidationErrors(detail);
|
|
191
214
|
return new ValidationError(message, {
|
|
@@ -247,6 +270,67 @@ function getErrorMessage(error) {
|
|
|
247
270
|
}
|
|
248
271
|
return "Unknown error occurred";
|
|
249
272
|
}
|
|
273
|
+
var ResourceError = class extends BusinessError {
|
|
274
|
+
constructor(message, data) {
|
|
275
|
+
super(message, data);
|
|
276
|
+
this.isResourceError = true;
|
|
277
|
+
this.errorCode = data.errorCode;
|
|
278
|
+
this.structuredDetails = data.structuredDetails;
|
|
279
|
+
this.suggestions = data.suggestions;
|
|
280
|
+
this.links = data.links;
|
|
281
|
+
}
|
|
282
|
+
};
|
|
283
|
+
function parseStructuredError(detail) {
|
|
284
|
+
if (!detail || typeof detail !== "object") {
|
|
285
|
+
return null;
|
|
286
|
+
}
|
|
287
|
+
const obj = detail;
|
|
288
|
+
if (obj.error_code && typeof obj.error_code === "string" && obj.message && typeof obj.message === "string") {
|
|
289
|
+
return {
|
|
290
|
+
error_code: obj.error_code,
|
|
291
|
+
message: obj.message,
|
|
292
|
+
details: obj.details,
|
|
293
|
+
suggestions: obj.suggestions,
|
|
294
|
+
links: obj.links
|
|
295
|
+
};
|
|
296
|
+
}
|
|
297
|
+
return null;
|
|
298
|
+
}
|
|
299
|
+
function formatStructuredError(error, options) {
|
|
300
|
+
const { showErrorCode = true, showSuggestions = true, showLinks = true } = options ?? {};
|
|
301
|
+
const parts = [];
|
|
302
|
+
if (showErrorCode && error.errorCode) {
|
|
303
|
+
parts.push(`Error [${error.errorCode}]: ${error.message}`);
|
|
304
|
+
} else {
|
|
305
|
+
parts.push(error.message);
|
|
306
|
+
}
|
|
307
|
+
if (error.structuredDetails && error.structuredDetails.length > 0) {
|
|
308
|
+
parts.push("");
|
|
309
|
+
parts.push("Details:");
|
|
310
|
+
error.structuredDetails.forEach((d) => {
|
|
311
|
+
if (d.message) {
|
|
312
|
+
parts.push(` - ${d.message}`);
|
|
313
|
+
} else if (d.field && d.value !== void 0) {
|
|
314
|
+
parts.push(` - ${d.field}: ${d.value}`);
|
|
315
|
+
}
|
|
316
|
+
});
|
|
317
|
+
}
|
|
318
|
+
if (showSuggestions && error.suggestions && error.suggestions.length > 0) {
|
|
319
|
+
parts.push("");
|
|
320
|
+
parts.push("Suggestions:");
|
|
321
|
+
error.suggestions.forEach((s) => {
|
|
322
|
+
parts.push(` - ${s}`);
|
|
323
|
+
});
|
|
324
|
+
}
|
|
325
|
+
if (showLinks && error.links && error.links.length > 0) {
|
|
326
|
+
parts.push("");
|
|
327
|
+
parts.push("Learn more:");
|
|
328
|
+
error.links.forEach((link) => {
|
|
329
|
+
parts.push(` - ${link.label}: ${link.url}`);
|
|
330
|
+
});
|
|
331
|
+
}
|
|
332
|
+
return parts.join("\n");
|
|
333
|
+
}
|
|
250
334
|
|
|
251
335
|
// src/client.ts
|
|
252
336
|
var SUPPORTED_API_VERSIONS = ["2025-05-31", "2025-10-28"];
|
|
@@ -804,10 +888,6 @@ var { action: getAvailableNodes, safeAction: safeGetAvailableNodes } = defineSim
|
|
|
804
888
|
|
|
805
889
|
// src/actions/list-instance-types.ts
|
|
806
890
|
import { z as z5 } from "zod";
|
|
807
|
-
var ListInstanceTypesRequestSchema = z5.object({
|
|
808
|
-
page: z5.number().int().min(1).optional().default(1),
|
|
809
|
-
page_size: z5.number().int().min(1).max(1e3).optional().default(100)
|
|
810
|
-
}).strict();
|
|
811
891
|
var InstanceTypeSchema = z5.object({
|
|
812
892
|
id: z5.string(),
|
|
813
893
|
name: z5.string(),
|
|
@@ -816,22 +896,34 @@ var InstanceTypeSchema = z5.object({
|
|
|
816
896
|
memory_mb: z5.number(),
|
|
817
897
|
hourly_rate: z5.string(),
|
|
818
898
|
requires_gpu: z5.boolean(),
|
|
819
|
-
|
|
820
|
-
|
|
899
|
+
default_disk_size_gb: z5.number().default(20),
|
|
900
|
+
family: z5.string().nullable()
|
|
821
901
|
}).passthrough();
|
|
822
|
-
var
|
|
902
|
+
var FamilyGroupSchema = z5.object({
|
|
903
|
+
name: z5.string(),
|
|
904
|
+
items: z5.array(InstanceTypeSchema),
|
|
905
|
+
total: z5.number()
|
|
906
|
+
}).strict();
|
|
907
|
+
var AllFamiliesResponseSchema = z5.object({
|
|
908
|
+
result: z5.array(FamilyGroupSchema)
|
|
909
|
+
}).strict();
|
|
910
|
+
var FamilyInstanceTypesResponseSchema = z5.object({
|
|
823
911
|
items: z5.array(InstanceTypeSchema),
|
|
824
912
|
total: z5.number(),
|
|
825
|
-
|
|
826
|
-
page_size: z5.number(),
|
|
827
|
-
pages: z5.number()
|
|
913
|
+
family: z5.string()
|
|
828
914
|
}).strict();
|
|
829
|
-
var
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
915
|
+
var ListFamilyInstanceTypesRequestSchema = z5.object({
|
|
916
|
+
family: z5.string()
|
|
917
|
+
}).strict();
|
|
918
|
+
var { action: listAllInstanceTypeFamilies, safeAction: safeListAllInstanceTypeFamilies } = defineAction(
|
|
919
|
+
AllFamiliesResponseSchema,
|
|
920
|
+
async (client) => {
|
|
921
|
+
return await client.get("/instance-types");
|
|
922
|
+
}
|
|
923
|
+
);
|
|
924
|
+
var { action: listFamilyInstanceTypes, safeAction: safeListFamilyInstanceTypes } = defineAction(FamilyInstanceTypesResponseSchema, async (client, request) => {
|
|
925
|
+
const validated = ListFamilyInstanceTypesRequestSchema.parse(request);
|
|
926
|
+
return await client.get(`/instance-types/${validated.family}`);
|
|
835
927
|
});
|
|
836
928
|
|
|
837
929
|
// src/actions/workspaces/list_workspaces.ts
|
|
@@ -1051,6 +1143,7 @@ var ProvisionCvmSchema = z10.object({
|
|
|
1051
1143
|
fmspc: z10.string().nullable().optional(),
|
|
1052
1144
|
device_id: z10.string().nullable().optional(),
|
|
1053
1145
|
os_image_hash: z10.string().nullable().optional(),
|
|
1146
|
+
instance_type: z10.string().nullable().optional(),
|
|
1054
1147
|
teepod_id: z10.number().nullable().optional(),
|
|
1055
1148
|
// Will be transformed to node_id
|
|
1056
1149
|
node_id: z10.number().nullable().optional(),
|
|
@@ -1064,19 +1157,24 @@ var ProvisionCvmSchema = z10.object({
|
|
|
1064
1157
|
});
|
|
1065
1158
|
var ProvisionCvmRequestSchema = z10.object({
|
|
1066
1159
|
node_id: z10.number().optional(),
|
|
1067
|
-
// recommended
|
|
1160
|
+
// recommended - optional, system auto-selects if not specified
|
|
1068
1161
|
teepod_id: z10.number().optional(),
|
|
1069
1162
|
// deprecated, for compatibility
|
|
1163
|
+
region: z10.string().optional(),
|
|
1164
|
+
// optional - region filter for auto-selection
|
|
1070
1165
|
name: z10.string(),
|
|
1071
|
-
|
|
1072
|
-
|
|
1073
|
-
|
|
1074
|
-
|
|
1166
|
+
instance_type: z10.string().default("tdx.small"),
|
|
1167
|
+
// defaults to "tdx.small"
|
|
1168
|
+
image: z10.string().optional(),
|
|
1169
|
+
vcpu: z10.number().optional(),
|
|
1170
|
+
memory: z10.number().optional(),
|
|
1171
|
+
disk_size: z10.number().optional(),
|
|
1075
1172
|
compose_file: z10.object({
|
|
1076
1173
|
allowed_envs: z10.array(z10.string()).optional(),
|
|
1077
1174
|
pre_launch_script: z10.string().optional(),
|
|
1078
1175
|
docker_compose_file: z10.string().optional(),
|
|
1079
|
-
name: z10.string().optional(),
|
|
1176
|
+
name: z10.string().optional().default(""),
|
|
1177
|
+
// optional with default empty string
|
|
1080
1178
|
kms_enabled: z10.boolean().optional(),
|
|
1081
1179
|
public_logs: z10.boolean().optional(),
|
|
1082
1180
|
public_sysinfo: z10.boolean().optional(),
|
|
@@ -1086,8 +1184,11 @@ var ProvisionCvmRequestSchema = z10.object({
|
|
|
1086
1184
|
// deprecated, for compatibility
|
|
1087
1185
|
}),
|
|
1088
1186
|
listed: z10.boolean().optional(),
|
|
1089
|
-
instance_type: z10.string().nullable().optional(),
|
|
1090
1187
|
kms_id: z10.string().optional(),
|
|
1188
|
+
kms: z10.enum(["PHALA", "ETHEREUM", "BASE"]).optional(),
|
|
1189
|
+
// KMS type selection (defaults to PHALA)
|
|
1190
|
+
kms_contract: z10.string().optional(),
|
|
1191
|
+
// KMS contract address for on-chain KMS
|
|
1091
1192
|
env_keys: z10.array(z10.string()).optional()
|
|
1092
1193
|
}).passthrough();
|
|
1093
1194
|
function handleGatewayCompatibility(appCompose) {
|
|
@@ -1112,7 +1213,8 @@ function handleGatewayCompatibility(appCompose) {
|
|
|
1112
1213
|
};
|
|
1113
1214
|
}
|
|
1114
1215
|
var { action: provisionCvm, safeAction: safeProvisionCvm } = defineAction(ProvisionCvmSchema, async (client, appCompose) => {
|
|
1115
|
-
const
|
|
1216
|
+
const validated = ProvisionCvmRequestSchema.parse(appCompose);
|
|
1217
|
+
const body = handleGatewayCompatibility(validated);
|
|
1116
1218
|
let requestBody = { ...body };
|
|
1117
1219
|
if (typeof body.node_id === "number") {
|
|
1118
1220
|
requestBody = { ...body, teepod_id: body.node_id };
|
|
@@ -1156,7 +1258,7 @@ var CommitCvmProvisionSchema = z11.object({
|
|
|
1156
1258
|
var CommitCvmProvisionRequestSchema = z11.object({
|
|
1157
1259
|
encrypted_env: z11.string().optional().nullable(),
|
|
1158
1260
|
app_id: z11.string(),
|
|
1159
|
-
compose_hash: z11.string()
|
|
1261
|
+
compose_hash: z11.string(),
|
|
1160
1262
|
kms_id: z11.string().optional(),
|
|
1161
1263
|
contract_address: z11.string().optional(),
|
|
1162
1264
|
deployer_address: z11.string().optional(),
|
|
@@ -1699,8 +1801,10 @@ function createClient2(config = {}) {
|
|
|
1699
1801
|
safeGetCurrentUser,
|
|
1700
1802
|
getAvailableNodes,
|
|
1701
1803
|
safeGetAvailableNodes,
|
|
1702
|
-
|
|
1703
|
-
|
|
1804
|
+
listAllInstanceTypeFamilies,
|
|
1805
|
+
safeListAllInstanceTypeFamilies,
|
|
1806
|
+
listFamilyInstanceTypes,
|
|
1807
|
+
safeListFamilyInstanceTypes,
|
|
1704
1808
|
listWorkspaces,
|
|
1705
1809
|
safeListWorkspaces,
|
|
1706
1810
|
getWorkspace,
|
|
@@ -3220,6 +3324,7 @@ import { getComposeHash as getComposeHash2 } from "@phala/dstack-sdk/get-compose
|
|
|
3220
3324
|
import { verifyEnvEncryptPublicKey } from "@phala/dstack-sdk/verify-env-encrypt-public-key";
|
|
3221
3325
|
export {
|
|
3222
3326
|
AddComposeHashSchema,
|
|
3327
|
+
AllFamiliesResponseSchema,
|
|
3223
3328
|
ApiErrorSchema,
|
|
3224
3329
|
AuthError,
|
|
3225
3330
|
AvailableNodesSchema,
|
|
@@ -3244,6 +3349,8 @@ export {
|
|
|
3244
3349
|
DeleteCvmRequestSchema,
|
|
3245
3350
|
DeployAppAuthRequestSchema,
|
|
3246
3351
|
DeployAppAuthSchema,
|
|
3352
|
+
FamilyGroupSchema,
|
|
3353
|
+
FamilyInstanceTypesResponseSchema,
|
|
3247
3354
|
GetAppEnvEncryptPubKeyRequestSchema,
|
|
3248
3355
|
GetAppEnvEncryptPubKeySchema,
|
|
3249
3356
|
GetAvailableOSImagesRequestSchema,
|
|
@@ -3263,7 +3370,7 @@ export {
|
|
|
3263
3370
|
GetKmsListSchema,
|
|
3264
3371
|
InstanceTypeSchema,
|
|
3265
3372
|
KmsInfoSchema,
|
|
3266
|
-
|
|
3373
|
+
ListFamilyInstanceTypesRequestSchema,
|
|
3267
3374
|
ListWorkspacesSchema,
|
|
3268
3375
|
ManagedUserSchema,
|
|
3269
3376
|
MaxRetriesExceededError,
|
|
@@ -3271,7 +3378,6 @@ export {
|
|
|
3271
3378
|
NextAppIdsRequestSchema,
|
|
3272
3379
|
NextAppIdsSchema,
|
|
3273
3380
|
OSImageVariantSchema,
|
|
3274
|
-
PaginatedInstanceTypesSchema,
|
|
3275
3381
|
PaginationMetadataSchema,
|
|
3276
3382
|
PhalaCloudError,
|
|
3277
3383
|
ProvisionCvmComposeFileUpdateRequestSchema,
|
|
@@ -3279,6 +3385,7 @@ export {
|
|
|
3279
3385
|
ProvisionCvmRequestSchema,
|
|
3280
3386
|
ProvisionCvmSchema,
|
|
3281
3387
|
RequestError,
|
|
3388
|
+
ResourceError,
|
|
3282
3389
|
RestartCvmRequestSchema,
|
|
3283
3390
|
SUPPORTED_CHAINS,
|
|
3284
3391
|
ServerError,
|
|
@@ -3323,6 +3430,7 @@ export {
|
|
|
3323
3430
|
executeTransactionWithRetry,
|
|
3324
3431
|
extractNetworkClients,
|
|
3325
3432
|
formatErrorMessage,
|
|
3433
|
+
formatStructuredError,
|
|
3326
3434
|
formatValidationErrors,
|
|
3327
3435
|
getAppEnvEncryptPubKey,
|
|
3328
3436
|
getAvailableNodes,
|
|
@@ -3343,7 +3451,8 @@ export {
|
|
|
3343
3451
|
getKmsList,
|
|
3344
3452
|
getValidationFields,
|
|
3345
3453
|
getWorkspace,
|
|
3346
|
-
|
|
3454
|
+
listAllInstanceTypeFamilies,
|
|
3455
|
+
listFamilyInstanceTypes,
|
|
3347
3456
|
listWorkspaces,
|
|
3348
3457
|
nextAppIds,
|
|
3349
3458
|
parseApiError,
|
|
@@ -3375,7 +3484,8 @@ export {
|
|
|
3375
3484
|
safeGetKmsInfo,
|
|
3376
3485
|
safeGetKmsList,
|
|
3377
3486
|
safeGetWorkspace,
|
|
3378
|
-
|
|
3487
|
+
safeListAllInstanceTypeFamilies,
|
|
3488
|
+
safeListFamilyInstanceTypes,
|
|
3379
3489
|
safeListWorkspaces,
|
|
3380
3490
|
safeNextAppIds,
|
|
3381
3491
|
safeProvisionCvm,
|
package/dist/utils/errors.d.ts
CHANGED
|
@@ -8,33 +8,43 @@ export declare const ApiErrorSchema: z.ZodObject<{
|
|
|
8
8
|
msg: z.ZodString;
|
|
9
9
|
type: z.ZodOptional<z.ZodString>;
|
|
10
10
|
ctx: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
}
|
|
11
|
+
loc: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodNumber]>, "many">>;
|
|
12
|
+
input: z.ZodOptional<z.ZodUnknown>;
|
|
13
|
+
}, "passthrough", z.ZodTypeAny, z.objectOutputType<{
|
|
14
|
+
msg: z.ZodString;
|
|
15
|
+
type: z.ZodOptional<z.ZodString>;
|
|
16
|
+
ctx: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
17
|
+
loc: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodNumber]>, "many">>;
|
|
18
|
+
input: z.ZodOptional<z.ZodUnknown>;
|
|
19
|
+
}, z.ZodTypeAny, "passthrough">, z.objectInputType<{
|
|
20
|
+
msg: z.ZodString;
|
|
21
|
+
type: z.ZodOptional<z.ZodString>;
|
|
22
|
+
ctx: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
23
|
+
loc: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodNumber]>, "many">>;
|
|
24
|
+
input: z.ZodOptional<z.ZodUnknown>;
|
|
25
|
+
}, z.ZodTypeAny, "passthrough">>, "many">, z.ZodRecord<z.ZodString, z.ZodUnknown>]>>;
|
|
20
26
|
type: z.ZodOptional<z.ZodString>;
|
|
21
27
|
code: z.ZodOptional<z.ZodString>;
|
|
22
28
|
}, "strip", z.ZodTypeAny, {
|
|
23
29
|
code?: string | undefined;
|
|
24
30
|
type?: string | undefined;
|
|
25
|
-
detail?: string | Record<string, unknown> | {
|
|
26
|
-
msg:
|
|
27
|
-
type
|
|
28
|
-
ctx
|
|
29
|
-
|
|
31
|
+
detail?: string | Record<string, unknown> | z.objectOutputType<{
|
|
32
|
+
msg: z.ZodString;
|
|
33
|
+
type: z.ZodOptional<z.ZodString>;
|
|
34
|
+
ctx: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
35
|
+
loc: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodNumber]>, "many">>;
|
|
36
|
+
input: z.ZodOptional<z.ZodUnknown>;
|
|
37
|
+
}, z.ZodTypeAny, "passthrough">[] | undefined;
|
|
30
38
|
}, {
|
|
31
39
|
code?: string | undefined;
|
|
32
40
|
type?: string | undefined;
|
|
33
|
-
detail?: string | Record<string, unknown> | {
|
|
34
|
-
msg:
|
|
35
|
-
type
|
|
36
|
-
ctx
|
|
37
|
-
|
|
41
|
+
detail?: string | Record<string, unknown> | z.objectInputType<{
|
|
42
|
+
msg: z.ZodString;
|
|
43
|
+
type: z.ZodOptional<z.ZodString>;
|
|
44
|
+
ctx: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
|
|
45
|
+
loc: z.ZodOptional<z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodNumber]>, "many">>;
|
|
46
|
+
input: z.ZodOptional<z.ZodUnknown>;
|
|
47
|
+
}, z.ZodTypeAny, "passthrough">[] | undefined;
|
|
38
48
|
}>;
|
|
39
49
|
export type ApiError = z.infer<typeof ApiErrorSchema>;
|
|
40
50
|
/**
|
|
@@ -94,6 +104,9 @@ export declare class RequestError extends PhalaCloudError implements ApiError {
|
|
|
94
104
|
msg: string;
|
|
95
105
|
type?: string;
|
|
96
106
|
ctx?: Record<string, unknown>;
|
|
107
|
+
loc?: (string | number)[];
|
|
108
|
+
input?: unknown;
|
|
109
|
+
[key: string]: unknown;
|
|
97
110
|
}>;
|
|
98
111
|
code?: string | undefined;
|
|
99
112
|
type?: string | undefined;
|
|
@@ -122,6 +135,9 @@ export declare class ValidationError extends PhalaCloudError {
|
|
|
122
135
|
msg: string;
|
|
123
136
|
type?: string;
|
|
124
137
|
ctx?: Record<string, unknown>;
|
|
138
|
+
loc?: (string | number)[];
|
|
139
|
+
input?: unknown;
|
|
140
|
+
[key: string]: unknown;
|
|
125
141
|
}>;
|
|
126
142
|
validationErrors: ValidationErrorItem[];
|
|
127
143
|
});
|
|
@@ -162,6 +178,7 @@ export declare class UnknownError extends PhalaCloudError {
|
|
|
162
178
|
* Parse RequestError into PhalaCloudError instance
|
|
163
179
|
*
|
|
164
180
|
* Returns the appropriate error subclass based on status code:
|
|
181
|
+
* - New structured errors (with error_code) → ResourceError
|
|
165
182
|
* - 422 → ValidationError (with validationErrors array)
|
|
166
183
|
* - 401, 403 → AuthError
|
|
167
184
|
* - 400, 409, etc. → BusinessError
|
|
@@ -176,7 +193,13 @@ export declare class UnknownError extends PhalaCloudError {
|
|
|
176
193
|
* try {
|
|
177
194
|
* await client.post('/cvms', data);
|
|
178
195
|
* } catch (error) {
|
|
179
|
-
* if (error instanceof
|
|
196
|
+
* if (error instanceof ResourceError) {
|
|
197
|
+
* // New structured error with error code
|
|
198
|
+
* console.error(`Error [${error.errorCode}]: ${error.message}`);
|
|
199
|
+
* if (error.suggestions) {
|
|
200
|
+
* error.suggestions.forEach(s => console.log(s));
|
|
201
|
+
* }
|
|
202
|
+
* } else if (error instanceof ValidationError) {
|
|
180
203
|
* // TypeScript knows error.validationErrors exists
|
|
181
204
|
* error.validationErrors.forEach(e => {
|
|
182
205
|
* console.error(`${e.field}: ${e.message}`);
|
|
@@ -259,3 +282,97 @@ export declare function formatErrorMessage(error: PhalaCloudError, options?: {
|
|
|
259
282
|
* @returns Error message string
|
|
260
283
|
*/
|
|
261
284
|
export declare function getErrorMessage(error: ApiError): string;
|
|
285
|
+
/**
|
|
286
|
+
* Structured error detail from new error format (ERR-xxxx codes)
|
|
287
|
+
*/
|
|
288
|
+
export interface StructuredErrorDetail {
|
|
289
|
+
field?: string;
|
|
290
|
+
value?: unknown;
|
|
291
|
+
message?: string;
|
|
292
|
+
}
|
|
293
|
+
/**
|
|
294
|
+
* Error link from structured error response
|
|
295
|
+
*/
|
|
296
|
+
export interface ErrorLink {
|
|
297
|
+
url: string;
|
|
298
|
+
label: string;
|
|
299
|
+
}
|
|
300
|
+
/**
|
|
301
|
+
* New structured error response format with unique error codes
|
|
302
|
+
*/
|
|
303
|
+
export interface StructuredErrorResponse {
|
|
304
|
+
error_code: string;
|
|
305
|
+
message: string;
|
|
306
|
+
details?: StructuredErrorDetail[];
|
|
307
|
+
suggestions?: string[];
|
|
308
|
+
links?: ErrorLink[];
|
|
309
|
+
}
|
|
310
|
+
/**
|
|
311
|
+
* Resource provisioning error with structured details
|
|
312
|
+
* Extends BusinessError to handle new error format from backend
|
|
313
|
+
*
|
|
314
|
+
* Use instanceof to check: if (error instanceof ResourceError) { ... }
|
|
315
|
+
* Or use property: if (error.isResourceError) { ... }
|
|
316
|
+
*/
|
|
317
|
+
export declare class ResourceError extends BusinessError {
|
|
318
|
+
readonly isResourceError: true;
|
|
319
|
+
readonly errorCode?: string;
|
|
320
|
+
readonly structuredDetails?: StructuredErrorDetail[];
|
|
321
|
+
readonly suggestions?: string[];
|
|
322
|
+
readonly links?: ErrorLink[];
|
|
323
|
+
constructor(message: string, data: {
|
|
324
|
+
status: number;
|
|
325
|
+
statusText: string;
|
|
326
|
+
detail?: string | Record<string, unknown> | Array<{
|
|
327
|
+
msg: string;
|
|
328
|
+
type?: string;
|
|
329
|
+
ctx?: Record<string, unknown>;
|
|
330
|
+
loc?: (string | number)[];
|
|
331
|
+
input?: unknown;
|
|
332
|
+
[key: string]: unknown;
|
|
333
|
+
}>;
|
|
334
|
+
errorCode?: string;
|
|
335
|
+
structuredDetails?: StructuredErrorDetail[];
|
|
336
|
+
suggestions?: string[];
|
|
337
|
+
links?: ErrorLink[];
|
|
338
|
+
});
|
|
339
|
+
}
|
|
340
|
+
/**
|
|
341
|
+
* Format structured error for display
|
|
342
|
+
*
|
|
343
|
+
* @param error - Resource error with structured details
|
|
344
|
+
* @param options - Formatting options
|
|
345
|
+
* @returns Formatted error message
|
|
346
|
+
*
|
|
347
|
+
* @example
|
|
348
|
+
* ```typescript
|
|
349
|
+
* try {
|
|
350
|
+
* await client.provisionCvm(payload);
|
|
351
|
+
* } catch (error) {
|
|
352
|
+
* if (error instanceof ResourceError) {
|
|
353
|
+
* console.error(formatStructuredError(error));
|
|
354
|
+
* }
|
|
355
|
+
* }
|
|
356
|
+
* // Output:
|
|
357
|
+
* // Error [ERR-01-001]: The requested instance type does not exist
|
|
358
|
+
* //
|
|
359
|
+
* // Details:
|
|
360
|
+
* // - Instance type 'invalid' is not recognized
|
|
361
|
+
* //
|
|
362
|
+
* // Suggestions:
|
|
363
|
+
* // - Use a valid instance type: tdx.small, tdx.medium, or tdx.large
|
|
364
|
+
* // - Alternatively, specify CPU and memory requirements manually
|
|
365
|
+
* //
|
|
366
|
+
* // Learn more:
|
|
367
|
+
* // - View available instance types: https://cloud.phala.network/instances
|
|
368
|
+
* // - Contact support: https://cloud.phala.network/support
|
|
369
|
+
* ```
|
|
370
|
+
*/
|
|
371
|
+
export declare function formatStructuredError(error: ResourceError, options?: {
|
|
372
|
+
/** Show error code in output (default: true) */
|
|
373
|
+
showErrorCode?: boolean;
|
|
374
|
+
/** Show suggestions (default: true) */
|
|
375
|
+
showSuggestions?: boolean;
|
|
376
|
+
/** Show links (default: true) */
|
|
377
|
+
showLinks?: boolean;
|
|
378
|
+
}): string;
|
package/dist/utils/index.d.ts
CHANGED
|
@@ -2,7 +2,7 @@ export { encryptEnvVars } from "@phala/dstack-sdk/encrypt-env-vars";
|
|
|
2
2
|
export { getComposeHash, dumpAppCompose, preprocessAppCompose, sortObject, withComposeMethods, type AppCompose, type AppComposeWithMethods, type SortableValue, type SortableObject, type SortableArray, } from "./get_compose_hash";
|
|
3
3
|
export { asHex } from "./as-hex";
|
|
4
4
|
export { validateActionParameters, safeValidateActionParameters } from "./validate-parameters";
|
|
5
|
-
export { parseApiError, PhalaCloudError, RequestError, ValidationError, AuthError, BusinessError, ServerError, UnknownError, formatValidationErrors, formatErrorMessage, getErrorMessage, getValidationFields, type ValidationErrorItem, ApiErrorSchema, type ApiError, } from "./errors";
|
|
5
|
+
export { parseApiError, PhalaCloudError, RequestError, ValidationError, AuthError, BusinessError, ServerError, UnknownError, ResourceError, formatValidationErrors, formatErrorMessage, formatStructuredError, getErrorMessage, getValidationFields, type ValidationErrorItem, type StructuredErrorDetail, type ErrorLink, type StructuredErrorResponse, ApiErrorSchema, type ApiError, } from "./errors";
|
|
6
6
|
export { createNetworkClients, extractNetworkClients, checkNetworkStatus, checkBalance, validateNetworkPrerequisites, waitForTransactionReceipt, executeTransaction, NetworkError, WalletError, TransactionError, type NetworkConfig, type WalletConnection, type NetworkClients, type BalanceCheckResult, type TransactionOptions, type TransactionResult, } from "./network";
|
|
7
7
|
export { createTransactionTracker, executeBatchTransactions, executeTransactionWithRetry, estimateTransactionGas, type TransactionState, type TransactionStatus, type TransactionTracker, type BatchTransactionOptions, type BatchTransactionResult, type RetryOptions, type GasEstimationOptions, } from "./transaction";
|
|
8
8
|
export { createClientsFromPrivateKey, createClientsFromBrowser, autoCreateClients, switchToNetwork, addNetwork, } from "./client-factories";
|