@byte_fluffy/nexra-sdk 0.1.0-alpha.5 → 0.1.0-alpha.7
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/catalog.d.ts +1 -1
- package/dist/catalog.js +1 -1
- package/dist/{chunk-2C2ZZKUC.js → chunk-3ZBQVBMA.js} +1438 -47
- package/dist/{index-FyUOK0F-.d.ts → index-DLTP5_Ri.d.ts} +6 -1
- package/dist/index.d.ts +28 -11
- package/dist/index.js +92 -1137
- package/package.json +1 -1
|
@@ -66,7 +66,7 @@ var image_generated_default = [
|
|
|
66
66
|
}
|
|
67
67
|
},
|
|
68
68
|
image: {
|
|
69
|
-
title: "\
|
|
69
|
+
title: "\u53C2\u8003\u56FE\u7247",
|
|
70
70
|
description: "\u7528\u4E8E\u56FE\u7247\u7F16\u8F91\uFF0C\u6700\u591A 16 \u5F20\uFF0C\u6BCF\u5F20\u5C0F\u4E8E 50 MB\u3002\u63D0\u4F9B\u8499\u7248\u65F6\uFF0C\u8499\u7248\u5E94\u7528\u4E8E\u7B2C\u4E00\u5F20\u8F93\u5165\u56FE\uFF0C\u5E76\u4E14\u5FC5\u987B\u4E0E\u8BE5\u56FE\u683C\u5F0F\u548C\u5C3A\u5BF8\u4E00\u81F4\u3002Task \u4E2D\u586B\u5199\u56FE\u7247 URL \u6216 Data URL\uFF1B\u6267\u884C\u65F6\u6309\u539F\u751F image[] \u5B57\u6BB5\u4E0A\u4F20\u6587\u4EF6\uFF0C\u987A\u5E8F\u4E0D\u53D8\u3002",
|
|
71
71
|
anyOf: [
|
|
72
72
|
{
|
|
@@ -607,7 +607,7 @@ var image_generated_default = [
|
|
|
607
607
|
}
|
|
608
608
|
},
|
|
609
609
|
image: {
|
|
610
|
-
title: "\
|
|
610
|
+
title: "\u53C2\u8003\u56FE\u7247",
|
|
611
611
|
description: "\u7528\u4E8E\u56FE\u7247\u7F16\u8F91\uFF0C\u6700\u591A 16 \u5F20\uFF0C\u6BCF\u5F20\u5C0F\u4E8E 50 MB\u3002\u63D0\u4F9B\u8499\u7248\u65F6\uFF0C\u8499\u7248\u5E94\u7528\u4E8E\u7B2C\u4E00\u5F20\u8F93\u5165\u56FE\uFF0C\u5E76\u4E14\u5FC5\u987B\u4E0E\u8BE5\u56FE\u683C\u5F0F\u548C\u5C3A\u5BF8\u4E00\u81F4\u3002Task \u4E2D\u586B\u5199\u56FE\u7247 URL \u6216 Data URL\uFF1B\u6267\u884C\u65F6\u6309\u539F\u751F image[] \u5B57\u6BB5\u4E0A\u4F20\u6587\u4EF6\uFF0C\u987A\u5E8F\u4E0D\u53D8\u3002",
|
|
612
612
|
anyOf: [
|
|
613
613
|
{
|
|
@@ -2123,6 +2123,8 @@ var image_generated_default = [
|
|
|
2123
2123
|
properties: {
|
|
2124
2124
|
prompt_extend: {
|
|
2125
2125
|
type: "boolean",
|
|
2126
|
+
title: "\u63D0\u793A\u8BCD\u6269\u5199",
|
|
2127
|
+
description: "\u8BA9\u4E0A\u6E38\u4F18\u5316\u7F16\u8F91\u63D0\u793A\u8BCD\u3002",
|
|
2126
2128
|
"x-ui": {
|
|
2127
2129
|
order: 2,
|
|
2128
2130
|
control: "switch"
|
|
@@ -3124,8 +3126,7 @@ var image_generated_default = [
|
|
|
3124
3126
|
"8:1",
|
|
3125
3127
|
"9:16",
|
|
3126
3128
|
"16:9",
|
|
3127
|
-
"21:9"
|
|
3128
|
-
"9:21"
|
|
3129
|
+
"21:9"
|
|
3129
3130
|
],
|
|
3130
3131
|
"x-ui": {
|
|
3131
3132
|
order: 2,
|
|
@@ -3144,8 +3145,7 @@ var image_generated_default = [
|
|
|
3144
3145
|
"8:1": "8:1",
|
|
3145
3146
|
"9:16": "9:16",
|
|
3146
3147
|
"16:9": "16:9",
|
|
3147
|
-
"21:9": "21:9"
|
|
3148
|
-
"9:21": "9:21"
|
|
3148
|
+
"21:9": "21:9"
|
|
3149
3149
|
}
|
|
3150
3150
|
},
|
|
3151
3151
|
default: "1:1",
|
|
@@ -3366,8 +3366,7 @@ var image_generated_default = [
|
|
|
3366
3366
|
"8:1",
|
|
3367
3367
|
"9:16",
|
|
3368
3368
|
"16:9",
|
|
3369
|
-
"21:9"
|
|
3370
|
-
"9:21"
|
|
3369
|
+
"21:9"
|
|
3371
3370
|
],
|
|
3372
3371
|
"x-ui": {
|
|
3373
3372
|
order: 2,
|
|
@@ -3386,8 +3385,7 @@ var image_generated_default = [
|
|
|
3386
3385
|
"8:1": "8:1",
|
|
3387
3386
|
"9:16": "9:16",
|
|
3388
3387
|
"16:9": "16:9",
|
|
3389
|
-
"21:9": "21:9"
|
|
3390
|
-
"9:21": "9:21"
|
|
3388
|
+
"21:9": "21:9"
|
|
3391
3389
|
}
|
|
3392
3390
|
},
|
|
3393
3391
|
default: "1:1",
|
|
@@ -3778,7 +3776,7 @@ var image_generated_default = [
|
|
|
3778
3776
|
}
|
|
3779
3777
|
},
|
|
3780
3778
|
image: {
|
|
3781
|
-
title: "\
|
|
3779
|
+
title: "\u53C2\u8003\u56FE\u7247",
|
|
3782
3780
|
description: "\u7528\u4E8E\u56FE\u7247\u7F16\u8F91\uFF0C\u6700\u591A 16 \u5F20\uFF0C\u6BCF\u5F20\u5C0F\u4E8E 50 MB\u3002\u63D0\u4F9B\u8499\u7248\u65F6\uFF0C\u8499\u7248\u5E94\u7528\u4E8E\u7B2C\u4E00\u5F20\u8F93\u5165\u56FE\uFF0C\u5E76\u4E14\u5FC5\u987B\u4E0E\u8BE5\u56FE\u683C\u5F0F\u548C\u5C3A\u5BF8\u4E00\u81F4\u3002Task \u4E2D\u586B\u5199\u56FE\u7247 URL \u6216 Data URL\uFF1B\u6267\u884C\u65F6\u6309\u539F\u751F image[] \u5B57\u6BB5\u4E0A\u4F20\u6587\u4EF6\uFF0C\u987A\u5E8F\u4E0D\u53D8\u3002",
|
|
3783
3781
|
anyOf: [
|
|
3784
3782
|
{
|
|
@@ -3865,16 +3863,14 @@ var image_generated_default = [
|
|
|
3865
3863
|
description: "\u8F93\u51FA\u56FE\u7247\u7684\u7F16\u7801\u683C\u5F0F\u3002",
|
|
3866
3864
|
enum: [
|
|
3867
3865
|
"png",
|
|
3868
|
-
"jpeg"
|
|
3869
|
-
"webp"
|
|
3866
|
+
"jpeg"
|
|
3870
3867
|
],
|
|
3871
3868
|
title: "\u56FE\u7247\u683C\u5F0F",
|
|
3872
3869
|
"x-ui": {
|
|
3873
3870
|
order: 7,
|
|
3874
3871
|
optionLabels: {
|
|
3875
3872
|
png: "PNG",
|
|
3876
|
-
jpeg: "JPEG"
|
|
3877
|
-
webp: "WebP"
|
|
3873
|
+
jpeg: "JPEG"
|
|
3878
3874
|
},
|
|
3879
3875
|
control: "segmented"
|
|
3880
3876
|
}
|
|
@@ -3884,7 +3880,7 @@ var image_generated_default = [
|
|
|
3884
3880
|
minimum: 0,
|
|
3885
3881
|
maximum: 100,
|
|
3886
3882
|
multipleOf: 1,
|
|
3887
|
-
description: "JPEG \
|
|
3883
|
+
description: "JPEG \u538B\u7F29\u8D28\u91CF\uFF0C0\uFF5E100\uFF1B\u5F53\u524D Azure \u90E8\u7F72\u63A5\u53E3\u4EC5\u5728 output_format \u4E3A jpeg \u65F6\u652F\u6301\u3002",
|
|
3888
3884
|
"x-ui": {
|
|
3889
3885
|
order: 8,
|
|
3890
3886
|
control: "range",
|
|
@@ -3899,7 +3895,7 @@ var image_generated_default = [
|
|
|
3899
3895
|
"opaque",
|
|
3900
3896
|
"transparent"
|
|
3901
3897
|
],
|
|
3902
|
-
description: "\u53EF\u9009\u62E9\u81EA\u52A8\u3001\u4E0D\u900F\u660E\u6216\u900F\u660E\u80CC\u666F\uFF1B\
|
|
3898
|
+
description: "\u53EF\u9009\u62E9\u81EA\u52A8\u3001\u4E0D\u900F\u660E\u6216\u900F\u660E\u80CC\u666F\uFF1B\u5F53\u524D Azure \u90E8\u7F72\u63A5\u53E3\u7684\u900F\u660E\u80CC\u666F\u9700\u4F7F\u7528 PNG\u3002",
|
|
3903
3899
|
"x-ui": {
|
|
3904
3900
|
order: 9,
|
|
3905
3901
|
optionLabels: {
|
|
@@ -3980,8 +3976,7 @@ var image_generated_default = [
|
|
|
3980
3976
|
properties: {
|
|
3981
3977
|
output_format: {
|
|
3982
3978
|
enum: [
|
|
3983
|
-
"jpeg"
|
|
3984
|
-
"webp"
|
|
3979
|
+
"jpeg"
|
|
3985
3980
|
]
|
|
3986
3981
|
}
|
|
3987
3982
|
}
|
|
@@ -4002,8 +3997,7 @@ var image_generated_default = [
|
|
|
4002
3997
|
properties: {
|
|
4003
3998
|
output_format: {
|
|
4004
3999
|
enum: [
|
|
4005
|
-
"png"
|
|
4006
|
-
"webp"
|
|
4000
|
+
"png"
|
|
4007
4001
|
]
|
|
4008
4002
|
}
|
|
4009
4003
|
}
|
|
@@ -5147,7 +5141,7 @@ var image_generated_default = [
|
|
|
5147
5141
|
contractVersion: 2,
|
|
5148
5142
|
developer: "runninghub",
|
|
5149
5143
|
displayName: "RunningHub Midjourney V8.2 Preview",
|
|
5150
|
-
summary: "RunningHub \u60A0\u8239 V8.2 \u9884\u89C8\u7248\u56FE\u7247\u751F\u6210\uFF0C\
|
|
5144
|
+
summary: "RunningHub \u60A0\u8239 V8.2 \u9884\u89C8\u7248\u56FE\u7247\u751F\u6210\uFF0C\u5F3A\u5316\u5BA1\u7F8E\u3001\u6750\u8D28\u5149\u7167\u3001\u89D2\u8272\u4E00\u81F4\u6027\u3001\u5C40\u90E8\u91CD\u7ED8\u6548\u679C\u548C\u968F\u673A\u98CE\u683C\u8349\u7A3F\u8868\u73B0\uFF0C\u652F\u6301\u5355\u56FE/\u98CE\u683C\u53C2\u8003\u4E0E\u539F\u751F 2K \u8F93\u51FA\uFF1B\u5F53\u524D\u63A5\u53E3\u672A\u63D0\u4F9B\u8499\u7248\u7F16\u8F91\uFF0C\u4E14\u9884\u89C8\u7248\u53C2\u6570\u903B\u8F91\u548C\u8F93\u51FA\u7A33\u5B9A\u6027\u53EF\u80FD\u53D8\u5316\u3002",
|
|
5151
5145
|
kind: "image",
|
|
5152
5146
|
family: "Midjourney",
|
|
5153
5147
|
versionLabel: "8.2 Preview",
|
|
@@ -5845,9 +5839,7 @@ var image_generated_default = [
|
|
|
5845
5839
|
"19.5:9",
|
|
5846
5840
|
"9:19.5",
|
|
5847
5841
|
"20:9",
|
|
5848
|
-
"9:20"
|
|
5849
|
-
"21:9",
|
|
5850
|
-
"5:2"
|
|
5842
|
+
"9:20"
|
|
5851
5843
|
],
|
|
5852
5844
|
"x-ui": {
|
|
5853
5845
|
order: 4,
|
|
@@ -5936,6 +5928,66 @@ var image_generated_default = [
|
|
|
5936
5928
|
order: 99,
|
|
5937
5929
|
hidden: true
|
|
5938
5930
|
}
|
|
5931
|
+
},
|
|
5932
|
+
storage_options: {
|
|
5933
|
+
type: [
|
|
5934
|
+
"object",
|
|
5935
|
+
"null"
|
|
5936
|
+
],
|
|
5937
|
+
title: "\u4E0A\u6E38\u6587\u4EF6\u4FDD\u5B58\u9009\u9879",
|
|
5938
|
+
description: "\u5C06\u751F\u6210\u6216\u7F16\u8F91\u7ED3\u679C\u4FDD\u5B58\u5230 xAI Files API\uFF1Bfilename \u5FC5\u586B\u3002",
|
|
5939
|
+
required: [
|
|
5940
|
+
"filename"
|
|
5941
|
+
],
|
|
5942
|
+
properties: {
|
|
5943
|
+
filename: {
|
|
5944
|
+
type: "string",
|
|
5945
|
+
minLength: 1,
|
|
5946
|
+
title: "\u6587\u4EF6\u540D"
|
|
5947
|
+
},
|
|
5948
|
+
expires_after: {
|
|
5949
|
+
type: [
|
|
5950
|
+
"integer",
|
|
5951
|
+
"null"
|
|
5952
|
+
],
|
|
5953
|
+
minimum: 3600,
|
|
5954
|
+
maximum: 2592e3,
|
|
5955
|
+
title: "\u6587\u4EF6\u6709\u6548\u671F",
|
|
5956
|
+
description: "\u6587\u4EF6\u81EA\u52A8\u8FC7\u671F\u79D2\u6570\uFF0C\u8303\u56F4\u4E3A 3600 \u5230 2592000\uFF1B\u7559\u7A7A\u8868\u793A\u6C38\u4E45\u4FDD\u5B58\u3002"
|
|
5957
|
+
},
|
|
5958
|
+
public_url: {
|
|
5959
|
+
title: "\u516C\u5F00\u5730\u5740\u9009\u9879",
|
|
5960
|
+
description: "true \u4F7F\u7528\u9ED8\u8BA4\u8BBE\u7F6E\u521B\u5EFA\u516C\u5F00\u5730\u5740\uFF0Cfalse \u6216\u7559\u7A7A\u8868\u793A\u4E0D\u521B\u5EFA\uFF1B\u4E5F\u53EF\u5355\u72EC\u8BBE\u7F6E\u516C\u5F00\u5730\u5740\u6709\u6548\u671F\u3002",
|
|
5961
|
+
oneOf: [
|
|
5962
|
+
{
|
|
5963
|
+
type: "boolean"
|
|
5964
|
+
},
|
|
5965
|
+
{
|
|
5966
|
+
type: "object",
|
|
5967
|
+
properties: {
|
|
5968
|
+
expires_after: {
|
|
5969
|
+
type: [
|
|
5970
|
+
"integer",
|
|
5971
|
+
"null"
|
|
5972
|
+
],
|
|
5973
|
+
minimum: 3600,
|
|
5974
|
+
maximum: 2592e3,
|
|
5975
|
+
title: "\u516C\u5F00\u5730\u5740\u6709\u6548\u671F",
|
|
5976
|
+
description: "\u516C\u5F00\u5730\u5740\u81EA\u52A8\u8FC7\u671F\u79D2\u6570\uFF0C\u8303\u56F4\u4E3A 3600 \u5230 2592000\u3002"
|
|
5977
|
+
}
|
|
5978
|
+
},
|
|
5979
|
+
additionalProperties: true
|
|
5980
|
+
},
|
|
5981
|
+
{
|
|
5982
|
+
type: "null"
|
|
5983
|
+
}
|
|
5984
|
+
]
|
|
5985
|
+
}
|
|
5986
|
+
},
|
|
5987
|
+
additionalProperties: true,
|
|
5988
|
+
"x-ui": {
|
|
5989
|
+
order: 9
|
|
5990
|
+
}
|
|
5939
5991
|
}
|
|
5940
5992
|
},
|
|
5941
5993
|
required: [
|
|
@@ -6111,6 +6163,33 @@ var image_generated_default = [
|
|
|
6111
6163
|
],
|
|
6112
6164
|
title: "\u8F93\u5165 Token"
|
|
6113
6165
|
},
|
|
6166
|
+
input_tokens_details: {
|
|
6167
|
+
type: [
|
|
6168
|
+
"object",
|
|
6169
|
+
"null"
|
|
6170
|
+
],
|
|
6171
|
+
title: "\u8F93\u5165 Token \u660E\u7EC6",
|
|
6172
|
+
required: [
|
|
6173
|
+
"cached_tokens",
|
|
6174
|
+
"image_tokens",
|
|
6175
|
+
"text_tokens"
|
|
6176
|
+
],
|
|
6177
|
+
properties: {
|
|
6178
|
+
cached_tokens: {
|
|
6179
|
+
type: "integer",
|
|
6180
|
+
title: "\u7F13\u5B58\u6587\u672C Token"
|
|
6181
|
+
},
|
|
6182
|
+
image_tokens: {
|
|
6183
|
+
type: "integer",
|
|
6184
|
+
title: "\u8F93\u5165\u56FE\u7247 Token"
|
|
6185
|
+
},
|
|
6186
|
+
text_tokens: {
|
|
6187
|
+
type: "integer",
|
|
6188
|
+
title: "\u8F93\u5165\u6587\u672C Token"
|
|
6189
|
+
}
|
|
6190
|
+
},
|
|
6191
|
+
additionalProperties: true
|
|
6192
|
+
},
|
|
6114
6193
|
output_tokens: {
|
|
6115
6194
|
type: [
|
|
6116
6195
|
"integer",
|
|
@@ -6118,6 +6197,33 @@ var image_generated_default = [
|
|
|
6118
6197
|
],
|
|
6119
6198
|
title: "\u8F93\u51FA Token"
|
|
6120
6199
|
},
|
|
6200
|
+
output_tokens_details: {
|
|
6201
|
+
type: [
|
|
6202
|
+
"object",
|
|
6203
|
+
"null"
|
|
6204
|
+
],
|
|
6205
|
+
title: "\u8F93\u51FA Token \u660E\u7EC6",
|
|
6206
|
+
required: [
|
|
6207
|
+
"image_tokens",
|
|
6208
|
+
"reasoning_tokens",
|
|
6209
|
+
"text_tokens"
|
|
6210
|
+
],
|
|
6211
|
+
properties: {
|
|
6212
|
+
image_tokens: {
|
|
6213
|
+
type: "integer",
|
|
6214
|
+
title: "\u8F93\u51FA\u56FE\u7247 Token"
|
|
6215
|
+
},
|
|
6216
|
+
reasoning_tokens: {
|
|
6217
|
+
type: "integer",
|
|
6218
|
+
title: "\u63A8\u7406 Token"
|
|
6219
|
+
},
|
|
6220
|
+
text_tokens: {
|
|
6221
|
+
type: "integer",
|
|
6222
|
+
title: "\u8F93\u51FA\u6587\u672C Token"
|
|
6223
|
+
}
|
|
6224
|
+
},
|
|
6225
|
+
additionalProperties: true
|
|
6226
|
+
},
|
|
6121
6227
|
total_tokens: {
|
|
6122
6228
|
type: [
|
|
6123
6229
|
"integer",
|
|
@@ -6165,6 +6271,1206 @@ var generatedCatalog = Object.freeze([
|
|
|
6165
6271
|
...image_generated_default
|
|
6166
6272
|
]);
|
|
6167
6273
|
|
|
6274
|
+
// ../contracts/src/assets.ts
|
|
6275
|
+
var MEDIA_KINDS = [
|
|
6276
|
+
"image",
|
|
6277
|
+
"video",
|
|
6278
|
+
"audio",
|
|
6279
|
+
"document",
|
|
6280
|
+
"archive",
|
|
6281
|
+
"other"
|
|
6282
|
+
];
|
|
6283
|
+
|
|
6284
|
+
// ../contracts/src/uploaded-media.ts
|
|
6285
|
+
function modelUploadRegion(regions) {
|
|
6286
|
+
return regions.length > 0 && regions.every((region) => /^cn(?:-|$)/.test(region.trim().toLowerCase())) ? "cn" : "global";
|
|
6287
|
+
}
|
|
6288
|
+
function uploadedMediaUrl(value, region) {
|
|
6289
|
+
if (!value.startsWith("https://")) return value;
|
|
6290
|
+
try {
|
|
6291
|
+
const url = new URL(value);
|
|
6292
|
+
if (url.username || url.password || url.port || !["tos.nexra-ai.com", "tos2.nexra-ai.com", "upload.nexra-ai.com"].includes(url.hostname) || !url.pathname.startsWith("/user-assets/") || url.pathname === "/user-assets/") return value;
|
|
6293
|
+
url.hostname = region === "cn" ? "tos.nexra-ai.com" : "tos2.nexra-ai.com";
|
|
6294
|
+
return url.href;
|
|
6295
|
+
} catch {
|
|
6296
|
+
return value;
|
|
6297
|
+
}
|
|
6298
|
+
}
|
|
6299
|
+
function uploadedMediaInput(input, region) {
|
|
6300
|
+
const visit = (value) => {
|
|
6301
|
+
if (typeof value === "string") return uploadedMediaUrl(value, region);
|
|
6302
|
+
if (Array.isArray(value)) return value.map(visit);
|
|
6303
|
+
if (value !== null && typeof value === "object") {
|
|
6304
|
+
return Object.fromEntries(Object.entries(value).map(([key, item]) => [
|
|
6305
|
+
key,
|
|
6306
|
+
["text", "texts", "prompt", "negative_prompt", "negativePrompt"].includes(key) ? item : visit(item)
|
|
6307
|
+
]));
|
|
6308
|
+
}
|
|
6309
|
+
return value;
|
|
6310
|
+
};
|
|
6311
|
+
return visit(input);
|
|
6312
|
+
}
|
|
6313
|
+
|
|
6314
|
+
// ../contracts/src/admin-usage.ts
|
|
6315
|
+
var USAGE_SOURCES = ["provider", "estimated", "reconciled"];
|
|
6316
|
+
var USAGE_NORMALIZATION_STATUSES = [
|
|
6317
|
+
"normalized",
|
|
6318
|
+
"partial",
|
|
6319
|
+
"invalid",
|
|
6320
|
+
"missing"
|
|
6321
|
+
];
|
|
6322
|
+
var USAGE_RATING_STATUSES = [
|
|
6323
|
+
"billed",
|
|
6324
|
+
"unsettled",
|
|
6325
|
+
"billing_failed",
|
|
6326
|
+
"unpriced",
|
|
6327
|
+
"usage_missing"
|
|
6328
|
+
];
|
|
6329
|
+
var USAGE_GROUP_BYS = [
|
|
6330
|
+
"minute",
|
|
6331
|
+
"hour",
|
|
6332
|
+
"day",
|
|
6333
|
+
"month",
|
|
6334
|
+
"user",
|
|
6335
|
+
"apiKey",
|
|
6336
|
+
"provider",
|
|
6337
|
+
"channel",
|
|
6338
|
+
"model",
|
|
6339
|
+
"operation"
|
|
6340
|
+
];
|
|
6341
|
+
var USAGE_AMOUNT_KINDS = ["sale", "cost", "gross"];
|
|
6342
|
+
var TOKEN_METRICS = [
|
|
6343
|
+
"input_tokens",
|
|
6344
|
+
"cached_input_tokens",
|
|
6345
|
+
"cache_write_tokens",
|
|
6346
|
+
"cache_creation_5m_input_tokens",
|
|
6347
|
+
"cache_creation_1h_input_tokens",
|
|
6348
|
+
"cache_read_input_tokens",
|
|
6349
|
+
"output_tokens"
|
|
6350
|
+
];
|
|
6351
|
+
var MONEY_STRING_PATTERN = /^-?(?:0|[1-9]\d*)(?:\.\d{1,8})?$/;
|
|
6352
|
+
var USAGE_FILTER_SELECTION_LIMIT = 200;
|
|
6353
|
+
function validateUsageFilters(value) {
|
|
6354
|
+
if (!isObject(value)) throw new Error("Usage filters must be an object");
|
|
6355
|
+
const filters = value;
|
|
6356
|
+
const start = Date.parse(String(filters.start));
|
|
6357
|
+
const end = Date.parse(String(filters.end));
|
|
6358
|
+
if (!Number.isFinite(start)) throw new Error("filters.start must be an ISO-8601 instant");
|
|
6359
|
+
if (!Number.isFinite(end)) throw new Error("filters.end must be an ISO-8601 instant");
|
|
6360
|
+
if (start >= end) throw new Error("filters.end must be after filters.start ([start, end) window)");
|
|
6361
|
+
if (filters.timeZoneOffsetMinutes !== void 0 && (!Number.isSafeInteger(filters.timeZoneOffsetMinutes) || filters.timeZoneOffsetMinutes < -720 || filters.timeZoneOffsetMinutes > 840)) {
|
|
6362
|
+
throw new Error("filters.timeZoneOffsetMinutes must be an integer between -720 and 840");
|
|
6363
|
+
}
|
|
6364
|
+
for (const key of ["userIds", "apiKeyIds", "providerIds", "channelIds", "modelIds", "operations", "requestStatuses"]) {
|
|
6365
|
+
const list = filters[key];
|
|
6366
|
+
if (list !== void 0 && (!isStringArray(list) || list.length > USAGE_FILTER_SELECTION_LIMIT)) {
|
|
6367
|
+
throw new Error(`filters.${key} must be at most ${USAGE_FILTER_SELECTION_LIMIT} non-empty strings`);
|
|
6368
|
+
}
|
|
6369
|
+
}
|
|
6370
|
+
if (filters.upstreamModelId !== void 0 && (typeof filters.upstreamModelId !== "string" || filters.upstreamModelId === "")) {
|
|
6371
|
+
throw new Error("filters.upstreamModelId must be a non-empty string");
|
|
6372
|
+
}
|
|
6373
|
+
for (const key of ["usageSources", "normalizationStatuses", "ratingStatuses"]) {
|
|
6374
|
+
const list = filters[key];
|
|
6375
|
+
if (list === void 0) continue;
|
|
6376
|
+
if (!isStringArray(list)) throw new Error(`filters.${key} must be an array of non-empty strings`);
|
|
6377
|
+
const allowed = key === "usageSources" ? USAGE_SOURCES : key === "normalizationStatuses" ? USAGE_NORMALIZATION_STATUSES : USAGE_RATING_STATUSES;
|
|
6378
|
+
if (list.some((item) => !allowed.includes(item))) {
|
|
6379
|
+
throw new Error(`filters.${key} contains an unsupported status`);
|
|
6380
|
+
}
|
|
6381
|
+
}
|
|
6382
|
+
}
|
|
6383
|
+
function validateUsageSummaryQuery(value) {
|
|
6384
|
+
if (!isObject(value)) throw new Error("Usage summary query must be an object");
|
|
6385
|
+
validateUsageFilters(value.filters);
|
|
6386
|
+
if (!Array.isArray(value.groupBy) || value.groupBy.length === 0) {
|
|
6387
|
+
throw new Error("groupBy must be a non-empty array");
|
|
6388
|
+
}
|
|
6389
|
+
const timeGranularities = value.groupBy.filter(
|
|
6390
|
+
(key) => ["minute", "hour", "day", "month"].includes(String(key))
|
|
6391
|
+
);
|
|
6392
|
+
if (timeGranularities.length > 1) {
|
|
6393
|
+
throw new Error("groupBy accepts at most one time granularity");
|
|
6394
|
+
}
|
|
6395
|
+
const seen = /* @__PURE__ */ new Set();
|
|
6396
|
+
for (const key of value.groupBy) {
|
|
6397
|
+
if (!USAGE_GROUP_BYS.includes(String(key))) {
|
|
6398
|
+
throw new Error(`groupBy contains an unsupported key: ${String(key)}`);
|
|
6399
|
+
}
|
|
6400
|
+
if (seen.has(String(key))) throw new Error("groupBy contains duplicate keys");
|
|
6401
|
+
seen.add(String(key));
|
|
6402
|
+
}
|
|
6403
|
+
if (!Number.isSafeInteger(value.limit) || value.limit < 1 || value.limit > 500) {
|
|
6404
|
+
throw new Error("limit must be an integer between 1 and 500");
|
|
6405
|
+
}
|
|
6406
|
+
if (value.cursor !== void 0 && (typeof value.cursor !== "string" || value.cursor === "")) {
|
|
6407
|
+
throw new Error("cursor must be a non-empty string");
|
|
6408
|
+
}
|
|
6409
|
+
}
|
|
6410
|
+
var CURSOR_PREFIX = "v1.offset.";
|
|
6411
|
+
function encodeUsageSummaryCursor(offset) {
|
|
6412
|
+
return `${CURSOR_PREFIX}${offset}`;
|
|
6413
|
+
}
|
|
6414
|
+
function parseUsageSummaryCursor(value) {
|
|
6415
|
+
if (!value.startsWith(CURSOR_PREFIX)) return null;
|
|
6416
|
+
const offset = Number(value.slice(CURSOR_PREFIX.length));
|
|
6417
|
+
return Number.isSafeInteger(offset) && offset >= 0 ? offset : null;
|
|
6418
|
+
}
|
|
6419
|
+
var KEYSET_CURSOR_PREFIX = "v1.key.";
|
|
6420
|
+
function encodeUsageKeysetCursor(receivedAt, requestId) {
|
|
6421
|
+
return `${KEYSET_CURSOR_PREFIX}${encodeURIComponent(receivedAt)}|${encodeURIComponent(requestId)}`;
|
|
6422
|
+
}
|
|
6423
|
+
function parseUsageKeysetCursor(value) {
|
|
6424
|
+
if (!value.startsWith(KEYSET_CURSOR_PREFIX)) return null;
|
|
6425
|
+
const parts = value.slice(KEYSET_CURSOR_PREFIX.length).split("|");
|
|
6426
|
+
if (parts.length !== 2 || !parts[0] || !parts[1]) return null;
|
|
6427
|
+
let receivedAt;
|
|
6428
|
+
let requestId;
|
|
6429
|
+
try {
|
|
6430
|
+
receivedAt = decodeURIComponent(parts[0]);
|
|
6431
|
+
requestId = decodeURIComponent(parts[1]);
|
|
6432
|
+
} catch {
|
|
6433
|
+
return null;
|
|
6434
|
+
}
|
|
6435
|
+
if (!/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(requestId)) {
|
|
6436
|
+
return null;
|
|
6437
|
+
}
|
|
6438
|
+
if (!/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d{1,6})?Z$/.test(receivedAt) || !Number.isFinite(Date.parse(receivedAt))) return null;
|
|
6439
|
+
if (new Date(receivedAt).toISOString().slice(0, 19) !== receivedAt.slice(0, 19)) return null;
|
|
6440
|
+
return { receivedAt, requestId };
|
|
6441
|
+
}
|
|
6442
|
+
function validateUsageDetailsQuery(value) {
|
|
6443
|
+
if (!isObject(value)) throw new Error("Usage details query must be an object");
|
|
6444
|
+
validateUsageFilters(value.filters);
|
|
6445
|
+
if (!Number.isSafeInteger(value.limit) || value.limit < 1 || value.limit > 200) {
|
|
6446
|
+
throw new Error("limit must be an integer between 1 and 200");
|
|
6447
|
+
}
|
|
6448
|
+
if (value.cursor !== void 0 && (typeof value.cursor !== "string" || value.cursor === "")) {
|
|
6449
|
+
throw new Error("cursor must be a non-empty string");
|
|
6450
|
+
}
|
|
6451
|
+
}
|
|
6452
|
+
var USAGE_ANOMALY_CATEGORIES = [
|
|
6453
|
+
"usage_missing",
|
|
6454
|
+
"normalization_failed",
|
|
6455
|
+
"unpriced",
|
|
6456
|
+
"dimension_mismatch",
|
|
6457
|
+
"settlement_failed"
|
|
6458
|
+
];
|
|
6459
|
+
function validateUsageAnomaliesQuery(value) {
|
|
6460
|
+
if (!isObject(value)) throw new Error("Usage anomalies query must be an object");
|
|
6461
|
+
validateUsageFilters(value.filters);
|
|
6462
|
+
if (value.categories !== void 0) {
|
|
6463
|
+
if (!isStringArray(value.categories) || value.categories.some((item) => !USAGE_ANOMALY_CATEGORIES.includes(item))) {
|
|
6464
|
+
throw new Error("categories contains an unsupported anomaly category");
|
|
6465
|
+
}
|
|
6466
|
+
}
|
|
6467
|
+
if (!Number.isSafeInteger(value.limit) || value.limit < 1 || value.limit > 200) {
|
|
6468
|
+
throw new Error("limit must be an integer between 1 and 200");
|
|
6469
|
+
}
|
|
6470
|
+
if (value.cursor !== void 0 && (typeof value.cursor !== "string" || value.cursor === "")) {
|
|
6471
|
+
throw new Error("cursor must be a non-empty string");
|
|
6472
|
+
}
|
|
6473
|
+
}
|
|
6474
|
+
function validateUsageAnomalySummaryQuery(value) {
|
|
6475
|
+
if (!isObject(value)) throw new Error("Usage anomaly summary query must be an object");
|
|
6476
|
+
validateUsageFilters(value.filters);
|
|
6477
|
+
if (value.breakdowns !== void 0) {
|
|
6478
|
+
if (!Array.isArray(value.breakdowns) || value.breakdowns.length > 2 || value.breakdowns.some((item) => !["provider", "channel", "model"].includes(String(item)))) {
|
|
6479
|
+
throw new Error("breakdowns accepts at most two of provider, channel, model");
|
|
6480
|
+
}
|
|
6481
|
+
}
|
|
6482
|
+
}
|
|
6483
|
+
function isObject(value) {
|
|
6484
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
6485
|
+
}
|
|
6486
|
+
function isStringArray(value) {
|
|
6487
|
+
return Array.isArray(value) && value.length > 0 && value.every((item) => typeof item === "string" && item !== "");
|
|
6488
|
+
}
|
|
6489
|
+
|
|
6490
|
+
// ../contracts/src/admin-users.ts
|
|
6491
|
+
var ADMIN_USER_ROLES = ["admin", "dealer", "user"];
|
|
6492
|
+
var ADMIN_USER_STATUSES = ["active", "banned"];
|
|
6493
|
+
function validateAdminUserListQuery(value) {
|
|
6494
|
+
if (!isObject2(value)) throw new Error("User list query must be an object");
|
|
6495
|
+
if (value.query !== void 0 && (typeof value.query !== "string" || value.query.trim() === "" || value.query.length > 320)) {
|
|
6496
|
+
throw new Error("query must be a non-empty string of at most 320 characters");
|
|
6497
|
+
}
|
|
6498
|
+
if (value.role !== void 0 && !ADMIN_USER_ROLES.includes(String(value.role))) {
|
|
6499
|
+
throw new Error("role is not supported");
|
|
6500
|
+
}
|
|
6501
|
+
if (value.status !== void 0 && !ADMIN_USER_STATUSES.includes(String(value.status))) {
|
|
6502
|
+
throw new Error("status is not supported");
|
|
6503
|
+
}
|
|
6504
|
+
if (!Number.isSafeInteger(value.limit) || value.limit < 1 || value.limit > 200) {
|
|
6505
|
+
throw new Error("limit must be an integer between 1 and 200");
|
|
6506
|
+
}
|
|
6507
|
+
if (value.cursor !== void 0 && (typeof value.cursor !== "string" || value.cursor === "")) {
|
|
6508
|
+
throw new Error("cursor must be a non-empty string");
|
|
6509
|
+
}
|
|
6510
|
+
}
|
|
6511
|
+
var USER_CURSOR_PREFIX = "v1.user.";
|
|
6512
|
+
function encodeAdminUserCursor(cursor) {
|
|
6513
|
+
return `${USER_CURSOR_PREFIX}${encodeURIComponent(cursor.createdAt)}|${encodeURIComponent(cursor.userId)}`;
|
|
6514
|
+
}
|
|
6515
|
+
function parseAdminUserCursor(value) {
|
|
6516
|
+
try {
|
|
6517
|
+
if (!value.startsWith(USER_CURSOR_PREFIX)) return null;
|
|
6518
|
+
const parts = value.slice(USER_CURSOR_PREFIX.length).split("|");
|
|
6519
|
+
if (parts.length !== 2) return null;
|
|
6520
|
+
const [encodedCreatedAt, encodedUserId] = parts;
|
|
6521
|
+
if (!encodedCreatedAt || !encodedUserId) return null;
|
|
6522
|
+
const createdAt = decodeURIComponent(encodedCreatedAt);
|
|
6523
|
+
const userId = decodeURIComponent(encodedUserId);
|
|
6524
|
+
return Number.isFinite(Date.parse(createdAt)) && userId !== "" ? { createdAt, userId } : null;
|
|
6525
|
+
} catch {
|
|
6526
|
+
return null;
|
|
6527
|
+
}
|
|
6528
|
+
}
|
|
6529
|
+
var ADMIN_USER_ACTIVITY_KINDS = ["ledger", "recharge", "hold", "audit"];
|
|
6530
|
+
function isMoneyString(value) {
|
|
6531
|
+
return MONEY_STRING_PATTERN.test(value);
|
|
6532
|
+
}
|
|
6533
|
+
function validateAdminUserUpdate(value) {
|
|
6534
|
+
if (!isObject2(value)) throw new Error("User update must be an object");
|
|
6535
|
+
if (typeof value.reason !== "string" || value.reason.trim() === "" || value.reason.length > 500) {
|
|
6536
|
+
throw new Error("reason is required (at most 500 characters)");
|
|
6537
|
+
}
|
|
6538
|
+
if (value.role !== void 0 && !ADMIN_USER_ROLES.includes(String(value.role))) {
|
|
6539
|
+
throw new Error("role is not supported");
|
|
6540
|
+
}
|
|
6541
|
+
if (value.status !== void 0 && !ADMIN_USER_STATUSES.includes(String(value.status))) {
|
|
6542
|
+
throw new Error("status is not supported");
|
|
6543
|
+
}
|
|
6544
|
+
if (value.qpsLimit !== void 0 && (!Number.isSafeInteger(value.qpsLimit) || value.qpsLimit < 1 || value.qpsLimit > 1e5)) {
|
|
6545
|
+
throw new Error("qpsLimit must be an integer between 1 and 100000");
|
|
6546
|
+
}
|
|
6547
|
+
if (value.role === void 0 && value.status === void 0 && value.qpsLimit === void 0) {
|
|
6548
|
+
throw new Error("At least one of role, status, or qpsLimit is required");
|
|
6549
|
+
}
|
|
6550
|
+
}
|
|
6551
|
+
function validateAdminUserApiKeyUpdate(value) {
|
|
6552
|
+
if (!isObject2(value)) throw new Error("API key update must be an object");
|
|
6553
|
+
if (typeof value.reason !== "string" || value.reason.trim() === "" || value.reason.length > 500) {
|
|
6554
|
+
throw new Error("reason is required (at most 500 characters)");
|
|
6555
|
+
}
|
|
6556
|
+
if (value.revoked !== void 0 && typeof value.revoked !== "boolean") {
|
|
6557
|
+
throw new Error("revoked must be a boolean");
|
|
6558
|
+
}
|
|
6559
|
+
if (value.rateLimitPerSecond !== void 0 && value.rateLimitPerSecond !== null && (!Number.isSafeInteger(value.rateLimitPerSecond) || value.rateLimitPerSecond < 1 || value.rateLimitPerSecond > 1e5)) {
|
|
6560
|
+
throw new Error("rateLimitPerSecond must be an integer between 1 and 100000, or null");
|
|
6561
|
+
}
|
|
6562
|
+
if (value.revoked === void 0 && value.rateLimitPerSecond === void 0) {
|
|
6563
|
+
throw new Error("At least one of revoked or rateLimitPerSecond is required");
|
|
6564
|
+
}
|
|
6565
|
+
}
|
|
6566
|
+
function validateAdminWalletRechargeInput(value) {
|
|
6567
|
+
if (!isObject2(value)) throw new Error("Wallet recharge must be an object");
|
|
6568
|
+
if (typeof value.userId !== "string" || value.userId === "") {
|
|
6569
|
+
throw new Error("userId is required");
|
|
6570
|
+
}
|
|
6571
|
+
if (value.currency !== "CNY") {
|
|
6572
|
+
throw new Error("currency must be CNY");
|
|
6573
|
+
}
|
|
6574
|
+
if (typeof value.amount !== "string" || !isMoneyString(value.amount) || value.amount.startsWith("-") || Number(value.amount) <= 0) {
|
|
6575
|
+
throw new Error("amount must be a positive decimal string");
|
|
6576
|
+
}
|
|
6577
|
+
if ((value.amount.split(".")[0]?.length ?? 0) > 12) {
|
|
6578
|
+
throw new Error("amount exceeds the 12-digit integer limit of the wallet balance");
|
|
6579
|
+
}
|
|
6580
|
+
if (typeof value.externalOrderId !== "string" || value.externalOrderId.trim() === "" || value.externalOrderId.trim().length > 240) {
|
|
6581
|
+
throw new Error("externalOrderId is required (at most 240 characters)");
|
|
6582
|
+
}
|
|
6583
|
+
if (typeof value.reason !== "string" || value.reason.trim() === "" || value.reason.length > 500) {
|
|
6584
|
+
throw new Error("reason is required (at most 500 characters)");
|
|
6585
|
+
}
|
|
6586
|
+
}
|
|
6587
|
+
function isObject2(value) {
|
|
6588
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
6589
|
+
}
|
|
6590
|
+
|
|
6591
|
+
// ../contracts/src/usage-filter-options.ts
|
|
6592
|
+
var USAGE_FILTER_KINDS = ["model", "user", "apiKey", "provider", "channel", "operation"];
|
|
6593
|
+
var MODEL_ID = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
6594
|
+
function validId(kind, id) {
|
|
6595
|
+
return typeof id === "string" && id.length > 0 && id.length <= 128 && !/[\s,|]/u.test(id) && (kind === "user" || kind === "operation" || MODEL_ID.test(id));
|
|
6596
|
+
}
|
|
6597
|
+
function encodeUsageFilterCursor(kind, query, id) {
|
|
6598
|
+
return `usage-filter-v1|${kind}|${encodeURIComponent(query)}|${encodeURIComponent(id)}`;
|
|
6599
|
+
}
|
|
6600
|
+
function parseUsageFilterCursor(value, kind, query) {
|
|
6601
|
+
try {
|
|
6602
|
+
const parts = value.split("|");
|
|
6603
|
+
if (parts.length !== 4 || parts[0] !== "usage-filter-v1" || parts[1] !== kind || decodeURIComponent(parts[2]) !== query) return null;
|
|
6604
|
+
const id = decodeURIComponent(parts[3]);
|
|
6605
|
+
return validId(kind, id) ? id : null;
|
|
6606
|
+
} catch {
|
|
6607
|
+
return null;
|
|
6608
|
+
}
|
|
6609
|
+
}
|
|
6610
|
+
function validateUsageFilterOptionsQuery(kind, value) {
|
|
6611
|
+
if (!value || typeof value !== "object") throw new Error("\u7B5B\u9009\u67E5\u8BE2\u683C\u5F0F\u4E0D\u6B63\u786E");
|
|
6612
|
+
const query = value;
|
|
6613
|
+
if (!Number.isInteger(query.limit) || query.limit < 1 || query.limit > 100) throw new Error("\u4E00\u6B21\u6700\u591A\u67E5\u8BE2 100 \u9879");
|
|
6614
|
+
if (query.query !== void 0 && (typeof query.query !== "string" || !query.query.trim() || query.query.length > 320)) throw new Error("\u641C\u7D22\u5185\u5BB9\u5FC5\u987B\u4E3A 1 \u81F3 320 \u4E2A\u5B57\u7B26");
|
|
6615
|
+
if (query.ids !== void 0) {
|
|
6616
|
+
if (!Array.isArray(query.ids) || !query.ids.length || query.ids.length > query.limit || query.ids.some((id) => !validId(kind, id))) throw new Error("\u8BF7\u8F93\u5165\u6709\u6548\u7684\u5185\u90E8 ID\uFF0C\u4E00\u6B21\u6700\u591A 100 \u9879");
|
|
6617
|
+
if (query.query !== void 0 || query.cursor !== void 0) throw new Error("ID \u786E\u8BA4\u4E0D\u80FD\u540C\u65F6\u4F7F\u7528\u641C\u7D22\u6216\u5206\u9875");
|
|
6618
|
+
}
|
|
6619
|
+
if (query.cursor !== void 0 && (typeof query.cursor !== "string" || query.cursor.length > 4096 || !parseUsageFilterCursor(query.cursor, kind, query.query ?? ""))) throw new Error("\u5206\u9875\u6E38\u6807\u4E0E\u5F53\u524D\u7B5B\u9009\u4E0D\u5339\u914D");
|
|
6620
|
+
}
|
|
6621
|
+
|
|
6622
|
+
// ../contracts/src/money.ts
|
|
6623
|
+
var MONEY_SCALE = 100000000n;
|
|
6624
|
+
var BILLING_CURRENCY = "CNY";
|
|
6625
|
+
var WALLET_MAX_BALANCE_UNITS = 99999999999999999999n;
|
|
6626
|
+
function moneyToUnits(value) {
|
|
6627
|
+
if (!/^-?\d+(\.\d{1,8})?$/.test(value)) throw new Error("Invalid money amount");
|
|
6628
|
+
const negative = value.startsWith("-");
|
|
6629
|
+
const [whole = "0", fraction = ""] = (negative ? value.slice(1) : value).split(".");
|
|
6630
|
+
const units = BigInt(whole) * MONEY_SCALE + BigInt(fraction.padEnd(8, "0"));
|
|
6631
|
+
return negative ? -units : units;
|
|
6632
|
+
}
|
|
6633
|
+
function moneyFromUnits(value) {
|
|
6634
|
+
const negative = value < 0n;
|
|
6635
|
+
const absolute = negative ? -value : value;
|
|
6636
|
+
const fraction = (absolute % MONEY_SCALE).toString().padStart(8, "0").replace(/0+$/, "");
|
|
6637
|
+
return `${negative ? "-" : ""}${absolute / MONEY_SCALE}${fraction ? `.${fraction}` : ""}`;
|
|
6638
|
+
}
|
|
6639
|
+
function multiplyMoney(value, multiplier, ...additionalMultipliers) {
|
|
6640
|
+
let product = moneyToUnits(value);
|
|
6641
|
+
if (product < 0n) throw new Error("Money amount must be non-negative");
|
|
6642
|
+
let divisor = 1n;
|
|
6643
|
+
for (const multiplierValue of [multiplier, ...additionalMultipliers]) {
|
|
6644
|
+
const factor = moneyToUnits(multiplierValue);
|
|
6645
|
+
if (factor <= 0n) throw new Error("Money multiplier must be positive");
|
|
6646
|
+
product *= factor;
|
|
6647
|
+
divisor *= MONEY_SCALE;
|
|
6648
|
+
}
|
|
6649
|
+
return moneyFromUnits((product + divisor / 2n) / divisor);
|
|
6650
|
+
}
|
|
6651
|
+
|
|
6652
|
+
// ../contracts/src/model-schema.ts
|
|
6653
|
+
function object(value) {
|
|
6654
|
+
return value !== null && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
6655
|
+
}
|
|
6656
|
+
function normalizeModelParameterSchema(source) {
|
|
6657
|
+
const result = structuredClone(source);
|
|
6658
|
+
const input = object(result.input);
|
|
6659
|
+
const properties = object(input.properties);
|
|
6660
|
+
const ui = object(result.ui);
|
|
6661
|
+
const fields = object(ui.fields);
|
|
6662
|
+
const defaults = object(result.defaults);
|
|
6663
|
+
const order = Array.isArray(ui.order) ? ui.order : [];
|
|
6664
|
+
for (const [key, value] of Object.entries(properties)) {
|
|
6665
|
+
if (!value || typeof value !== "object" || Array.isArray(value)) continue;
|
|
6666
|
+
const position = order.indexOf(key);
|
|
6667
|
+
const decoration = {
|
|
6668
|
+
...position >= 0 ? { order: position } : {},
|
|
6669
|
+
...object(fields[key]),
|
|
6670
|
+
...object(value["x-ui"])
|
|
6671
|
+
};
|
|
6672
|
+
if (Object.keys(decoration).length) value["x-ui"] = decoration;
|
|
6673
|
+
if (key in defaults) value.default = defaults[key];
|
|
6674
|
+
}
|
|
6675
|
+
delete result.ui;
|
|
6676
|
+
delete result.defaults;
|
|
6677
|
+
return result;
|
|
6678
|
+
}
|
|
6679
|
+
function modelInputDefaults(input) {
|
|
6680
|
+
return Object.fromEntries(Object.entries(object(input.properties)).flatMap(([key, value]) => {
|
|
6681
|
+
const field = object(value);
|
|
6682
|
+
return "default" in field ? [[key, structuredClone(field.default)]] : [];
|
|
6683
|
+
}));
|
|
6684
|
+
}
|
|
6685
|
+
function orderedSchemaProperties(schema) {
|
|
6686
|
+
const rank = (value) => {
|
|
6687
|
+
const order = object(object(value)["x-ui"]).order;
|
|
6688
|
+
return typeof order === "number" ? order : Number.MAX_SAFE_INTEGER;
|
|
6689
|
+
};
|
|
6690
|
+
return Object.entries(object(schema.properties)).sort(([, a], [, b]) => rank(a) - rank(b));
|
|
6691
|
+
}
|
|
6692
|
+
function modelInputUi(input) {
|
|
6693
|
+
const entries = orderedSchemaProperties(input);
|
|
6694
|
+
return {
|
|
6695
|
+
order: entries.map(([key]) => key),
|
|
6696
|
+
fields: Object.fromEntries(entries.flatMap(([key, value]) => {
|
|
6697
|
+
const { order: _order, ...ui } = object(object(value)["x-ui"]);
|
|
6698
|
+
return Object.keys(ui).length ? [[key, ui]] : [];
|
|
6699
|
+
}))
|
|
6700
|
+
};
|
|
6701
|
+
}
|
|
6702
|
+
|
|
6703
|
+
// ../contracts/src/pricing.ts
|
|
6704
|
+
var BILLING_METRICS = [
|
|
6705
|
+
"requests",
|
|
6706
|
+
"input_tokens",
|
|
6707
|
+
"cached_input_tokens",
|
|
6708
|
+
"cache_write_tokens",
|
|
6709
|
+
"cache_creation_5m_input_tokens",
|
|
6710
|
+
"cache_creation_1h_input_tokens",
|
|
6711
|
+
"cache_read_input_tokens",
|
|
6712
|
+
"output_tokens",
|
|
6713
|
+
"input_characters",
|
|
6714
|
+
"input_utf8_bytes",
|
|
6715
|
+
"input_images",
|
|
6716
|
+
"output_images",
|
|
6717
|
+
"input_audio_seconds",
|
|
6718
|
+
"output_audio_seconds",
|
|
6719
|
+
"input_video_seconds",
|
|
6720
|
+
"output_video_seconds",
|
|
6721
|
+
"provider_credits",
|
|
6722
|
+
"web_search_requests"
|
|
6723
|
+
];
|
|
6724
|
+
var BILLING_EXPORT_DIMENSIONS = [
|
|
6725
|
+
"resolution",
|
|
6726
|
+
"duration",
|
|
6727
|
+
"layer_decomposition",
|
|
6728
|
+
"with_audio",
|
|
6729
|
+
"has_input_video",
|
|
6730
|
+
"hd",
|
|
6731
|
+
"prompt_extend",
|
|
6732
|
+
"modality",
|
|
6733
|
+
"tier",
|
|
6734
|
+
"quality",
|
|
6735
|
+
"image_count",
|
|
6736
|
+
"input_token_tier",
|
|
6737
|
+
"input_modality",
|
|
6738
|
+
"service_tier",
|
|
6739
|
+
"inference_geo",
|
|
6740
|
+
"speed",
|
|
6741
|
+
"region_scope",
|
|
6742
|
+
"has_reference_image",
|
|
6743
|
+
"mode"
|
|
6744
|
+
];
|
|
6745
|
+
function allocateDiscountedPriceLines(lines, saleAmount) {
|
|
6746
|
+
const moneyPattern = /^(?:0|[1-9]\d*)(?:\.\d{1,8})?$/;
|
|
6747
|
+
if (!moneyPattern.test(saleAmount) || lines.some((line) => !moneyPattern.test(line.amount))) {
|
|
6748
|
+
throw new Error("Sale allocation requires non-negative eight-decimal money");
|
|
6749
|
+
}
|
|
6750
|
+
const target = priceScaled(saleAmount);
|
|
6751
|
+
const weights = lines.map((line) => priceScaled(line.amount));
|
|
6752
|
+
const total = weights.reduce((sum, amount) => sum + amount, 0n);
|
|
6753
|
+
if (target > total) throw new Error("Discounted sale amount exceeds the frozen line total");
|
|
6754
|
+
const allocations = weights.map((weight) => total === 0n ? 0n : target * weight / total);
|
|
6755
|
+
let remainder = target - allocations.reduce((sum, amount) => sum + amount, 0n);
|
|
6756
|
+
return lines.map((line, index) => {
|
|
6757
|
+
let amount = allocations[index];
|
|
6758
|
+
if (weights[index] > 0n && remainder > 0n) {
|
|
6759
|
+
amount += 1n;
|
|
6760
|
+
remainder -= 1n;
|
|
6761
|
+
}
|
|
6762
|
+
return { ...line, discountedAmount: scaledMoney(amount) };
|
|
6763
|
+
});
|
|
6764
|
+
}
|
|
6765
|
+
function validateNormalizedUsage(value) {
|
|
6766
|
+
if (!isObject3(value) || value.schemaVersion !== 1 || !Array.isArray(value.components)) {
|
|
6767
|
+
throw new Error("Normalized usage must use the metered v1 envelope");
|
|
6768
|
+
}
|
|
6769
|
+
if (value.billingEvidenceComplete !== void 0 && typeof value.billingEvidenceComplete !== "boolean") {
|
|
6770
|
+
throw new Error("billingEvidenceComplete must be boolean");
|
|
6771
|
+
}
|
|
6772
|
+
if (value.components.length === 0 || value.components.length > 64) {
|
|
6773
|
+
throw new Error("Normalized usage must contain between 1 and 64 components");
|
|
6774
|
+
}
|
|
6775
|
+
const identities = /* @__PURE__ */ new Set();
|
|
6776
|
+
for (const [index, raw] of value.components.entries()) {
|
|
6777
|
+
if (!isObject3(raw) || !BILLING_METRICS.includes(raw.metric)) {
|
|
6778
|
+
throw new Error(`Usage component ${index} has an unsupported billing metric`);
|
|
6779
|
+
}
|
|
6780
|
+
if (typeof raw.quantity !== "number" || !Number.isFinite(raw.quantity) || raw.quantity < 0) {
|
|
6781
|
+
throw new Error(`Usage component ${index} quantity must be non-negative`);
|
|
6782
|
+
}
|
|
6783
|
+
if (raw.dimensions !== void 0 && (!isObject3(raw.dimensions) || Object.values(raw.dimensions).some((item) => !isPrimitive(item)))) {
|
|
6784
|
+
throw new Error(`Usage component ${index} dimensions must contain only scalar values`);
|
|
6785
|
+
}
|
|
6786
|
+
const identity = `${String(raw.metric)}:${stableDimensions(raw.dimensions)}`;
|
|
6787
|
+
if (identities.has(identity)) {
|
|
6788
|
+
throw new Error(`Usage component ${index} duplicates a metric and dimension set`);
|
|
6789
|
+
}
|
|
6790
|
+
identities.add(identity);
|
|
6791
|
+
}
|
|
6792
|
+
}
|
|
6793
|
+
function evaluatePriceRule(ruleValue, usageValue) {
|
|
6794
|
+
validatePriceRule(ruleValue);
|
|
6795
|
+
validateNormalizedUsage(usageValue);
|
|
6796
|
+
const rule = ruleValue;
|
|
6797
|
+
const usage = usageValue;
|
|
6798
|
+
if (usage.billingEvidenceComplete === false) {
|
|
6799
|
+
return { status: "incomplete", amount: "0", lines: [], issues: [{ code: "missing_usage", metric: "input_tokens", componentIndex: 0 }] };
|
|
6800
|
+
}
|
|
6801
|
+
const lines = [];
|
|
6802
|
+
const issues = [];
|
|
6803
|
+
let total = 0n;
|
|
6804
|
+
for (const [componentIndex, component] of usage.components.entries()) {
|
|
6805
|
+
const metricRates = rule.rates.filter((rate2) => rate2.metric === component.metric);
|
|
6806
|
+
if (metricRates.length === 0) continue;
|
|
6807
|
+
const matching = metricRates.filter((rate2) => dimensionsMatch(
|
|
6808
|
+
rate2.dimensions,
|
|
6809
|
+
component.dimensions
|
|
6810
|
+
));
|
|
6811
|
+
if (matching.length === 0) {
|
|
6812
|
+
if (component.quantity === 0) continue;
|
|
6813
|
+
issues.push({ code: "dimension_mismatch", metric: component.metric, componentIndex });
|
|
6814
|
+
continue;
|
|
6815
|
+
}
|
|
6816
|
+
const specificity = Math.max(...matching.map((rate2) => Object.keys(rate2.dimensions ?? {}).length));
|
|
6817
|
+
const selected = matching.filter((rate2) => Object.keys(rate2.dimensions ?? {}).length === specificity);
|
|
6818
|
+
if (selected.length !== 1) {
|
|
6819
|
+
if (component.quantity === 0) continue;
|
|
6820
|
+
issues.push({ code: "ambiguous_rate", metric: component.metric, componentIndex });
|
|
6821
|
+
continue;
|
|
6822
|
+
}
|
|
6823
|
+
const rate = selected[0];
|
|
6824
|
+
const amount = rateAmount(component.quantity, rate);
|
|
6825
|
+
total += amount;
|
|
6826
|
+
lines.push({
|
|
6827
|
+
metric: component.metric,
|
|
6828
|
+
quantity: component.quantity,
|
|
6829
|
+
unitSize: rate.unitSize,
|
|
6830
|
+
unitPrice: rate.unitPrice,
|
|
6831
|
+
rounding: rate.rounding,
|
|
6832
|
+
includedQuantity: rate.includedQuantity ?? 0,
|
|
6833
|
+
...rate.dimensions ? { dimensions: { ...rate.dimensions } } : {},
|
|
6834
|
+
amount: scaledMoney(amount),
|
|
6835
|
+
...component.evidence ? { evidence: structuredClone(component.evidence) } : {}
|
|
6836
|
+
});
|
|
6837
|
+
}
|
|
6838
|
+
return {
|
|
6839
|
+
status: issues.length === 0 ? "rated" : "incomplete",
|
|
6840
|
+
amount: scaledMoney(total),
|
|
6841
|
+
lines,
|
|
6842
|
+
issues
|
|
6843
|
+
};
|
|
6844
|
+
}
|
|
6845
|
+
function validatePriceRule(value) {
|
|
6846
|
+
if (!isObject3(value) || value.schemaVersion !== 1 || value.type !== "metered") {
|
|
6847
|
+
throw new Error("Price rule must use the metered v1 envelope");
|
|
6848
|
+
}
|
|
6849
|
+
if (!Array.isArray(value.rates) || value.rates.length === 0 || value.rates.length > 32) {
|
|
6850
|
+
throw new Error("Price rule must contain between 1 and 32 rates");
|
|
6851
|
+
}
|
|
6852
|
+
const identities = /* @__PURE__ */ new Set();
|
|
6853
|
+
for (const [index, raw] of value.rates.entries()) {
|
|
6854
|
+
if (!isObject3(raw) || !BILLING_METRICS.includes(raw.metric)) {
|
|
6855
|
+
throw new Error(`Price rate ${index} has an unsupported billing metric`);
|
|
6856
|
+
}
|
|
6857
|
+
if (!Number.isSafeInteger(raw.unitSize) || raw.unitSize <= 0) {
|
|
6858
|
+
throw new Error(`Price rate ${index} unitSize must be a positive integer`);
|
|
6859
|
+
}
|
|
6860
|
+
if (typeof raw.unitPrice !== "string" || !/^(?:0|[1-9]\d*)(?:\.\d{1,8})?$/.test(raw.unitPrice)) {
|
|
6861
|
+
throw new Error(`Price rate ${index} unitPrice must be a non-negative decimal string`);
|
|
6862
|
+
}
|
|
6863
|
+
if (!["proportional", "ceil"].includes(String(raw.rounding))) {
|
|
6864
|
+
throw new Error(`Price rate ${index} has an unsupported rounding mode`);
|
|
6865
|
+
}
|
|
6866
|
+
if (raw.includedQuantity !== void 0 && (typeof raw.includedQuantity !== "number" || !Number.isFinite(raw.includedQuantity) || raw.includedQuantity < 0)) {
|
|
6867
|
+
throw new Error(`Price rate ${index} includedQuantity must be non-negative`);
|
|
6868
|
+
}
|
|
6869
|
+
if (raw.dimensions !== void 0 && (!isObject3(raw.dimensions) || Object.values(raw.dimensions).some((item) => !isPrimitive(item)))) {
|
|
6870
|
+
throw new Error(`Price rate ${index} dimensions must contain only scalar values`);
|
|
6871
|
+
}
|
|
6872
|
+
const identity = `${String(raw.metric)}:${stableDimensions(raw.dimensions)}`;
|
|
6873
|
+
if (identities.has(identity)) {
|
|
6874
|
+
throw new Error(`Price rate ${index} duplicates a metric and dimension set`);
|
|
6875
|
+
}
|
|
6876
|
+
identities.add(identity);
|
|
6877
|
+
}
|
|
6878
|
+
}
|
|
6879
|
+
function isObject3(value) {
|
|
6880
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
6881
|
+
}
|
|
6882
|
+
function isPrimitive(value) {
|
|
6883
|
+
return value === null || ["string", "number", "boolean"].includes(typeof value);
|
|
6884
|
+
}
|
|
6885
|
+
function stableDimensions(value) {
|
|
6886
|
+
if (!isObject3(value)) return "";
|
|
6887
|
+
return Object.entries(value).sort(([left], [right]) => left.localeCompare(right)).map(([key, item]) => `${JSON.stringify(key)}:${JSON.stringify(item)}`).join(",");
|
|
6888
|
+
}
|
|
6889
|
+
var MONEY_SCALE2 = 100000000n;
|
|
6890
|
+
function dimensionsMatch(expected, actual) {
|
|
6891
|
+
return Object.entries(expected ?? {}).every(([key, value]) => actual?.[key] === value);
|
|
6892
|
+
}
|
|
6893
|
+
function rateAmount(quantity, rate) {
|
|
6894
|
+
const quantityFraction = subtractFractions(
|
|
6895
|
+
numberFraction(quantity),
|
|
6896
|
+
numberFraction(rate.includedQuantity ?? 0)
|
|
6897
|
+
);
|
|
6898
|
+
if (quantityFraction.numerator <= 0n) return 0n;
|
|
6899
|
+
const price = priceScaled(rate.unitPrice);
|
|
6900
|
+
const unitDenominator = quantityFraction.denominator * BigInt(rate.unitSize);
|
|
6901
|
+
if (rate.rounding === "ceil") {
|
|
6902
|
+
const units = divideCeil(quantityFraction.numerator, unitDenominator);
|
|
6903
|
+
return units * price;
|
|
6904
|
+
}
|
|
6905
|
+
return divideHalfUp(quantityFraction.numerator * price, unitDenominator);
|
|
6906
|
+
}
|
|
6907
|
+
function priceScaled(value) {
|
|
6908
|
+
const [whole = "0", fraction = ""] = value.split(".");
|
|
6909
|
+
return BigInt(whole) * MONEY_SCALE2 + BigInt((fraction + "00000000").slice(0, 8));
|
|
6910
|
+
}
|
|
6911
|
+
function scaledMoney(value) {
|
|
6912
|
+
const whole = value / MONEY_SCALE2;
|
|
6913
|
+
const fraction = (value % MONEY_SCALE2).toString().padStart(8, "0").replace(/0+$/, "");
|
|
6914
|
+
return fraction ? `${whole}.${fraction}` : whole.toString();
|
|
6915
|
+
}
|
|
6916
|
+
function numberFraction(value) {
|
|
6917
|
+
const [mantissa, exponentText] = value.toString().toLowerCase().split("e");
|
|
6918
|
+
const exponent = exponentText ? Number(exponentText) : 0;
|
|
6919
|
+
const [whole = "0", fraction = ""] = mantissa.split(".");
|
|
6920
|
+
const digits = `${whole}${fraction}`.replace(/^\+/, "");
|
|
6921
|
+
const decimalPlaces = fraction.length - exponent;
|
|
6922
|
+
if (decimalPlaces <= 0) {
|
|
6923
|
+
return { numerator: BigInt(digits) * 10n ** BigInt(-decimalPlaces), denominator: 1n };
|
|
6924
|
+
}
|
|
6925
|
+
return { numerator: BigInt(digits), denominator: 10n ** BigInt(decimalPlaces) };
|
|
6926
|
+
}
|
|
6927
|
+
function subtractFractions(left, right) {
|
|
6928
|
+
return {
|
|
6929
|
+
numerator: left.numerator * right.denominator - right.numerator * left.denominator,
|
|
6930
|
+
denominator: left.denominator * right.denominator
|
|
6931
|
+
};
|
|
6932
|
+
}
|
|
6933
|
+
function divideCeil(numerator, denominator) {
|
|
6934
|
+
return (numerator + denominator - 1n) / denominator;
|
|
6935
|
+
}
|
|
6936
|
+
function divideHalfUp(numerator, denominator) {
|
|
6937
|
+
return (numerator * 2n + denominator) / (denominator * 2n);
|
|
6938
|
+
}
|
|
6939
|
+
|
|
6940
|
+
// ../contracts/src/metering.ts
|
|
6941
|
+
function validateMeteringContract(value) {
|
|
6942
|
+
if (!isObject4(value) || value.schemaVersion !== 1 || !isMeteringKind(value.kind)) {
|
|
6943
|
+
throw new Error("Metering contract must use schemaVersion 1 and a supported kind");
|
|
6944
|
+
}
|
|
6945
|
+
if (!Array.isArray(value.metrics) || value.metrics.length === 0 || value.metrics.length > BILLING_METRICS.length) {
|
|
6946
|
+
throw new Error("Metering contract must contain supported metrics");
|
|
6947
|
+
}
|
|
6948
|
+
const seen = /* @__PURE__ */ new Set();
|
|
6949
|
+
for (const entry of value.metrics) {
|
|
6950
|
+
if (!isObject4(entry) || !BILLING_METRICS.includes(entry.metric)) {
|
|
6951
|
+
throw new Error("Metering contract has an unsupported metric");
|
|
6952
|
+
}
|
|
6953
|
+
if (typeof entry.requirement !== "string" || !["required", "conditional", "informational"].includes(entry.requirement)) {
|
|
6954
|
+
throw new Error("Metering metric has an unsupported requirement");
|
|
6955
|
+
}
|
|
6956
|
+
if (seen.has(String(entry.metric))) throw new Error("Metering contract duplicates a metric");
|
|
6957
|
+
seen.add(String(entry.metric));
|
|
6958
|
+
if (entry.requirement === "conditional") {
|
|
6959
|
+
if (typeof entry.whenFeature !== "string" || !entry.whenFeature.trim()) {
|
|
6960
|
+
throw new Error("Conditional metric requires whenFeature");
|
|
6961
|
+
}
|
|
6962
|
+
} else if ("whenFeature" in entry) {
|
|
6963
|
+
throw new Error("Only conditional metrics may declare whenFeature");
|
|
6964
|
+
}
|
|
6965
|
+
}
|
|
6966
|
+
}
|
|
6967
|
+
function assessUsageEvidence(contract, usage, features = {}) {
|
|
6968
|
+
const result = {
|
|
6969
|
+
kind: "unknown",
|
|
6970
|
+
evidenceStatus: "invalid",
|
|
6971
|
+
expectedMetrics: [],
|
|
6972
|
+
observedMetrics: [],
|
|
6973
|
+
missingMetrics: [],
|
|
6974
|
+
issues: []
|
|
6975
|
+
};
|
|
6976
|
+
if (contract === void 0 || contract === null) {
|
|
6977
|
+
result.issues.push("contract_unknown");
|
|
6978
|
+
return result;
|
|
6979
|
+
}
|
|
6980
|
+
try {
|
|
6981
|
+
validateMeteringContract(contract);
|
|
6982
|
+
} catch (error) {
|
|
6983
|
+
result.issues.push(`contract_invalid:${errorMessage(error)}`);
|
|
6984
|
+
return result;
|
|
6985
|
+
}
|
|
6986
|
+
result.kind = contract.kind;
|
|
6987
|
+
for (const entry of contract.metrics) {
|
|
6988
|
+
if (entry.requirement === "required") result.expectedMetrics.push(entry.metric);
|
|
6989
|
+
if (entry.requirement === "conditional") {
|
|
6990
|
+
const feature = entry.whenFeature;
|
|
6991
|
+
if (!Object.hasOwn(features, feature) || typeof features[feature] !== "boolean") {
|
|
6992
|
+
result.issues.push(`condition_unknown:${feature}`);
|
|
6993
|
+
} else if (features[feature]) {
|
|
6994
|
+
result.expectedMetrics.push(entry.metric);
|
|
6995
|
+
}
|
|
6996
|
+
}
|
|
6997
|
+
}
|
|
6998
|
+
if (result.issues.length > 0) return result;
|
|
6999
|
+
let explicitlyIncomplete = false;
|
|
7000
|
+
if (usage !== void 0 && usage !== null) {
|
|
7001
|
+
try {
|
|
7002
|
+
if (!isObject4(usage) || usage.schemaVersion !== 1 || !Array.isArray(usage.components)) {
|
|
7003
|
+
throw new Error("Normalized usage must use the metered v1 envelope");
|
|
7004
|
+
}
|
|
7005
|
+
if (usage.billingEvidenceComplete !== void 0 && typeof usage.billingEvidenceComplete !== "boolean") {
|
|
7006
|
+
throw new Error("billingEvidenceComplete must be boolean");
|
|
7007
|
+
}
|
|
7008
|
+
if (usage.components.length > 0) validateNormalizedUsage(usage);
|
|
7009
|
+
const observed = /* @__PURE__ */ new Set();
|
|
7010
|
+
for (const component of usage.components) {
|
|
7011
|
+
if (!component.metric.endsWith("_seconds") && component.metric !== "provider_credits" && !Number.isSafeInteger(component.quantity)) {
|
|
7012
|
+
throw new Error(`Quantity for ${component.metric} must be a safe integer`);
|
|
7013
|
+
}
|
|
7014
|
+
if (Object.values(component.dimensions ?? {}).some((value) => typeof value === "number" && !Number.isFinite(value))) {
|
|
7015
|
+
throw new Error("Usage dimensions must contain finite numeric values");
|
|
7016
|
+
}
|
|
7017
|
+
observed.add(component.metric);
|
|
7018
|
+
}
|
|
7019
|
+
result.observedMetrics = [...observed];
|
|
7020
|
+
explicitlyIncomplete = usage.billingEvidenceComplete === false;
|
|
7021
|
+
} catch (error) {
|
|
7022
|
+
result.issues.push(`usage_invalid:${errorMessage(error)}`);
|
|
7023
|
+
return result;
|
|
7024
|
+
}
|
|
7025
|
+
}
|
|
7026
|
+
result.missingMetrics = result.expectedMetrics.filter((metric) => !result.observedMetrics.includes(metric));
|
|
7027
|
+
if (explicitlyIncomplete) result.issues.push("billing_evidence_incomplete");
|
|
7028
|
+
result.evidenceStatus = result.expectedMetrics.length === 0 ? "not_expected" : result.missingMetrics.length === result.expectedMetrics.length ? "missing" : result.missingMetrics.length > 0 || explicitlyIncomplete ? "partial" : "complete";
|
|
7029
|
+
return result;
|
|
7030
|
+
}
|
|
7031
|
+
function isObject4(value) {
|
|
7032
|
+
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
7033
|
+
}
|
|
7034
|
+
function isMeteringKind(value) {
|
|
7035
|
+
return value === "token" || value === "non_token" || value === "mixed";
|
|
7036
|
+
}
|
|
7037
|
+
function errorMessage(error) {
|
|
7038
|
+
return error instanceof Error ? error.message : String(error);
|
|
7039
|
+
}
|
|
7040
|
+
|
|
7041
|
+
// ../contracts/src/tasks.ts
|
|
7042
|
+
var TASK_STATUSES = [
|
|
7043
|
+
"queued",
|
|
7044
|
+
"running",
|
|
7045
|
+
"succeeded",
|
|
7046
|
+
"failed",
|
|
7047
|
+
"cancelling",
|
|
7048
|
+
"cancelled"
|
|
7049
|
+
];
|
|
7050
|
+
function taskReceipt(task) {
|
|
7051
|
+
return { id: task.id, status: task.status };
|
|
7052
|
+
}
|
|
7053
|
+
function taskResult(task) {
|
|
7054
|
+
return {
|
|
7055
|
+
id: task.id,
|
|
7056
|
+
model: task.model,
|
|
7057
|
+
status: task.status,
|
|
7058
|
+
...task.assets.length ? { assets: task.assets } : {},
|
|
7059
|
+
...task.requestId ? { requestId: task.requestId } : {},
|
|
7060
|
+
...task.output !== void 0 ? { output: task.output } : {},
|
|
7061
|
+
...task.error ? { error: task.error } : {},
|
|
7062
|
+
...task.deliveryStatus ? { deliveryStatus: task.deliveryStatus } : {},
|
|
7063
|
+
...task.settlement ? { settlement: task.settlement } : {}
|
|
7064
|
+
};
|
|
7065
|
+
}
|
|
7066
|
+
function isTerminalTaskStatus(status) {
|
|
7067
|
+
return status === "succeeded" || status === "failed" || status === "cancelled";
|
|
7068
|
+
}
|
|
7069
|
+
|
|
7070
|
+
// ../contracts/src/monitoring.ts
|
|
7071
|
+
function defaultProbeInterval(kind, model) {
|
|
7072
|
+
if (/music/i.test(model)) return 172800;
|
|
7073
|
+
if (kind === "audio" && /sound/i.test(model)) return 86400;
|
|
7074
|
+
return ["language", "embedding", "audio"].includes(kind) ? 3600 : 86400;
|
|
7075
|
+
}
|
|
7076
|
+
function defaultProbeTimeout(kind) {
|
|
7077
|
+
return ["video", "world"].includes(kind) ? 1800 : ["image", "audio"].includes(kind) ? 300 : 120;
|
|
7078
|
+
}
|
|
7079
|
+
function classifyObservation(status, httpStatus, code = "") {
|
|
7080
|
+
if (/cancel|client_disconnect|invalid_input|validation_error/i.test(code) || status === "cancelled")
|
|
7081
|
+
return "excluded";
|
|
7082
|
+
if (httpStatus === 429) return "rate_limited";
|
|
7083
|
+
if (httpStatus === 403 && /geo|region|location|country/i.test(code))
|
|
7084
|
+
return "restricted";
|
|
7085
|
+
if (/auth|api.?key|balance|credit|quota_exhaust|model.*(not.?found|not.?exist)|invalid_model/i.test(
|
|
7086
|
+
code
|
|
7087
|
+
))
|
|
7088
|
+
return "failure";
|
|
7089
|
+
if ([400, 413, 422].includes(httpStatus ?? 0)) return "excluded";
|
|
7090
|
+
if (status === "failed" || status === "rejected" || httpStatus !== null && httpStatus >= 400 || /error|incomplete|truncat/i.test(code))
|
|
7091
|
+
return "failure";
|
|
7092
|
+
return status === "succeeded" ? "success" : "excluded";
|
|
7093
|
+
}
|
|
7094
|
+
var sampleCount = (items) => items.reduce((n, x) => n + (x.count ?? 1), 0);
|
|
7095
|
+
function availabilityStats(items) {
|
|
7096
|
+
const success = sampleCount(items.filter((x) => x.result === "success")), failure = sampleCount(items.filter((x) => x.result === "failure"));
|
|
7097
|
+
return {
|
|
7098
|
+
success,
|
|
7099
|
+
failure,
|
|
7100
|
+
excluded: sampleCount(items.filter((x) => x.result === "excluded")),
|
|
7101
|
+
rateLimited: sampleCount(items.filter((x) => x.result === "rate_limited")),
|
|
7102
|
+
restricted: sampleCount(items.filter((x) => x.result === "restricted")),
|
|
7103
|
+
rate: success + failure ? success / (success + failure) : null
|
|
7104
|
+
};
|
|
7105
|
+
}
|
|
7106
|
+
function availabilityBuckets(items, end, hours, intervalSeconds, core = false) {
|
|
7107
|
+
const endMs = end.getTime(), first = Math.floor(endMs / 36e5) * 36e5 - (hours - 1) * 36e5;
|
|
7108
|
+
const sorted = items.filter(
|
|
7109
|
+
(x) => Number.isFinite(Date.parse(x.at)) && Date.parse(x.at) <= endMs
|
|
7110
|
+
).slice().sort((a, b) => Date.parse(a.at) - Date.parse(b.at));
|
|
7111
|
+
const grace = Math.min(3600, Math.max(300, intervalSeconds * 0.1)) * 1e3;
|
|
7112
|
+
let cursor = 0;
|
|
7113
|
+
let prior;
|
|
7114
|
+
return Array.from({ length: hours }, (_, i) => {
|
|
7115
|
+
const start = first + i * 36e5, stop = Math.min(start + 36e5, endMs);
|
|
7116
|
+
const valid = [];
|
|
7117
|
+
while (cursor < sorted.length && (Date.parse(sorted[cursor].at) < stop || i === hours - 1 && Date.parse(sorted[cursor].at) === endMs)) {
|
|
7118
|
+
const item = sorted[cursor++];
|
|
7119
|
+
if (item.result !== "success" && item.result !== "failure") continue;
|
|
7120
|
+
prior = item;
|
|
7121
|
+
if (Date.parse(item.at) >= start) valid.push(item);
|
|
7122
|
+
}
|
|
7123
|
+
const s = sampleCount(valid.filter((x) => x.result === "success")), f = sampleCount(valid) - s;
|
|
7124
|
+
const fresh = prior && stop - Date.parse(prior.at) <= intervalSeconds * 1e3 + grace;
|
|
7125
|
+
const state = valid.length ? s && f ? "mixed" : s ? "success" : "failure" : !core && fresh ? prior.result : "unknown";
|
|
7126
|
+
const expected = core ? Math.ceil((stop - start) / 3e4) : null;
|
|
7127
|
+
return {
|
|
7128
|
+
start: new Date(start).toISOString(),
|
|
7129
|
+
end: new Date(stop).toISOString(),
|
|
7130
|
+
state,
|
|
7131
|
+
evidence: valid.length ? "measured" : !core && fresh ? "carried" : prior ? "expired" : "none",
|
|
7132
|
+
businessSuccess: sampleCount(
|
|
7133
|
+
valid.filter((x) => x.source === "business" && x.result === "success")
|
|
7134
|
+
),
|
|
7135
|
+
businessFailure: sampleCount(
|
|
7136
|
+
valid.filter((x) => x.source === "business" && x.result === "failure")
|
|
7137
|
+
),
|
|
7138
|
+
probeSuccess: sampleCount(
|
|
7139
|
+
valid.filter((x) => x.source === "probe" && x.result === "success")
|
|
7140
|
+
),
|
|
7141
|
+
probeFailure: sampleCount(
|
|
7142
|
+
valid.filter((x) => x.source === "probe" && x.result === "failure")
|
|
7143
|
+
),
|
|
7144
|
+
coreSuccess: sampleCount(
|
|
7145
|
+
valid.filter((x) => x.source === "core" && x.result === "success")
|
|
7146
|
+
),
|
|
7147
|
+
coreFailure: sampleCount(
|
|
7148
|
+
valid.filter((x) => x.source === "core" && x.result === "failure")
|
|
7149
|
+
),
|
|
7150
|
+
latestAt: prior?.at ?? null,
|
|
7151
|
+
expectedSamples: expected,
|
|
7152
|
+
incomplete: expected !== null && sampleCount(valid) < expected
|
|
7153
|
+
};
|
|
7154
|
+
});
|
|
7155
|
+
}
|
|
7156
|
+
function rateProbeUsage(price, usage) {
|
|
7157
|
+
if (!usage || !Array.isArray(usage.components) || !usage.components.length)
|
|
7158
|
+
return void 0;
|
|
7159
|
+
try {
|
|
7160
|
+
validatePriceRule(price);
|
|
7161
|
+
const metrics = new Set(
|
|
7162
|
+
usage.components.flatMap(
|
|
7163
|
+
(c) => c && typeof c === "object" && !Array.isArray(c) && typeof c.metric === "string" ? [c.metric] : []
|
|
7164
|
+
)
|
|
7165
|
+
);
|
|
7166
|
+
if (price.rates.some(
|
|
7167
|
+
(r) => !/^cache|cached_|web_search/.test(r.metric) && !metrics.has(r.metric)
|
|
7168
|
+
))
|
|
7169
|
+
return void 0;
|
|
7170
|
+
const e = evaluatePriceRule(price, usage);
|
|
7171
|
+
return e.status === "rated" && e.lines.length > 0 ? e.amount : void 0;
|
|
7172
|
+
} catch {
|
|
7173
|
+
return void 0;
|
|
7174
|
+
}
|
|
7175
|
+
}
|
|
7176
|
+
function probeCostExceeds(actual, limit) {
|
|
7177
|
+
const units = (value) => {
|
|
7178
|
+
if (!/^\d+(\.\d{1,8})?$/.test(value)) throw new Error("invalid_probe_cost");
|
|
7179
|
+
const [whole, fraction = ""] = value.split(".");
|
|
7180
|
+
return BigInt(whole) * 100000000n + BigInt(fraction.padEnd(8, "0"));
|
|
7181
|
+
};
|
|
7182
|
+
return units(actual) > units(limit);
|
|
7183
|
+
}
|
|
7184
|
+
|
|
7185
|
+
// ../contracts/src/sandbox.ts
|
|
7186
|
+
var SANDBOX_OPERATIONS = [
|
|
7187
|
+
{ id: "text-to-speech", modality: "audio", label: "\u8BED\u97F3\u5408\u6210" },
|
|
7188
|
+
{ id: "text-to-music", modality: "audio", label: "\u97F3\u4E50\u751F\u6210" },
|
|
7189
|
+
{ id: "multimodal-to-video", modality: "video", label: "\u5168\u80FD\u53C2\u8003\u751F" },
|
|
7190
|
+
{ id: "text-to-video", modality: "video", label: "\u53C2\u8003\u751F\u6210\u89C6\u9891" },
|
|
7191
|
+
{ id: "image-to-video", modality: "video", label: "\u9996\u5C3E\u5E27\u751F\u6210\u89C6\u9891" },
|
|
7192
|
+
{ id: "text-to-image", modality: "image", label: "\u6587\u751F\u56FE" },
|
|
7193
|
+
{ id: "image-to-image", modality: "image", label: "\u56FE\u751F\u56FE" },
|
|
7194
|
+
{ id: "text-to-text", modality: "language", label: "\u5BF9\u8BDD\u751F\u6210" }
|
|
7195
|
+
];
|
|
7196
|
+
var sandboxObject = (v) => v && typeof v === "object" && !Array.isArray(v) ? v : {};
|
|
7197
|
+
var obj = sandboxObject;
|
|
7198
|
+
var array = (v) => Array.isArray(v) ? v : [];
|
|
7199
|
+
function sandboxIdentity(slug) {
|
|
7200
|
+
return slug === "google/veo-3-1-fast" ? "google/veo-3-1-fast-generate-001" : slug;
|
|
7201
|
+
}
|
|
7202
|
+
function sandboxModelModes(model) {
|
|
7203
|
+
if (model.modality === "language") return ["text-to-text"];
|
|
7204
|
+
if (model.modality === "audio") return model.capabilities.inputModes.includes("text-to-speech") ? ["text-to-speech"] : ["elevenlabs/music_v2", "minimax/music-2.6"].includes(model.slug) ? ["text-to-music"] : [];
|
|
7205
|
+
if (model.slug === "heygen/heygen-avatar-video" || model.slug === "yadan/minimax-h3-local") return [];
|
|
7206
|
+
const modes = model.capabilities.inputModes.filter((mode) => ["text-to-image", "image-to-image", "text-to-video", "image-to-video"].includes(mode)).filter((mode) => !(model.slug === "pixverse/baidu-vod-pc1" && mode === "image-to-video"));
|
|
7207
|
+
if (model.capabilities.inputModes.includes("audio-to-video") && model.capabilities.inputModes.includes("video-to-video")) modes.push("multimodal-to-video");
|
|
7208
|
+
return modes;
|
|
7209
|
+
}
|
|
7210
|
+
function sandboxOperations(models) {
|
|
7211
|
+
return SANDBOX_OPERATIONS.filter((op) => new Set(models.filter((m) => m.modality === op.modality && sandboxModelModes(m).includes(op.id)).map((m) => sandboxIdentity(m.slug))).size >= 2);
|
|
7212
|
+
}
|
|
7213
|
+
function sandboxProperties(schema) {
|
|
7214
|
+
const root = obj(schema.inputSchema.properties);
|
|
7215
|
+
return { root, parameters: obj(obj(root.parameters).properties) };
|
|
7216
|
+
}
|
|
7217
|
+
function values(field) {
|
|
7218
|
+
return Array.isArray(field.enum) ? field.enum : [];
|
|
7219
|
+
}
|
|
7220
|
+
function normalized(value) {
|
|
7221
|
+
return String(value).toLowerCase();
|
|
7222
|
+
}
|
|
7223
|
+
function choose(field, requested, numeric = false) {
|
|
7224
|
+
const options = values(field);
|
|
7225
|
+
if (options.length) {
|
|
7226
|
+
const exact = options.find((v) => normalized(v) === normalized(requested));
|
|
7227
|
+
if (exact !== void 0) return exact;
|
|
7228
|
+
if (numeric) {
|
|
7229
|
+
const n = parseFloat(String(requested));
|
|
7230
|
+
const ranked = options.filter((v) => Number.isFinite(parseFloat(String(v)))).sort((a, b) => Math.abs(parseFloat(String(a)) - n) - Math.abs(parseFloat(String(b)) - n));
|
|
7231
|
+
if (ranked.length && Number.isFinite(n)) return ranked[0];
|
|
7232
|
+
}
|
|
7233
|
+
throw new Error(`\u4E0D\u652F\u6301 ${String(requested)}`);
|
|
7234
|
+
}
|
|
7235
|
+
const branches = array(field.anyOf).map(obj);
|
|
7236
|
+
const range = branches.find((b) => b.type === "integer" || typeof b.minimum === "number") ?? field;
|
|
7237
|
+
if (numeric) {
|
|
7238
|
+
const n = Number(requested);
|
|
7239
|
+
if (!Number.isFinite(n)) throw new Error("\u9700\u8981\u6709\u6548\u6570\u503C");
|
|
7240
|
+
const bounded = Math.min(Number(range.maximum ?? n), Math.max(Number(range.minimum ?? n), n));
|
|
7241
|
+
return range.type === "integer" || field.type === "integer" ? Math.round(bounded) : bounded;
|
|
7242
|
+
}
|
|
7243
|
+
return requested;
|
|
7244
|
+
}
|
|
7245
|
+
function applyFieldDefault(settings, fields, key, enabled = true) {
|
|
7246
|
+
if (!enabled || settings[key] !== void 0 || !fields[key]) return;
|
|
7247
|
+
const field = obj(fields[key]);
|
|
7248
|
+
if (field.default === void 0) return;
|
|
7249
|
+
const numeric = field.type === "integer" || typeof field.minimum === "number";
|
|
7250
|
+
settings[key] = choose(field, field.default, numeric);
|
|
7251
|
+
}
|
|
7252
|
+
function urls(value) {
|
|
7253
|
+
return array(value).map((v) => typeof v === "string" ? v : String(obj(v).url ?? "")).filter(Boolean);
|
|
7254
|
+
}
|
|
7255
|
+
function mediaRoles(schema) {
|
|
7256
|
+
const { root } = sandboxProperties(schema);
|
|
7257
|
+
if (root.content) return array(obj(obj(root.content).items).oneOf).flatMap((v) => array(obj(obj(obj(v).properties).role).enum)).filter((v) => typeof v === "string");
|
|
7258
|
+
return array(obj(obj(root.images)["x-ui"]).roles).filter((v) => typeof v === "string");
|
|
7259
|
+
}
|
|
7260
|
+
function sandboxSupports(schema, feature) {
|
|
7261
|
+
const { root } = sandboxProperties(schema);
|
|
7262
|
+
if (feature === "last_frame") return schema.model !== "yadan/minimax-h3-local" && mediaRoles(schema).includes("last_frame");
|
|
7263
|
+
if (feature === "reference_images") return mediaRoles(schema).includes("reference_image") || schema.model === "pixverse/baidu-vod-pc1";
|
|
7264
|
+
if (feature === "videos") return mediaRoles(schema).includes("reference_video") || array(obj(obj(root.videos)["x-ui"]).roles).includes("reference_video");
|
|
7265
|
+
if (feature === "audios") return mediaRoles(schema).includes("reference_audio") || !!root.audios && array(obj(obj(root.audios)["x-ui"]).accept).includes("url");
|
|
7266
|
+
return false;
|
|
7267
|
+
}
|
|
7268
|
+
function sandboxVoiceKey(model) {
|
|
7269
|
+
return `voice:${model}`;
|
|
7270
|
+
}
|
|
7271
|
+
function adaptSandboxInput(schema, mode, input) {
|
|
7272
|
+
const { root, parameters } = sandboxProperties(schema);
|
|
7273
|
+
const nested = !!root.input && !!root.parameters;
|
|
7274
|
+
const fields = nested ? parameters : root;
|
|
7275
|
+
const body = {};
|
|
7276
|
+
const settings = nested ? {} : body;
|
|
7277
|
+
for (const key of array(schema.inputSchema.required)) if (typeof key === "string" && obj(root[key]).default !== void 0) body[key] = obj(root[key]).default;
|
|
7278
|
+
if (root.model) body.model = String(schema.defaults?.model ?? schema.model.split("/").at(-1));
|
|
7279
|
+
const prompt = typeof input.prompt === "string" ? input.prompt.trim() : "";
|
|
7280
|
+
if (!prompt) throw new Error("\u8BF7\u586B\u5199\u63D0\u793A\u8BCD\u6216\u6717\u8BFB\u6587\u672C");
|
|
7281
|
+
if (nested) body.input = { messages: [{ role: "user", content: [{ text: prompt }, ...urls(input.images).map((image) => ({ image }))] }] };
|
|
7282
|
+
else if (root.content) body.content = [{ type: "text", text: prompt }];
|
|
7283
|
+
else body[root.prompt ? "prompt" : root.texts ? "texts" : "text"] = prompt;
|
|
7284
|
+
if (schema.model === "yadan/minimax-h3-local" && !["first_frame", "reference_images", "videos", "audios"].some((key) => urls(input[key]).length)) throw new Error("H3 Local \u5F53\u524D\u63A5\u5165\u9700\u8981\u81F3\u5C11\u4E00\u4EFD\u53C2\u8003\u7D20\u6750");
|
|
7285
|
+
const imageInput = urls(input.images);
|
|
7286
|
+
const first = urls(input.first_frame);
|
|
7287
|
+
if (mode === "image-to-image" && !imageInput.length) throw new Error("\u56FE\u751F\u56FE\u9700\u8981\u8F93\u5165\u56FE\u7247");
|
|
7288
|
+
if (mode === "image-to-video" && first.length !== 1) throw new Error("\u9996\u5C3E\u5E27\u751F\u6210\u89C6\u9891\u9700\u8981\u4E00\u5F20\u9996\u5E27");
|
|
7289
|
+
if (mode === "text-to-image" && imageInput.length) throw new Error("\u8BF7\u5207\u6362\u5230\u56FE\u751F\u56FE");
|
|
7290
|
+
if (mode === "text-to-video" && first.length) throw new Error("\u8BF7\u5207\u6362\u5230\u9996\u5C3E\u5E27\u751F\u6210\u89C6\u9891");
|
|
7291
|
+
if (!nested && mode === "image-to-image") {
|
|
7292
|
+
if (root.imageUrl) {
|
|
7293
|
+
if (imageInput.length > 1) throw new Error("\u6B64\u6A21\u578B\u53EA\u652F\u6301\u4E00\u5F20\u8F93\u5165\u56FE");
|
|
7294
|
+
body.imageUrl = imageInput[0];
|
|
7295
|
+
} else if (obj(root.image).type === "object") body.images = imageInput.map((url) => ({ url }));
|
|
7296
|
+
else if (root.image) body.image = imageInput;
|
|
7297
|
+
else if (root.images) body.images = imageInput;
|
|
7298
|
+
else throw new Error("\u6A21\u578B\u6CA1\u6709\u53EF\u6620\u5C04\u7684\u56FE\u7247\u8F93\u5165");
|
|
7299
|
+
}
|
|
7300
|
+
const media = [];
|
|
7301
|
+
for (const [key, role, type] of [["first_frame", "first_frame", "image_url"], ["last_frame", "last_frame", "image_url"], ["reference_images", "reference_image", "image_url"], ["videos", "reference_video", "video_url"], ["audios", "reference_audio", "audio_url"]]) {
|
|
7302
|
+
const entries = urls(input[key]);
|
|
7303
|
+
if (key !== "first_frame" && entries.length && !sandboxSupports(schema, key)) throw new Error(`\u6A21\u578B\u4E0D\u652F\u6301 ${key}`);
|
|
7304
|
+
for (const url of entries) media.push({ key, role, type, url });
|
|
7305
|
+
}
|
|
7306
|
+
if (urls(input.last_frame).length && !first.length) throw new Error("\u5C3E\u5E27\u9700\u8981\u540C\u65F6\u63D0\u4F9B\u9996\u5E27");
|
|
7307
|
+
if (first.length && (urls(input.reference_images).length || urls(input.videos).length || urls(input.audios).length)) throw new Error("\u9996\u5C3E\u5E27\u4E0E\u53C2\u8003\u7D20\u6750\u8BF7\u5206\u5F00\u8FD0\u884C");
|
|
7308
|
+
if (root.content) body.content = [...array(body.content), ...media.map((m) => ({ type: m.type, [m.type]: { url: m.url }, role: m.role }))];
|
|
7309
|
+
else for (const [key, type] of [["images", "image_url"], ["videos", "video_url"], ["audios", "audio_url"]]) {
|
|
7310
|
+
const entries = media.filter((m) => m.type === type);
|
|
7311
|
+
if (entries.length) body[key] = entries.map((m, i) => schema.model === "yadan/minimax-h3-local" ? { url: m.url } : schema.model === "pixverse/baidu-vod-pc1" ? { url: m.url, role: "subject", referenceName: `ref${i + 1}` } : { url: m.url, role: m.role });
|
|
7312
|
+
}
|
|
7313
|
+
if (schema.model === "pixverse/baidu-vod-pc1" && urls(input.reference_images).length) {
|
|
7314
|
+
const names = urls(input.reference_images).map((_, i) => `@ref${i + 1}`);
|
|
7315
|
+
if (!names.every((name) => prompt.includes(name))) throw new Error(`\u8BF7\u5728\u63D0\u793A\u8BCD\u4E2D\u5F15\u7528 ${names.join("\u3001")}`);
|
|
7316
|
+
}
|
|
7317
|
+
if (schema.model.startsWith("xai/grok-imagine-video")) body.mode = first.length ? "image-to-video" : urls(input.reference_images).length ? "reference-to-video" : "text-to-video";
|
|
7318
|
+
const ratio = typeof input.aspect_ratio === "string" && input.aspect_ratio !== "default" ? input.aspect_ratio : void 0;
|
|
7319
|
+
const resolution = typeof input.resolution === "string" && input.resolution !== "default" ? input.resolution : void 0;
|
|
7320
|
+
const ratioKey = ["ratio", "aspect_ratio", "aspectRatio"].find((k) => fields[k]);
|
|
7321
|
+
if (ratio && ratioKey && !(["kuaishou/baidu-vod-kling-v3", "pixverse/baidu-vod-p60", "bytedance/doubao-seedance-2-5-260628"].includes(schema.model) && first.length)) settings[ratioKey] = choose(obj(fields[ratioKey]), ratio);
|
|
7322
|
+
if (first.length && schema.model === "bytedance/doubao-seedance-2-5-260628") settings.ratio = "adaptive";
|
|
7323
|
+
if (resolution && fields.resolution) settings.resolution = choose(obj(fields.resolution), resolution);
|
|
7324
|
+
else applyFieldDefault(settings, fields, "resolution");
|
|
7325
|
+
applyFieldDefault(settings, fields, "duration", input.duration === void 0);
|
|
7326
|
+
applyFieldDefault(settings, fields, "mode", settings.mode === void 0 && body.mode === void 0);
|
|
7327
|
+
if (input.generate_audio === void 0) applyFieldDefault(settings, fields, fields.with_audio ? "with_audio" : "generate_audio");
|
|
7328
|
+
if (fields.size && (ratio || resolution)) {
|
|
7329
|
+
const [rw, rh] = (ratio ?? "1:1").split(":").map(Number);
|
|
7330
|
+
if (!rw || !rh) throw new Error("\u65E0\u6548\u753B\u9762\u6BD4\u4F8B");
|
|
7331
|
+
const edge = resolution ? parseFloat(resolution) * 1024 : 1024;
|
|
7332
|
+
let w = Math.round(edge * Math.sqrt(rw / rh) / 16) * 16;
|
|
7333
|
+
let h = Math.round(edge * Math.sqrt(rh / rw) / 16) * 16;
|
|
7334
|
+
const max = schema.model.startsWith("openai/") ? 3840 : schema.model.includes("qwen-image-edit") || nested && mode === "image-to-image" ? 2048 : 4096;
|
|
7335
|
+
if (Math.max(w, h) > max) {
|
|
7336
|
+
const scale = max / Math.max(w, h);
|
|
7337
|
+
w = Math.floor(w * scale / 16) * 16;
|
|
7338
|
+
h = Math.floor(h * scale / 16) * 16;
|
|
7339
|
+
}
|
|
7340
|
+
settings.size = `${w}${nested ? "*" : "x"}${h}`;
|
|
7341
|
+
}
|
|
7342
|
+
if (input.duration !== void 0 && fields.duration) settings.duration = choose(obj(fields.duration), input.duration, true);
|
|
7343
|
+
if (input.generate_audio !== void 0) {
|
|
7344
|
+
const key = fields.generate_audio ? "generate_audio" : fields.with_audio ? "with_audio" : void 0;
|
|
7345
|
+
if (!key) throw new Error("\u6A21\u578B\u4E0D\u652F\u6301\u63A7\u5236\u751F\u6210\u97F3\u9891");
|
|
7346
|
+
settings[key] = input.generate_audio;
|
|
7347
|
+
}
|
|
7348
|
+
if (mode === "text-to-speech") {
|
|
7349
|
+
const voice = input[sandboxVoiceKey(schema.model)] ?? obj(root.voice_id).default;
|
|
7350
|
+
if (!voice) throw new Error("\u8BF7\u9009\u62E9\u6B64\u6A21\u578B\u7684\u97F3\u8272");
|
|
7351
|
+
body.voice_id = voice;
|
|
7352
|
+
}
|
|
7353
|
+
if (mode === "text-to-music") {
|
|
7354
|
+
body.instrumental = input.instrumental ?? true;
|
|
7355
|
+
if (root.lyrics_optimizer && body.instrumental === false) body.lyrics_optimizer = true;
|
|
7356
|
+
}
|
|
7357
|
+
if (nested) body.parameters = settings;
|
|
7358
|
+
return body;
|
|
7359
|
+
}
|
|
7360
|
+
function sandboxInputSchema(schemas, mode) {
|
|
7361
|
+
const field = (title, type = "string", extra = {}) => ({ type, title, ...extra });
|
|
7362
|
+
const properties = { prompt: field(mode === "text-to-speech" ? "\u6717\u8BFB\u6587\u672C" : "\u63D0\u793A\u8BCD", "string", { minLength: 1, "x-ui": { control: "textarea", order: 0 } }) };
|
|
7363
|
+
const required = ["prompt"];
|
|
7364
|
+
const mediaField = (title, maxItems) => field(title, "array", { items: { type: "object", properties: { url: { type: "string", minLength: 1 }, role: { type: "string" } }, required: ["url"] }, maxItems, "x-ui": { control: "media", accept: ["url"] } });
|
|
7365
|
+
if (mode === "image-to-image") {
|
|
7366
|
+
properties.images = mediaField("\u8F93\u5165\u56FE\u7247", 16);
|
|
7367
|
+
required.push("images");
|
|
7368
|
+
obj(properties.images).minItems = 1;
|
|
7369
|
+
}
|
|
7370
|
+
if (mode === "image-to-video") {
|
|
7371
|
+
properties.first_frame = mediaField("\u9996\u5E27", 1);
|
|
7372
|
+
required.push("first_frame");
|
|
7373
|
+
obj(properties.first_frame).minItems = 1;
|
|
7374
|
+
}
|
|
7375
|
+
if (mode.endsWith("video")) {
|
|
7376
|
+
for (const [key, title, max] of [["last_frame", "\u5C3E\u5E27", 1], ["reference_images", "\u53C2\u8003\u56FE\u7247", 9], ["videos", "\u53C2\u8003\u89C6\u9891", 3], ["audios", "\u53C2\u8003\u97F3\u9891", 3]]) {
|
|
7377
|
+
if (key === "last_frame" && mode !== "image-to-video") continue;
|
|
7378
|
+
if (key !== "last_frame" && mode === "image-to-video") continue;
|
|
7379
|
+
if (new Set(schemas.map((s) => sandboxIdentity(s.model))).size >= 2 && schemas.every((s) => sandboxSupports(s, key))) properties[key] = mediaField(title, max);
|
|
7380
|
+
}
|
|
7381
|
+
properties.duration = field("\u76EE\u6807\u65F6\u957F\uFF08\u79D2\uFF09", "integer", { minimum: 1, maximum: 30 });
|
|
7382
|
+
}
|
|
7383
|
+
if (mode.endsWith("image") || mode.endsWith("video")) {
|
|
7384
|
+
const fields = schemas.map((s) => {
|
|
7385
|
+
const { root, parameters } = sandboxProperties(s);
|
|
7386
|
+
return root.parameters ? parameters : root;
|
|
7387
|
+
});
|
|
7388
|
+
const ratios = ["1:1", "16:9", "9:16", "4:3", "3:4", "3:2", "2:3", "21:9"].filter((r) => fields.every((p) => {
|
|
7389
|
+
const k = ["ratio", "aspect_ratio", "aspectRatio"].find((k2) => p[k2]);
|
|
7390
|
+
return !k || !values(obj(p[k])).length || values(obj(p[k])).includes(r);
|
|
7391
|
+
}));
|
|
7392
|
+
properties.aspect_ratio = field("\u753B\u9762\u6BD4\u4F8B", "string", { enum: ["default", ...ratios], default: "default", "x-ui": { optionLabels: { default: "\u5404\u6A21\u578B\u9ED8\u8BA4" } } });
|
|
7393
|
+
const resolutions = (mode.endsWith("image") ? ["1K", "2K", "4K"] : ["480p", "540p", "720p", "768p", "1080p", "2K", "4K"]).filter((r) => fields.every((p) => !p.resolution || !values(obj(p.resolution)).length || values(obj(p.resolution)).some((v) => normalized(v) === r.toLowerCase())));
|
|
7394
|
+
properties.resolution = field("\u6E05\u6670\u5EA6", "string", { enum: ["default", ...resolutions], default: "default", "x-ui": { optionLabels: { default: "\u5404\u6A21\u578B\u9ED8\u8BA4" } } });
|
|
7395
|
+
if (schemas.length >= 2 && fields.every((p) => p.generate_audio || p.with_audio)) properties.generate_audio = field("\u751F\u6210\u58F0\u97F3", "boolean");
|
|
7396
|
+
}
|
|
7397
|
+
if (mode === "text-to-speech") for (const s of schemas) {
|
|
7398
|
+
const voice = obj(sandboxProperties(s).root.voice_id);
|
|
7399
|
+
properties[sandboxVoiceKey(s.model)] = { ...voice, title: `${s.model} \xB7 \u97F3\u8272`, "x-ui": { ...obj(voice["x-ui"]), resourceModel: s.model } };
|
|
7400
|
+
required.push(sandboxVoiceKey(s.model));
|
|
7401
|
+
}
|
|
7402
|
+
if (mode === "text-to-text") {
|
|
7403
|
+
properties.system = field("\u7CFB\u7EDF\u63D0\u793A\u8BCD", "string", { "x-ui": { control: "textarea" } });
|
|
7404
|
+
properties.messages = field("\u5BF9\u8BDD\u5386\u53F2\uFF08\u53EF\u9009\uFF09", "array", { items: { type: "object", properties: { role: { type: "string", enum: ["user", "assistant"] }, content: { type: "string" } }, required: ["role", "content"], additionalProperties: false }, "x-ui": { control: "json" } });
|
|
7405
|
+
}
|
|
7406
|
+
if (mode === "text-to-music") properties.instrumental = field("\u7EAF\u97F3\u4E50", "boolean", { default: true });
|
|
7407
|
+
const defaults = {};
|
|
7408
|
+
for (const [key, value] of Object.entries(properties)) if (obj(value).default !== void 0) defaults[key] = obj(value).default;
|
|
7409
|
+
return { model: schemas.map((s) => s.model).join(","), version: 1, dialect: "https://json-schema.org/draft/2020-12/schema", inputSchema: { type: "object", properties, required, additionalProperties: false }, outputSchema: {}, uiSchema: {}, defaults, examples: [] };
|
|
7410
|
+
}
|
|
7411
|
+
|
|
7412
|
+
// ../contracts/src/ratio-display-order.ts
|
|
7413
|
+
function parseRatioParts(value) {
|
|
7414
|
+
const matched = /^\s*(\d+(?:\.\d+)?)\s*:\s*(\d+(?:\.\d+)?)\s*$/.exec(value);
|
|
7415
|
+
if (!matched) return void 0;
|
|
7416
|
+
const w = Number(matched[1]);
|
|
7417
|
+
const h = Number(matched[2]);
|
|
7418
|
+
return w > 0 && h > 0 ? { w, h } : void 0;
|
|
7419
|
+
}
|
|
7420
|
+
function ratioDisplayOrderKey(value) {
|
|
7421
|
+
const normalized2 = value.trim();
|
|
7422
|
+
const parts = parseRatioParts(normalized2);
|
|
7423
|
+
if (!parts) {
|
|
7424
|
+
const auto = normalized2.toLowerCase() === "auto" ? 0 : 1;
|
|
7425
|
+
return [0, auto, 0, 0, value];
|
|
7426
|
+
}
|
|
7427
|
+
if (parts.w === parts.h) return [1, 0, 0, 0, value];
|
|
7428
|
+
const long = Math.max(parts.w, parts.h);
|
|
7429
|
+
const short = Math.min(parts.w, parts.h);
|
|
7430
|
+
const landscape = parts.w > parts.h ? 1 : 0;
|
|
7431
|
+
return short === 1 ? [3, long, landscape, -short, value] : [2, long, landscape, -short, value];
|
|
7432
|
+
}
|
|
7433
|
+
function compareRatioDisplayOrder(a, b) {
|
|
7434
|
+
const ka = ratioDisplayOrderKey(a);
|
|
7435
|
+
const kb = ratioDisplayOrderKey(b);
|
|
7436
|
+
for (let index = 0; index < ka.length; index += 1) {
|
|
7437
|
+
if (ka[index] !== kb[index]) return ka[index] < kb[index] ? -1 : 1;
|
|
7438
|
+
}
|
|
7439
|
+
return 0;
|
|
7440
|
+
}
|
|
7441
|
+
function sortRatioDisplayOrder(values2) {
|
|
7442
|
+
return [...values2].sort(compareRatioDisplayOrder);
|
|
7443
|
+
}
|
|
7444
|
+
var RATIO_SCHEMA_FIELDS = ["ratio", "aspect_ratio", "aspectRatio"];
|
|
7445
|
+
function isPlainRecord(value) {
|
|
7446
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
7447
|
+
}
|
|
7448
|
+
function orderSchemaRatioProperties(properties) {
|
|
7449
|
+
if (!isPlainRecord(properties)) return properties;
|
|
7450
|
+
let touched = false;
|
|
7451
|
+
const next = { ...properties };
|
|
7452
|
+
for (const field of RATIO_SCHEMA_FIELDS) {
|
|
7453
|
+
const property = next[field];
|
|
7454
|
+
if (!isPlainRecord(property)) continue;
|
|
7455
|
+
const values2 = property.enum;
|
|
7456
|
+
if (!Array.isArray(values2) || !values2.every((value) => typeof value === "string")) continue;
|
|
7457
|
+
const ordered = sortRatioDisplayOrder(values2);
|
|
7458
|
+
if (ordered.every((value, index) => value === values2[index])) continue;
|
|
7459
|
+
const orderedProperty = { ...property, enum: ordered };
|
|
7460
|
+
const ui = orderedProperty["x-ui"];
|
|
7461
|
+
if (isPlainRecord(ui) && isPlainRecord(ui.optionLabels)) {
|
|
7462
|
+
const labels = ui.optionLabels;
|
|
7463
|
+
orderedProperty["x-ui"] = {
|
|
7464
|
+
...ui,
|
|
7465
|
+
optionLabels: Object.fromEntries(ordered.map((value) => [value, labels[value] ?? value]))
|
|
7466
|
+
};
|
|
7467
|
+
}
|
|
7468
|
+
next[field] = orderedProperty;
|
|
7469
|
+
touched = true;
|
|
7470
|
+
}
|
|
7471
|
+
return touched ? next : properties;
|
|
7472
|
+
}
|
|
7473
|
+
|
|
6168
7474
|
// src/catalog/media-geometry.ts
|
|
6169
7475
|
var RATIO_FIELDS = ["ratio", "aspect_ratio", "aspectRatio"];
|
|
6170
7476
|
var QUALITY_FIELDS = ["quality"];
|
|
@@ -6202,12 +7508,12 @@ var PRO_TIER_SIZE_BY_RATIO = {
|
|
|
6202
7508
|
"1.5K": { "1:1": "1.5K", "4:3": "1792x1344", "3:4": "1344x1792", "16:9": "2048x1152", "9:16": "1152x2048", "3:2": "1872x1248", "2:3": "1248x1872", "21:9": "2352x1008" },
|
|
6203
7509
|
"2K": { "1:1": "2K", "4:3": "2368x1776", "3:4": "1776x2368", "16:9": "2816x1584", "9:16": "1584x2816", "3:2": "2496x1664", "2:3": "1664x2496", "21:9": "3136x1344" }
|
|
6204
7510
|
};
|
|
6205
|
-
function
|
|
7511
|
+
function isObject5(value) {
|
|
6206
7512
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
6207
7513
|
}
|
|
6208
7514
|
function propertiesOf(schema) {
|
|
6209
|
-
if (!
|
|
6210
|
-
return
|
|
7515
|
+
if (!isObject5(schema)) return {};
|
|
7516
|
+
return isObject5(schema.properties) ? schema.properties : {};
|
|
6211
7517
|
}
|
|
6212
7518
|
function stringList(value) {
|
|
6213
7519
|
if (!Array.isArray(value)) return [];
|
|
@@ -6219,8 +7525,8 @@ function stringOptions(property) {
|
|
|
6219
7525
|
return stringList(property.examples);
|
|
6220
7526
|
}
|
|
6221
7527
|
function optionLabelsOf(property, options, fallback) {
|
|
6222
|
-
const ui =
|
|
6223
|
-
const fromSchema =
|
|
7528
|
+
const ui = isObject5(property["x-ui"]) ? property["x-ui"] : {};
|
|
7529
|
+
const fromSchema = isObject5(ui.optionLabels) ? ui.optionLabels : {};
|
|
6224
7530
|
const labels = {};
|
|
6225
7531
|
for (const option of options) {
|
|
6226
7532
|
const schemaLabel = fromSchema[option];
|
|
@@ -6248,10 +7554,10 @@ function collectTiers(property) {
|
|
|
6248
7554
|
function locate(root, names) {
|
|
6249
7555
|
const nested = propertiesOf(root.parameters);
|
|
6250
7556
|
for (const field of names) {
|
|
6251
|
-
if (
|
|
7557
|
+
if (isObject5(root[field])) return { field, property: root[field] };
|
|
6252
7558
|
}
|
|
6253
7559
|
for (const field of names) {
|
|
6254
|
-
if (
|
|
7560
|
+
if (isObject5(nested[field])) return { field, nest: "parameters", property: nested[field] };
|
|
6255
7561
|
}
|
|
6256
7562
|
return void 0;
|
|
6257
7563
|
}
|
|
@@ -6353,7 +7659,7 @@ function writeField(output, located, value) {
|
|
|
6353
7659
|
return;
|
|
6354
7660
|
}
|
|
6355
7661
|
const current = output[located.nest];
|
|
6356
|
-
const nested =
|
|
7662
|
+
const nested = isObject5(current) ? { ...current } : {};
|
|
6357
7663
|
nested[located.field] = value;
|
|
6358
7664
|
output[located.nest] = nested;
|
|
6359
7665
|
}
|
|
@@ -6363,16 +7669,16 @@ function readField(input, located) {
|
|
|
6363
7669
|
return typeof value2 === "string" ? value2 : void 0;
|
|
6364
7670
|
}
|
|
6365
7671
|
const nested = input[located.nest];
|
|
6366
|
-
if (!
|
|
7672
|
+
if (!isObject5(nested)) return void 0;
|
|
6367
7673
|
const value = nested[located.field];
|
|
6368
7674
|
return typeof value === "string" ? value : void 0;
|
|
6369
7675
|
}
|
|
6370
7676
|
function reverseLookup(table, size) {
|
|
6371
|
-
const
|
|
6372
|
-
if (TIER_PATTERN.test(
|
|
7677
|
+
const normalized2 = size.replaceAll("*", "x");
|
|
7678
|
+
if (TIER_PATTERN.test(normalized2)) return { resolution: displayTier(normalized2), ratio: "1:1" };
|
|
6373
7679
|
for (const [resolution, ratios] of Object.entries(table)) {
|
|
6374
7680
|
for (const [ratio, mapped] of Object.entries(ratios)) {
|
|
6375
|
-
if (mapped.replaceAll("*", "x") ===
|
|
7681
|
+
if (mapped.replaceAll("*", "x") === normalized2) return { resolution, ratio };
|
|
6376
7682
|
}
|
|
6377
7683
|
}
|
|
6378
7684
|
return void 0;
|
|
@@ -6383,7 +7689,7 @@ function projectMediaGeometry(inputSchema) {
|
|
|
6383
7689
|
const quality = inspected.quality ? fieldView(inspected.quality, stringOptions(inspected.quality.property), QUALITY_LABELS) : void 0;
|
|
6384
7690
|
if (inspected.kind === "resolution-ratio" && inspected.resolution && inspected.ratio) {
|
|
6385
7691
|
const resolutionOptions = stringOptions(inspected.resolution.property).map(displayTier);
|
|
6386
|
-
const ratioOptions = stringOptions(inspected.ratio.property);
|
|
7692
|
+
const ratioOptions = sortRatioDisplayOrder(stringOptions(inspected.ratio.property));
|
|
6387
7693
|
return {
|
|
6388
7694
|
kind: inspected.kind,
|
|
6389
7695
|
resolution: fieldView(inspected.resolution, resolutionOptions, identityLabels(resolutionOptions)),
|
|
@@ -6392,12 +7698,12 @@ function projectMediaGeometry(inputSchema) {
|
|
|
6392
7698
|
};
|
|
6393
7699
|
}
|
|
6394
7700
|
if (inspected.kind === "ratio-only" && inspected.ratio) {
|
|
6395
|
-
const ratioOptions = stringOptions(inspected.ratio.property);
|
|
7701
|
+
const ratioOptions = sortRatioDisplayOrder(stringOptions(inspected.ratio.property));
|
|
6396
7702
|
return { kind: inspected.kind, ratio: ratioView(inspected.ratio, ratioOptions), ...quality ? { quality } : {} };
|
|
6397
7703
|
}
|
|
6398
7704
|
if ((inspected.kind === "pixel-size" || inspected.kind === "tier-size") && inspected.size && table) {
|
|
6399
7705
|
const resolutionOptions = Object.keys(table);
|
|
6400
|
-
const ratioOptions = [...new Set(Object.values(table).flatMap((ratios) => Object.keys(ratios)))];
|
|
7706
|
+
const ratioOptions = sortRatioDisplayOrder([...new Set(Object.values(table).flatMap((ratios) => Object.keys(ratios)))]);
|
|
6401
7707
|
return {
|
|
6402
7708
|
kind: inspected.kind,
|
|
6403
7709
|
resolution: {
|
|
@@ -6477,7 +7783,7 @@ function unifiedFromInput(input) {
|
|
|
6477
7783
|
function applyMediaGeometry(inputSchema, input) {
|
|
6478
7784
|
const inspected = inspect(inputSchema);
|
|
6479
7785
|
const next = { ...input };
|
|
6480
|
-
if (inspected.size?.nest === "parameters" &&
|
|
7786
|
+
if (inspected.size?.nest === "parameters" && isObject5(input.parameters)) {
|
|
6481
7787
|
next.parameters = { ...input.parameters };
|
|
6482
7788
|
}
|
|
6483
7789
|
const nativeSize = inspected.size ? readField(next, inspected.size) : void 0;
|
|
@@ -6487,7 +7793,7 @@ function applyMediaGeometry(inputSchema, input) {
|
|
|
6487
7793
|
);
|
|
6488
7794
|
if (!shouldEncode) return next;
|
|
6489
7795
|
const encoded = encodeMediaGeometry(inputSchema, unified);
|
|
6490
|
-
if (
|
|
7796
|
+
if (isObject5(encoded.parameters) && isObject5(next.parameters)) {
|
|
6491
7797
|
next.parameters = { ...next.parameters, ...encoded.parameters };
|
|
6492
7798
|
} else {
|
|
6493
7799
|
Object.assign(next, encoded);
|
|
@@ -6543,7 +7849,7 @@ var NexraWaitTimeoutError = class extends Error {
|
|
|
6543
7849
|
};
|
|
6544
7850
|
|
|
6545
7851
|
// src/generated/version.generated.ts
|
|
6546
|
-
var SDK_VERSION = "0.1.0-alpha.
|
|
7852
|
+
var SDK_VERSION = "0.1.0-alpha.7";
|
|
6547
7853
|
|
|
6548
7854
|
// src/transport.ts
|
|
6549
7855
|
var DEFAULT_BASE_URL = "https://api.nexra-ai.com/v1";
|
|
@@ -6615,9 +7921,9 @@ function jsonBody(value) {
|
|
|
6615
7921
|
headers: { "content-type": "application/json" }
|
|
6616
7922
|
};
|
|
6617
7923
|
}
|
|
6618
|
-
function queryString(
|
|
7924
|
+
function queryString(values2) {
|
|
6619
7925
|
const params = new URLSearchParams();
|
|
6620
|
-
for (const [key, value] of Object.entries(
|
|
7926
|
+
for (const [key, value] of Object.entries(values2)) {
|
|
6621
7927
|
if (value !== void 0) params.set(key, String(value));
|
|
6622
7928
|
}
|
|
6623
7929
|
const query = params.toString();
|
|
@@ -6653,8 +7959,8 @@ async function createApiError(response) {
|
|
|
6653
7959
|
});
|
|
6654
7960
|
}
|
|
6655
7961
|
function isSafeMethod(method) {
|
|
6656
|
-
const
|
|
6657
|
-
return
|
|
7962
|
+
const normalized2 = (method ?? "GET").toUpperCase();
|
|
7963
|
+
return normalized2 === "GET" || normalized2 === "HEAD" || normalized2 === "OPTIONS";
|
|
6658
7964
|
}
|
|
6659
7965
|
function shouldRetryStatus(status) {
|
|
6660
7966
|
return status === 408 || status === 409 || status === 429 || status >= 500;
|
|
@@ -6679,6 +7985,13 @@ var CatalogClient = class {
|
|
|
6679
7985
|
this.transport = transport;
|
|
6680
7986
|
}
|
|
6681
7987
|
transport;
|
|
7988
|
+
listPrices(signal) {
|
|
7989
|
+
return this.transport.json(
|
|
7990
|
+
"/catalog/prices",
|
|
7991
|
+
{ method: "GET", signal },
|
|
7992
|
+
{ retryable: true }
|
|
7993
|
+
);
|
|
7994
|
+
}
|
|
6682
7995
|
quote(request, signal) {
|
|
6683
7996
|
const spec = getModelSpec(request.modelId);
|
|
6684
7997
|
const schema = spec?.operations.find((operation) => operation.operation === request.operation)?.inputSchema ?? spec?.operations[0]?.inputSchema;
|
|
@@ -6707,6 +8020,84 @@ function deepFreeze(value) {
|
|
|
6707
8020
|
}
|
|
6708
8021
|
|
|
6709
8022
|
export {
|
|
8023
|
+
MEDIA_KINDS,
|
|
8024
|
+
modelUploadRegion,
|
|
8025
|
+
uploadedMediaUrl,
|
|
8026
|
+
uploadedMediaInput,
|
|
8027
|
+
USAGE_SOURCES,
|
|
8028
|
+
USAGE_NORMALIZATION_STATUSES,
|
|
8029
|
+
USAGE_RATING_STATUSES,
|
|
8030
|
+
USAGE_GROUP_BYS,
|
|
8031
|
+
USAGE_AMOUNT_KINDS,
|
|
8032
|
+
TOKEN_METRICS,
|
|
8033
|
+
MONEY_STRING_PATTERN,
|
|
8034
|
+
USAGE_FILTER_SELECTION_LIMIT,
|
|
8035
|
+
validateUsageFilters,
|
|
8036
|
+
validateUsageSummaryQuery,
|
|
8037
|
+
encodeUsageSummaryCursor,
|
|
8038
|
+
parseUsageSummaryCursor,
|
|
8039
|
+
encodeUsageKeysetCursor,
|
|
8040
|
+
parseUsageKeysetCursor,
|
|
8041
|
+
validateUsageDetailsQuery,
|
|
8042
|
+
USAGE_ANOMALY_CATEGORIES,
|
|
8043
|
+
validateUsageAnomaliesQuery,
|
|
8044
|
+
validateUsageAnomalySummaryQuery,
|
|
8045
|
+
ADMIN_USER_ROLES,
|
|
8046
|
+
ADMIN_USER_STATUSES,
|
|
8047
|
+
validateAdminUserListQuery,
|
|
8048
|
+
encodeAdminUserCursor,
|
|
8049
|
+
parseAdminUserCursor,
|
|
8050
|
+
ADMIN_USER_ACTIVITY_KINDS,
|
|
8051
|
+
isMoneyString,
|
|
8052
|
+
validateAdminUserUpdate,
|
|
8053
|
+
validateAdminUserApiKeyUpdate,
|
|
8054
|
+
validateAdminWalletRechargeInput,
|
|
8055
|
+
USAGE_FILTER_KINDS,
|
|
8056
|
+
encodeUsageFilterCursor,
|
|
8057
|
+
parseUsageFilterCursor,
|
|
8058
|
+
validateUsageFilterOptionsQuery,
|
|
8059
|
+
BILLING_CURRENCY,
|
|
8060
|
+
WALLET_MAX_BALANCE_UNITS,
|
|
8061
|
+
moneyToUnits,
|
|
8062
|
+
moneyFromUnits,
|
|
8063
|
+
multiplyMoney,
|
|
8064
|
+
normalizeModelParameterSchema,
|
|
8065
|
+
modelInputDefaults,
|
|
8066
|
+
orderedSchemaProperties,
|
|
8067
|
+
modelInputUi,
|
|
8068
|
+
BILLING_METRICS,
|
|
8069
|
+
BILLING_EXPORT_DIMENSIONS,
|
|
8070
|
+
allocateDiscountedPriceLines,
|
|
8071
|
+
validateNormalizedUsage,
|
|
8072
|
+
evaluatePriceRule,
|
|
8073
|
+
validatePriceRule,
|
|
8074
|
+
validateMeteringContract,
|
|
8075
|
+
assessUsageEvidence,
|
|
8076
|
+
TASK_STATUSES,
|
|
8077
|
+
taskReceipt,
|
|
8078
|
+
taskResult,
|
|
8079
|
+
isTerminalTaskStatus,
|
|
8080
|
+
defaultProbeInterval,
|
|
8081
|
+
defaultProbeTimeout,
|
|
8082
|
+
classifyObservation,
|
|
8083
|
+
availabilityStats,
|
|
8084
|
+
availabilityBuckets,
|
|
8085
|
+
rateProbeUsage,
|
|
8086
|
+
probeCostExceeds,
|
|
8087
|
+
SANDBOX_OPERATIONS,
|
|
8088
|
+
sandboxObject,
|
|
8089
|
+
sandboxIdentity,
|
|
8090
|
+
sandboxModelModes,
|
|
8091
|
+
sandboxOperations,
|
|
8092
|
+
sandboxProperties,
|
|
8093
|
+
sandboxSupports,
|
|
8094
|
+
sandboxVoiceKey,
|
|
8095
|
+
adaptSandboxInput,
|
|
8096
|
+
sandboxInputSchema,
|
|
8097
|
+
ratioDisplayOrderKey,
|
|
8098
|
+
compareRatioDisplayOrder,
|
|
8099
|
+
sortRatioDisplayOrder,
|
|
8100
|
+
orderSchemaRatioProperties,
|
|
6710
8101
|
NexraApiError,
|
|
6711
8102
|
NexraTaskError,
|
|
6712
8103
|
NexraWaitTimeoutError,
|