@shop-os/modelkit 0.7.3 → 0.7.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -6329,14 +6329,14 @@ function xaiReferenceMode(model, req) {
6329
6329
  const takesLastFrame = (model.constraints.supports ?? []).includes("lastFrame");
6330
6330
  return (req.referenceImages ?? []).length > 0 || takesLastFrame && req.lastFrame !== void 0;
6331
6331
  }
6332
- function applyXaiVideoRules(model, req, onUnsupported, warnings) {
6333
- if (model.adapter !== "xai-video" || req.resolution !== "1080p") return;
6334
- if (!xaiReferenceMode(model, req)) return;
6332
+ function xaiReferenceResolution(model, req, onUnsupported, warnings, provider) {
6333
+ if (req.resolution !== "1080p" || !xaiReferenceMode(model, req)) return void 0;
6335
6334
  const message = xaiReferenceResolutionMessage(model.id);
6336
6335
  if (onUnsupported === "error") {
6337
6336
  throw new ModelKitError({
6338
6337
  code: "unsupported_option",
6339
6338
  message,
6339
+ ...provider === void 0 ? {} : { provider },
6340
6340
  model: model.id,
6341
6341
  retryable: false
6342
6342
  });
@@ -6348,7 +6348,12 @@ function applyXaiVideoRules(model, req, onUnsupported, warnings) {
6348
6348
  to: XAI_REFERENCE_MAX_RESOLUTION,
6349
6349
  message
6350
6350
  });
6351
- req.resolution = XAI_REFERENCE_MAX_RESOLUTION;
6351
+ return XAI_REFERENCE_MAX_RESOLUTION;
6352
+ }
6353
+ function applyXaiVideoRules(model, req, onUnsupported, warnings) {
6354
+ if (model.adapter !== "xai-video") return;
6355
+ const lowered = xaiReferenceResolution(model, req, onUnsupported, warnings);
6356
+ if (lowered !== void 0) req.resolution = lowered;
6352
6357
  }
6353
6358
  function takesTargetAspectRatio(model) {
6354
6359
  const ratios = model.constraints.aspectRatios ?? [];
@@ -6549,6 +6554,161 @@ var MODEL3D_IMAGE_SLOTS = {
6549
6554
  ordered: ["image", "left", "back", "right"],
6550
6555
  unordered: ["image", "back", "left", "right", "top"]
6551
6556
  };
6557
+ var MODEL3D_FAMILY_RULES = {
6558
+ trellis: {
6559
+ textPath: false,
6560
+ views: ["none"],
6561
+ multiImage: false,
6562
+ texture: null,
6563
+ pbr: false,
6564
+ seed: true,
6565
+ textureRef: false,
6566
+ resolutions: "integer"
6567
+ },
6568
+ hunyuan: {
6569
+ textPath: true,
6570
+ views: ["none", "named"],
6571
+ multiImage: false,
6572
+ // generate_type
6573
+ texture: { none: "Geometry", standard: "Normal" },
6574
+ pbr: true,
6575
+ seed: false,
6576
+ textureRef: false,
6577
+ resolutions: null
6578
+ },
6579
+ tripo: {
6580
+ textPath: true,
6581
+ views: ["none", "ordered"],
6582
+ multiImage: true,
6583
+ // texture_quality; null sends an untextured model.
6584
+ texture: { none: null, standard: "standard", detailed: "detailed" },
6585
+ pbr: true,
6586
+ seed: true,
6587
+ textureRef: false,
6588
+ resolutions: null
6589
+ },
6590
+ rodin: {
6591
+ textPath: true,
6592
+ views: ["none", "unordered"],
6593
+ multiImage: false,
6594
+ texture: null,
6595
+ pbr: false,
6596
+ seed: true,
6597
+ textureRef: false,
6598
+ resolutions: null
6599
+ },
6600
+ meshy: {
6601
+ textPath: true,
6602
+ views: ["none", "unordered"],
6603
+ multiImage: true,
6604
+ // The text endpoint's mode; the image endpoints take should_texture.
6605
+ texture: { none: "preview", standard: "full" },
6606
+ pbr: true,
6607
+ seed: true,
6608
+ textureRef: true,
6609
+ resolutions: null
6610
+ },
6611
+ hi3d: {
6612
+ textPath: false,
6613
+ views: ["none", "named"],
6614
+ multiImage: true,
6615
+ // enable_texture
6616
+ texture: { none: false, standard: true },
6617
+ pbr: true,
6618
+ seed: false,
6619
+ textureRef: false,
6620
+ resolutions: { quality: "2048quality", master: "2048master" }
6621
+ },
6622
+ sam: {
6623
+ textPath: false,
6624
+ views: ["none"],
6625
+ multiImage: false,
6626
+ texture: null,
6627
+ pbr: false,
6628
+ seed: true,
6629
+ textureRef: false,
6630
+ resolutions: null
6631
+ }
6632
+ };
6633
+ function model3dSpecIssues(spec) {
6634
+ const issues = [];
6635
+ const add = (path, message) => issues.push({ path, message });
6636
+ const rules = MODEL3D_FAMILY_RULES[spec.family];
6637
+ const promptOnly = spec.text && !spec.imageRequired;
6638
+ if (spec.endpoints.image === void 0)
6639
+ add(["endpoints", "image"], "every row needs an image endpoint");
6640
+ if (promptOnly && !rules.textPath) {
6641
+ add(
6642
+ ["imageRequired"],
6643
+ `${spec.family} has no text-to-3D endpoint; a text row needs an image`
6644
+ );
6645
+ }
6646
+ if (promptOnly && spec.endpoints.text === void 0) {
6647
+ add(["endpoints", "text"], "a text row needs a text endpoint");
6648
+ }
6649
+ if (!rules.views.includes(spec.views)) {
6650
+ add(["views"], `${spec.family} takes views ${rules.views.join(" or ")}`);
6651
+ }
6652
+ if (spec.views === "none" && spec.maxImages !== 1) {
6653
+ add(["maxImages"], "a row without views takes 1 image");
6654
+ }
6655
+ if (spec.views === "unordered" && spec.maxImages < 2) {
6656
+ add(["maxImages"], "a row with views takes at least 2 images");
6657
+ }
6658
+ const slots = MODEL3D_IMAGE_SLOTS[spec.views].length;
6659
+ if (spec.views !== "none" && spec.maxImages > slots) {
6660
+ add(["maxImages"], `a row with ${spec.views} views sends at most ${slots} images`);
6661
+ }
6662
+ if ((spec.views === "named" || spec.views === "ordered") && spec.maxImages < slots) {
6663
+ add(
6664
+ ["maxImages"],
6665
+ `a row with ${spec.views} views takes ${slots} images (front and three sides)`
6666
+ );
6667
+ }
6668
+ if (spec.views !== "none" && rules.multiImage && spec.endpoints.multiImage === void 0) {
6669
+ add(["endpoints", "multiImage"], `${spec.family} sends views to a multi-image endpoint`);
6670
+ }
6671
+ if (rules.texture === null) {
6672
+ if (spec.texture.length > 0) add(["texture"], `${spec.family} has no texture switch`);
6673
+ } else {
6674
+ const allowed = rules.texture;
6675
+ if (spec.texture.length === 0) add(["texture"], `${spec.family} needs its texture options`);
6676
+ if (new Set(spec.texture).size !== spec.texture.length)
6677
+ add(["texture"], "texture options repeat");
6678
+ for (const t of spec.texture) {
6679
+ if (!Object.hasOwn(allowed, t))
6680
+ add(["texture"], `${spec.family} has no "${t}" texture`);
6681
+ }
6682
+ }
6683
+ if (spec.pbr && !rules.pbr) add(["pbr"], `${spec.family} has no PBR switch`);
6684
+ if (spec.pbr && !spec.texture.some((t) => t !== "none")) {
6685
+ add(["pbr"], "PBR needs a textured option");
6686
+ }
6687
+ if (spec.seed && !rules.seed) add(["seed"], `${spec.family} takes no seed`);
6688
+ if (spec.seedMax !== void 0 && !spec.seed) add(["seedMax"], "seedMax needs seed");
6689
+ if (spec.textureRef && !rules.textureRef)
6690
+ add(["textureRef"], `${spec.family} takes no texture reference`);
6691
+ const res = spec.resolutions;
6692
+ if (rules.resolutions === null) {
6693
+ if (res !== void 0) add(["resolutions"], `${spec.family} has no resolution option`);
6694
+ } else if (res === void 0) {
6695
+ add(["resolutions"], `${spec.family} needs its resolution options`);
6696
+ } else {
6697
+ if (!res.options.includes(res.default)) {
6698
+ add(["resolutions", "default"], "default must be an option");
6699
+ }
6700
+ if (new Set(res.options).size !== res.options.length) {
6701
+ add(["resolutions", "options"], "resolution options repeat");
6702
+ }
6703
+ const allowed = rules.resolutions;
6704
+ for (const option of res.options) {
6705
+ const ok = allowed === "integer" ? /^[1-9][0-9]*$/.test(option) : Object.hasOwn(allowed, option);
6706
+ if (!ok)
6707
+ add(["resolutions", "options"], `${spec.family} has no "${option}" resolution`);
6708
+ }
6709
+ }
6710
+ return issues;
6711
+ }
6552
6712
  function model3dInputRefusal(spec, wired) {
6553
6713
  const top = spec.views === "unordered" && wired.top === true;
6554
6714
  const anyView = spec.views !== "none" && (wired.back || wired.left || wired.right || top);
@@ -7136,156 +7296,6 @@ var LanguageOptionSchema = z3.looseObject({
7136
7296
  code: z3.string().min(1),
7137
7297
  name: z3.string().min(1)
7138
7298
  });
7139
- var MODEL3D_FAMILY_RULES = {
7140
- trellis: {
7141
- textPath: false,
7142
- views: ["none"],
7143
- multiImage: false,
7144
- texture: null,
7145
- pbr: false,
7146
- seed: true,
7147
- textureRef: false,
7148
- resolutions: "integer"
7149
- },
7150
- hunyuan: {
7151
- textPath: true,
7152
- views: ["none", "named"],
7153
- multiImage: false,
7154
- texture: ["none", "standard"],
7155
- pbr: true,
7156
- seed: false,
7157
- textureRef: false,
7158
- resolutions: null
7159
- },
7160
- tripo: {
7161
- textPath: true,
7162
- views: ["none", "ordered"],
7163
- multiImage: true,
7164
- texture: ["none", "standard", "detailed"],
7165
- pbr: true,
7166
- seed: true,
7167
- textureRef: false,
7168
- resolutions: null
7169
- },
7170
- rodin: {
7171
- textPath: true,
7172
- views: ["none", "unordered"],
7173
- multiImage: false,
7174
- texture: null,
7175
- pbr: false,
7176
- seed: true,
7177
- textureRef: false,
7178
- resolutions: null
7179
- },
7180
- meshy: {
7181
- textPath: true,
7182
- views: ["none", "unordered"],
7183
- multiImage: true,
7184
- texture: ["none", "standard"],
7185
- pbr: true,
7186
- seed: true,
7187
- textureRef: true,
7188
- resolutions: null
7189
- },
7190
- hi3d: {
7191
- textPath: false,
7192
- views: ["none", "named"],
7193
- multiImage: true,
7194
- texture: ["none", "standard"],
7195
- pbr: true,
7196
- seed: false,
7197
- textureRef: false,
7198
- resolutions: ["quality", "master"]
7199
- },
7200
- sam: {
7201
- textPath: false,
7202
- views: ["none"],
7203
- multiImage: false,
7204
- texture: null,
7205
- pbr: false,
7206
- seed: true,
7207
- textureRef: false,
7208
- resolutions: null
7209
- }
7210
- };
7211
- function model3dSpecIssues(spec) {
7212
- const issues = [];
7213
- const add = (path, message) => issues.push({ path, message });
7214
- const rules = MODEL3D_FAMILY_RULES[spec.family];
7215
- const promptOnly = spec.text && !spec.imageRequired;
7216
- if (spec.endpoints.image === void 0)
7217
- add(["endpoints", "image"], "every row needs an image endpoint");
7218
- if (promptOnly && !rules.textPath) {
7219
- add(
7220
- ["imageRequired"],
7221
- `${spec.family} has no text-to-3D endpoint; a text row needs an image`
7222
- );
7223
- }
7224
- if (promptOnly && spec.endpoints.text === void 0) {
7225
- add(["endpoints", "text"], "a text row needs a text endpoint");
7226
- }
7227
- if (!rules.views.includes(spec.views)) {
7228
- add(["views"], `${spec.family} takes views ${rules.views.join(" or ")}`);
7229
- }
7230
- if (spec.views === "none" && spec.maxImages !== 1) {
7231
- add(["maxImages"], "a row without views takes 1 image");
7232
- }
7233
- if (spec.views === "unordered" && spec.maxImages < 2) {
7234
- add(["maxImages"], "a row with views takes at least 2 images");
7235
- }
7236
- const slots = MODEL3D_IMAGE_SLOTS[spec.views].length;
7237
- if (spec.views !== "none" && spec.maxImages > slots) {
7238
- add(["maxImages"], `a row with ${spec.views} views sends at most ${slots} images`);
7239
- }
7240
- if ((spec.views === "named" || spec.views === "ordered") && spec.maxImages < slots) {
7241
- add(
7242
- ["maxImages"],
7243
- `a row with ${spec.views} views takes ${slots} images (front and three sides)`
7244
- );
7245
- }
7246
- if (spec.views !== "none" && rules.multiImage && spec.endpoints.multiImage === void 0) {
7247
- add(["endpoints", "multiImage"], `${spec.family} sends views to a multi-image endpoint`);
7248
- }
7249
- if (rules.texture === null) {
7250
- if (spec.texture.length > 0) add(["texture"], `${spec.family} has no texture switch`);
7251
- } else {
7252
- const allowed = rules.texture;
7253
- if (spec.texture.length === 0) add(["texture"], `${spec.family} needs its texture options`);
7254
- if (new Set(spec.texture).size !== spec.texture.length)
7255
- add(["texture"], "texture options repeat");
7256
- for (const t of spec.texture) {
7257
- if (!allowed.includes(t)) add(["texture"], `${spec.family} has no "${t}" texture`);
7258
- }
7259
- }
7260
- if (spec.pbr && !rules.pbr) add(["pbr"], `${spec.family} has no PBR switch`);
7261
- if (spec.pbr && !spec.texture.some((t) => t !== "none")) {
7262
- add(["pbr"], "PBR needs a textured option");
7263
- }
7264
- if (spec.seed && !rules.seed) add(["seed"], `${spec.family} takes no seed`);
7265
- if (spec.seedMax !== void 0 && !spec.seed) add(["seedMax"], "seedMax needs seed");
7266
- if (spec.textureRef && !rules.textureRef)
7267
- add(["textureRef"], `${spec.family} takes no texture reference`);
7268
- const res = spec.resolutions;
7269
- if (rules.resolutions === null) {
7270
- if (res !== void 0) add(["resolutions"], `${spec.family} has no resolution option`);
7271
- } else if (res === void 0) {
7272
- add(["resolutions"], `${spec.family} needs its resolution options`);
7273
- } else {
7274
- if (!res.options.includes(res.default)) {
7275
- add(["resolutions", "default"], "default must be an option");
7276
- }
7277
- if (new Set(res.options).size !== res.options.length) {
7278
- add(["resolutions", "options"], "resolution options repeat");
7279
- }
7280
- const allowed = rules.resolutions;
7281
- for (const option of res.options) {
7282
- const ok = allowed === "integer" ? /^[1-9][0-9]*$/.test(option) : allowed.includes(option);
7283
- if (!ok)
7284
- add(["resolutions", "options"], `${spec.family} has no "${option}" resolution`);
7285
- }
7286
- }
7287
- return issues;
7288
- }
7289
7299
  var VideoToolConstraintsSchema = z3.looseObject({
7290
7300
  kind: z3.enum(["upscale", "interpolate", "hdr", "bg-remove", "subtitles"]),
7291
7301
  upscaleFactor: RangeSchema.optional(),
@@ -10687,6 +10697,19 @@ function specOf(ctx) {
10687
10697
  return spec;
10688
10698
  }
10689
10699
  var present = (v) => v !== void 0 && v.length > 0;
10700
+ function wireValue(row2, values, option, what) {
10701
+ const value = option !== void 0 && Object.hasOwn(values, option) ? values[option] : void 0;
10702
+ if (value === void 0) {
10703
+ throw new ModelKitError({
10704
+ code: "unsupported_option",
10705
+ message: `${row2.id} has no ${what} "${option ?? ""}" to send`,
10706
+ provider: "fal",
10707
+ model: row2.id,
10708
+ retryable: false
10709
+ });
10710
+ }
10711
+ return value;
10712
+ }
10690
10713
  function model3dCall(row2, spec, req) {
10691
10714
  const prompt = req.prompt?.trim() || void 0;
10692
10715
  const texture = model3dTexture(spec, req.texture);
@@ -10730,7 +10753,15 @@ function model3dCall(row2, spec, req) {
10730
10753
  }
10731
10754
  };
10732
10755
  case "hunyuan": {
10733
- const opts = { generate_type: textured ? "Normal" : "Geometry", enable_pbr: pbr };
10756
+ const opts = {
10757
+ generate_type: wireValue(
10758
+ row2,
10759
+ MODEL3D_FAMILY_RULES.hunyuan.texture,
10760
+ texture,
10761
+ "texture"
10762
+ ),
10763
+ enable_pbr: pbr
10764
+ };
10734
10765
  if (!present(req.image)) {
10735
10766
  return {
10736
10767
  endpoint: endpoint(spec.endpoints.text),
@@ -10749,12 +10780,11 @@ function model3dCall(row2, spec, req) {
10749
10780
  };
10750
10781
  }
10751
10782
  case "tripo": {
10783
+ const quality = wireValue(row2, MODEL3D_FAMILY_RULES.tripo.texture, texture, "texture");
10752
10784
  const opts = {
10753
10785
  texture: textured,
10754
10786
  pbr,
10755
- ...textured && {
10756
- texture_quality: texture === "detailed" ? "detailed" : "standard"
10757
- },
10787
+ ...quality !== null && { texture_quality: quality },
10758
10788
  ...seed !== void 0 && { model_seed: seed }
10759
10789
  };
10760
10790
  if (!present(req.image)) {
@@ -10790,6 +10820,7 @@ function model3dCall(row2, spec, req) {
10790
10820
  };
10791
10821
  }
10792
10822
  case "meshy": {
10823
+ const mode = wireValue(row2, MODEL3D_FAMILY_RULES.meshy.texture, texture, "texture");
10793
10824
  const texturePrompt = req.texturePrompt?.trim() || void 0;
10794
10825
  const opts = {
10795
10826
  enable_pbr: pbr,
@@ -10801,7 +10832,7 @@ function model3dCall(row2, spec, req) {
10801
10832
  endpoint: endpoint(spec.endpoints.text),
10802
10833
  input: {
10803
10834
  prompt: prompt ?? "",
10804
- mode: textured ? "full" : "preview",
10835
+ mode,
10805
10836
  ...opts,
10806
10837
  ...seed !== void 0 && { seed }
10807
10838
  }
@@ -10817,8 +10848,18 @@ function model3dCall(row2, spec, req) {
10817
10848
  }
10818
10849
  case "hi3d": {
10819
10850
  const opts = {
10820
- resolution: resolution === "master" ? "2048master" : "2048quality",
10821
- enable_texture: textured,
10851
+ resolution: wireValue(
10852
+ row2,
10853
+ MODEL3D_FAMILY_RULES.hi3d.resolutions,
10854
+ resolution,
10855
+ "resolution"
10856
+ ),
10857
+ enable_texture: wireValue(
10858
+ row2,
10859
+ MODEL3D_FAMILY_RULES.hi3d.texture,
10860
+ texture,
10861
+ "texture"
10862
+ ),
10822
10863
  enable_pbr: pbr,
10823
10864
  export_format: "glb"
10824
10865
  };
@@ -15546,14 +15587,15 @@ async function generateXaiVideo(req, ctx, deps) {
15546
15587
  });
15547
15588
  }
15548
15589
  const refLimit = ctx.model.constraints.references?.images ?? SDK_REFERENCE_CAP;
15549
- const refUrls = (req.referenceImages ?? []).map(refToUrl).slice(0, refLimit);
15590
+ const refs = (req.referenceImages ?? []).slice(0, refLimit);
15591
+ const refUrls = refs.map(refToUrl);
15550
15592
  const takesLastFrame = (ctx.model.constraints.supports ?? []).includes("lastFrame");
15551
15593
  const lastFrame = takesLastFrame && req.lastFrame ? refToUrl(req.lastFrame) : void 0;
15552
15594
  const xaiOptions = {
15553
15595
  pollIntervalMs: POLL_INTERVAL_MS2,
15554
15596
  pollTimeoutMs: POLL_TIMEOUT_MS2
15555
15597
  };
15556
- const resolution = xaiResolution(req, ctx, refUrls.length > 0 || lastFrame !== void 0);
15598
+ const resolution = xaiResolution(req, ctx, refs);
15557
15599
  if (resolution !== void 0) xaiOptions.resolution = resolution;
15558
15600
  const sent = resolution === void 0 ? req : { ...req, resolution };
15559
15601
  if (refUrls.length > SDK_REFERENCE_CAP) {
@@ -15680,27 +15722,17 @@ function usage2(ctx, req, meta) {
15680
15722
  if (req.resolution !== void 0) event.resolution = req.resolution;
15681
15723
  return event;
15682
15724
  }
15683
- function xaiResolution(req, ctx, referenceMode) {
15725
+ function xaiResolution(req, ctx, sentRefs) {
15684
15726
  const requested = req.resolution;
15685
15727
  if (requested !== "480p" && requested !== "720p" && requested !== "1080p") return void 0;
15686
- if (!referenceMode || requested !== "1080p") return requested;
15687
- if ((ctx.call.onUnsupported ?? "error") === "error") {
15688
- throw new ModelKitError({
15689
- code: "unsupported_option",
15690
- message: xaiReferenceResolutionMessage(ctx.model.id),
15691
- provider: "xai-video",
15692
- model: ctx.model.id,
15693
- retryable: false
15694
- });
15695
- }
15696
- ctx.warnings.push({
15697
- code: "resolution_coerced",
15698
- field: "resolution",
15699
- from: requested,
15700
- to: XAI_REFERENCE_MAX_RESOLUTION,
15701
- message: xaiReferenceResolutionMessage(ctx.model.id)
15702
- });
15703
- return XAI_REFERENCE_MAX_RESOLUTION;
15728
+ const lowered = xaiReferenceResolution(
15729
+ ctx.model,
15730
+ { ...req, referenceImages: sentRefs },
15731
+ ctx.call.onUnsupported ?? "error",
15732
+ ctx.warnings,
15733
+ "xai-video"
15734
+ );
15735
+ return lowered ?? requested;
15704
15736
  }
15705
15737
 
15706
15738
  // src/adapters/index.ts