@ai-sdk/luma 3.0.0-beta.3 → 3.0.0-beta.31

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
@@ -1,46 +1,95 @@
1
- "use strict";
2
- var __defProp = Object.defineProperty;
3
- var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
- var __getOwnPropNames = Object.getOwnPropertyNames;
5
- var __hasOwnProp = Object.prototype.hasOwnProperty;
6
- var __export = (target, all) => {
7
- for (var name in all)
8
- __defProp(target, name, { get: all[name], enumerable: true });
9
- };
10
- var __copyProps = (to, from, except, desc) => {
11
- if (from && typeof from === "object" || typeof from === "function") {
12
- for (let key of __getOwnPropNames(from))
13
- if (!__hasOwnProp.call(to, key) && key !== except)
14
- __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
- }
16
- return to;
17
- };
18
- var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
1
+ // src/luma-provider.ts
2
+ import {
3
+ NoSuchModelError
4
+ } from "@ai-sdk/provider";
5
+ import {
6
+ loadApiKey,
7
+ withoutTrailingSlash,
8
+ withUserAgentSuffix
9
+ } from "@ai-sdk/provider-utils";
19
10
 
20
- // src/index.ts
21
- var index_exports = {};
22
- __export(index_exports, {
23
- VERSION: () => VERSION,
24
- createLuma: () => createLuma,
25
- luma: () => luma
26
- });
27
- module.exports = __toCommonJS(index_exports);
11
+ // src/luma-image-model.ts
12
+ import {
13
+ InvalidResponseDataError
14
+ } from "@ai-sdk/provider";
15
+ import {
16
+ combineHeaders,
17
+ createBinaryResponseHandler,
18
+ createJsonResponseHandler,
19
+ createJsonErrorResponseHandler,
20
+ createStatusCodeErrorResponseHandler,
21
+ delay,
22
+ getFromApi,
23
+ postJsonToApi,
24
+ lazySchema as lazySchema2,
25
+ parseProviderOptions,
26
+ zodSchema as zodSchema2,
27
+ serializeModelOptions,
28
+ WORKFLOW_SERIALIZE,
29
+ WORKFLOW_DESERIALIZE
30
+ } from "@ai-sdk/provider-utils";
28
31
 
29
- // src/luma-provider.ts
30
- var import_provider2 = require("@ai-sdk/provider");
31
- var import_provider_utils2 = require("@ai-sdk/provider-utils");
32
+ // src/luma-image-model-options.ts
33
+ import {
34
+ lazySchema,
35
+ zodSchema
36
+ } from "@ai-sdk/provider-utils";
37
+ import { z } from "zod/v4";
38
+ var lumaImageModelOptionsSchema = lazySchema(
39
+ () => zodSchema(
40
+ z.object({
41
+ /**
42
+ * The type of image reference to use when providing input images.
43
+ * - `image`: Guide generation using reference images (up to 4). Default.
44
+ * - `style`: Apply a specific style from reference image(s).
45
+ * - `character`: Create consistent characters from reference images (up to 4).
46
+ * - `modify_image`: Transform a single input image with prompt guidance.
47
+ */
48
+ referenceType: z.enum(["image", "style", "character", "modify_image"]).nullish(),
49
+ /**
50
+ * Per-image configuration array. Each entry corresponds to an image in `prompt.images`.
51
+ * Allows setting individual weights for each reference image.
52
+ */
53
+ images: z.array(
54
+ z.object({
55
+ /**
56
+ * The weight of this image's influence on the generation.
57
+ * - For `image`: Higher weight = closer to reference (default: 0.85)
58
+ * - For `style`: Higher weight = stronger style influence (default: 0.8)
59
+ * - For `modify_image`: Higher weight = closer to input, lower = more creative (default: 1.0)
60
+ */
61
+ weight: z.number().min(0).max(1).nullish(),
62
+ /**
63
+ * The identity name for character references.
64
+ * Used with `character` to specify which identity group the image belongs to.
65
+ * Luma supports multiple identities (e.g., 'identity0', 'identity1') for generating
66
+ * images with multiple consistent characters.
67
+ * Default: 'identity0'
68
+ */
69
+ id: z.string().nullish()
70
+ })
71
+ ).nullish(),
72
+ /**
73
+ * Override the polling interval in milliseconds (default 500).
74
+ */
75
+ pollIntervalMillis: z.number().nullish(),
76
+ /**
77
+ * Override the maximum number of polling attempts (default 120).
78
+ */
79
+ maxPollAttempts: z.number().nullish()
80
+ }).passthrough()
81
+ )
82
+ );
32
83
 
33
84
  // src/luma-image-model.ts
34
- var import_provider = require("@ai-sdk/provider");
35
- var import_provider_utils = require("@ai-sdk/provider-utils");
36
- var import_v4 = require("zod/v4");
85
+ import { z as z2 } from "zod/v4";
37
86
  var DEFAULT_POLL_INTERVAL_MILLIS = 500;
38
87
  var DEFAULT_MAX_POLL_ATTEMPTS = 6e4 / DEFAULT_POLL_INTERVAL_MILLIS;
39
- var LumaImageModel = class {
88
+ var LumaImageModel = class _LumaImageModel {
40
89
  constructor(modelId, config) {
41
90
  this.modelId = modelId;
42
91
  this.config = config;
43
- this.specificationVersion = "v3";
92
+ this.specificationVersion = "v4";
44
93
  this.maxImagesPerCall = 1;
45
94
  this.pollIntervalMillis = DEFAULT_POLL_INTERVAL_MILLIS;
46
95
  this.maxPollAttempts = DEFAULT_MAX_POLL_ATTEMPTS;
@@ -48,9 +97,17 @@ var LumaImageModel = class {
48
97
  get provider() {
49
98
  return this.config.provider;
50
99
  }
100
+ static [WORKFLOW_SERIALIZE](model) {
101
+ return serializeModelOptions({
102
+ modelId: model.modelId,
103
+ config: model.config
104
+ });
105
+ }
106
+ static [WORKFLOW_DESERIALIZE](options) {
107
+ return new _LumaImageModel(options.modelId, options.config);
108
+ }
51
109
  async doGenerate({
52
110
  prompt,
53
- n,
54
111
  size,
55
112
  aspectRatio,
56
113
  seed,
@@ -60,7 +117,7 @@ var LumaImageModel = class {
60
117
  files,
61
118
  mask
62
119
  }) {
63
- var _a, _b, _c;
120
+ var _a, _b, _c, _d, _e;
64
121
  const warnings = [];
65
122
  if (seed != null) {
66
123
  warnings.push({
@@ -76,7 +133,7 @@ var LumaImageModel = class {
76
133
  details: "This model does not support the `size` option. Use `aspectRatio` instead."
77
134
  });
78
135
  }
79
- const lumaOptions = await (0, import_provider_utils.parseProviderOptions)({
136
+ const lumaOptions = await parseProviderOptions({
80
137
  provider: "luma",
81
138
  providerOptions,
82
139
  schema: lumaImageModelOptionsSchema
@@ -95,8 +152,8 @@ var LumaImageModel = class {
95
152
  imageConfigs != null ? imageConfigs : []
96
153
  );
97
154
  const currentDate = (_c = (_b = (_a = this.config._internal) == null ? void 0 : _a.currentDate) == null ? void 0 : _b.call(_a)) != null ? _c : /* @__PURE__ */ new Date();
98
- const fullHeaders = (0, import_provider_utils.combineHeaders)(this.config.headers(), headers);
99
- const { value: generationResponse, responseHeaders } = await (0, import_provider_utils.postJsonToApi)({
155
+ const fullHeaders = combineHeaders((_e = (_d = this.config).headers) == null ? void 0 : _e.call(_d), headers);
156
+ const { value: generationResponse, responseHeaders } = await postJsonToApi({
100
157
  url: this.getLumaGenerationsUrl(),
101
158
  headers: fullHeaders,
102
159
  body: {
@@ -109,7 +166,7 @@ var LumaImageModel = class {
109
166
  abortSignal,
110
167
  fetch: this.config.fetch,
111
168
  failedResponseHandler: this.createLumaErrorHandler(),
112
- successfulResponseHandler: (0, import_provider_utils.createJsonResponseHandler)(
169
+ successfulResponseHandler: createJsonResponseHandler(
113
170
  lumaGenerationResponseSchema
114
171
  )
115
172
  });
@@ -139,39 +196,39 @@ var LumaImageModel = class {
139
196
  const maxPollAttempts = (_a = pollSettings == null ? void 0 : pollSettings.maxPollAttempts) != null ? _a : this.maxPollAttempts;
140
197
  const pollIntervalMillis = (_b = pollSettings == null ? void 0 : pollSettings.pollIntervalMillis) != null ? _b : this.pollIntervalMillis;
141
198
  for (let i = 0; i < maxPollAttempts; i++) {
142
- const { value: statusResponse } = await (0, import_provider_utils.getFromApi)({
199
+ const { value: statusResponse } = await getFromApi({
143
200
  url,
144
201
  headers,
145
202
  abortSignal,
146
203
  fetch: this.config.fetch,
147
204
  failedResponseHandler: this.createLumaErrorHandler(),
148
- successfulResponseHandler: (0, import_provider_utils.createJsonResponseHandler)(
205
+ successfulResponseHandler: createJsonResponseHandler(
149
206
  lumaGenerationResponseSchema
150
207
  )
151
208
  });
152
209
  switch (statusResponse.state) {
153
210
  case "completed":
154
211
  if (!((_c = statusResponse.assets) == null ? void 0 : _c.image)) {
155
- throw new import_provider.InvalidResponseDataError({
212
+ throw new InvalidResponseDataError({
156
213
  data: statusResponse,
157
214
  message: `Image generation completed but no image was found.`
158
215
  });
159
216
  }
160
217
  return statusResponse.assets.image;
161
218
  case "failed":
162
- throw new import_provider.InvalidResponseDataError({
219
+ throw new InvalidResponseDataError({
163
220
  data: statusResponse,
164
221
  message: `Image generation failed.`
165
222
  });
166
223
  }
167
- await (0, import_provider_utils.delay)(pollIntervalMillis);
224
+ await delay(pollIntervalMillis);
168
225
  }
169
226
  throw new Error(
170
227
  `Image generation timed out after ${this.maxPollAttempts} attempts.`
171
228
  );
172
229
  }
173
230
  createLumaErrorHandler() {
174
- return (0, import_provider_utils.createJsonErrorResponseHandler)({
231
+ return createJsonErrorResponseHandler({
175
232
  errorSchema: lumaErrorSchema,
176
233
  errorToMessage: (error) => {
177
234
  var _a;
@@ -271,101 +328,56 @@ var LumaImageModel = class {
271
328
  return `${this.config.baseURL}/dream-machine/v1/generations/${generationId != null ? generationId : "image"}`;
272
329
  }
273
330
  async downloadImage(url, abortSignal) {
274
- const { value: response } = await (0, import_provider_utils.getFromApi)({
331
+ const { value: response } = await getFromApi({
275
332
  url,
276
333
  // No specific headers should be needed for this request as it's a
277
334
  // generated image provided by Luma.
278
335
  abortSignal,
279
- failedResponseHandler: (0, import_provider_utils.createStatusCodeErrorResponseHandler)(),
280
- successfulResponseHandler: (0, import_provider_utils.createBinaryResponseHandler)(),
336
+ failedResponseHandler: createStatusCodeErrorResponseHandler(),
337
+ successfulResponseHandler: createBinaryResponseHandler(),
281
338
  fetch: this.config.fetch
282
339
  });
283
340
  return response;
284
341
  }
285
342
  };
286
- var lumaGenerationResponseSchema = (0, import_provider_utils.lazySchema)(
287
- () => (0, import_provider_utils.zodSchema)(
288
- import_v4.z.object({
289
- id: import_v4.z.string(),
290
- state: import_v4.z.enum(["queued", "dreaming", "completed", "failed"]),
291
- failure_reason: import_v4.z.string().nullish(),
292
- assets: import_v4.z.object({
293
- image: import_v4.z.string()
343
+ var lumaGenerationResponseSchema = lazySchema2(
344
+ () => zodSchema2(
345
+ z2.object({
346
+ id: z2.string(),
347
+ state: z2.enum(["queued", "dreaming", "completed", "failed"]),
348
+ failure_reason: z2.string().nullish(),
349
+ assets: z2.object({
350
+ image: z2.string()
294
351
  // URL of the generated image
295
352
  }).nullish()
296
353
  })
297
354
  )
298
355
  );
299
- var lumaErrorSchema = import_v4.z.object({
300
- detail: import_v4.z.array(
301
- import_v4.z.object({
302
- type: import_v4.z.string(),
303
- loc: import_v4.z.array(import_v4.z.string()),
304
- msg: import_v4.z.string(),
305
- input: import_v4.z.string(),
306
- ctx: import_v4.z.object({
307
- expected: import_v4.z.string()
356
+ var lumaErrorSchema = z2.object({
357
+ detail: z2.array(
358
+ z2.object({
359
+ type: z2.string(),
360
+ loc: z2.array(z2.string()),
361
+ msg: z2.string(),
362
+ input: z2.string(),
363
+ ctx: z2.object({
364
+ expected: z2.string()
308
365
  }).nullish()
309
366
  })
310
367
  )
311
368
  });
312
- var lumaImageModelOptionsSchema = (0, import_provider_utils.lazySchema)(
313
- () => (0, import_provider_utils.zodSchema)(
314
- import_v4.z.object({
315
- /**
316
- * The type of image reference to use when providing input images.
317
- * - `image`: Guide generation using reference images (up to 4). Default.
318
- * - `style`: Apply a specific style from reference image(s).
319
- * - `character`: Create consistent characters from reference images (up to 4).
320
- * - `modify_image`: Transform a single input image with prompt guidance.
321
- */
322
- referenceType: import_v4.z.enum(["image", "style", "character", "modify_image"]).nullish(),
323
- /**
324
- * Per-image configuration array. Each entry corresponds to an image in `prompt.images`.
325
- * Allows setting individual weights for each reference image.
326
- */
327
- images: import_v4.z.array(
328
- import_v4.z.object({
329
- /**
330
- * The weight of this image's influence on the generation.
331
- * - For `image`: Higher weight = closer to reference (default: 0.85)
332
- * - For `style`: Higher weight = stronger style influence (default: 0.8)
333
- * - For `modify_image`: Higher weight = closer to input, lower = more creative (default: 1.0)
334
- */
335
- weight: import_v4.z.number().min(0).max(1).nullish(),
336
- /**
337
- * The identity name for character references.
338
- * Used with `character` to specify which identity group the image belongs to.
339
- * Luma supports multiple identities (e.g., 'identity0', 'identity1') for generating
340
- * images with multiple consistent characters.
341
- * Default: 'identity0'
342
- */
343
- id: import_v4.z.string().nullish()
344
- })
345
- ).nullish(),
346
- /**
347
- * Override the polling interval in milliseconds (default 500).
348
- */
349
- pollIntervalMillis: import_v4.z.number().nullish(),
350
- /**
351
- * Override the maximum number of polling attempts (default 120).
352
- */
353
- maxPollAttempts: import_v4.z.number().nullish()
354
- }).passthrough()
355
- )
356
- );
357
369
 
358
370
  // src/version.ts
359
- var VERSION = true ? "3.0.0-beta.3" : "0.0.0-test";
371
+ var VERSION = true ? "3.0.0-beta.31" : "0.0.0-test";
360
372
 
361
373
  // src/luma-provider.ts
362
374
  var defaultBaseURL = "https://api.lumalabs.ai";
363
375
  function createLuma(options = {}) {
364
376
  var _a;
365
- const baseURL = (0, import_provider_utils2.withoutTrailingSlash)((_a = options.baseURL) != null ? _a : defaultBaseURL);
366
- const getHeaders = () => (0, import_provider_utils2.withUserAgentSuffix)(
377
+ const baseURL = withoutTrailingSlash((_a = options.baseURL) != null ? _a : defaultBaseURL);
378
+ const getHeaders = () => withUserAgentSuffix(
367
379
  {
368
- Authorization: `Bearer ${(0, import_provider_utils2.loadApiKey)({
380
+ Authorization: `Bearer ${loadApiKey({
369
381
  apiKey: options.apiKey,
370
382
  environmentVariableName: "LUMA_API_KEY",
371
383
  description: "Luma"
@@ -381,17 +393,17 @@ function createLuma(options = {}) {
381
393
  fetch: options.fetch
382
394
  });
383
395
  const embeddingModel = (modelId) => {
384
- throw new import_provider2.NoSuchModelError({
396
+ throw new NoSuchModelError({
385
397
  modelId,
386
398
  modelType: "embeddingModel"
387
399
  });
388
400
  };
389
401
  return {
390
- specificationVersion: "v3",
402
+ specificationVersion: "v4",
391
403
  image: createImageModel,
392
404
  imageModel: createImageModel,
393
405
  languageModel: (modelId) => {
394
- throw new import_provider2.NoSuchModelError({
406
+ throw new NoSuchModelError({
395
407
  modelId,
396
408
  modelType: "languageModel"
397
409
  });
@@ -401,10 +413,9 @@ function createLuma(options = {}) {
401
413
  };
402
414
  }
403
415
  var luma = createLuma();
404
- // Annotate the CommonJS export names for ESM import in node:
405
- 0 && (module.exports = {
416
+ export {
406
417
  VERSION,
407
418
  createLuma,
408
419
  luma
409
- });
420
+ };
410
421
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/luma-provider.ts","../src/luma-image-model.ts","../src/version.ts"],"sourcesContent":["export { createLuma, luma } from './luma-provider';\nexport type { LumaProvider, LumaProviderSettings } from './luma-provider';\nexport type {\n LumaErrorData,\n LumaImageModelOptions,\n /** @deprecated Use `LumaImageModelOptions` instead. */\n LumaImageModelOptions as LumaImageProviderOptions,\n} from './luma-image-model';\nexport { VERSION } from './version';\n","import { ImageModelV3, NoSuchModelError, ProviderV3 } from '@ai-sdk/provider';\nimport {\n FetchFunction,\n loadApiKey,\n withoutTrailingSlash,\n withUserAgentSuffix,\n} from '@ai-sdk/provider-utils';\nimport { LumaImageModel } from './luma-image-model';\nimport { LumaImageModelId } from './luma-image-settings';\nimport { VERSION } from './version';\n\nexport interface LumaProviderSettings {\n /**\n * Luma API key. Default value is taken from the `LUMA_API_KEY` environment\n * variable.\n */\n apiKey?: string;\n /**\n * Base URL for the API calls.\n */\n baseURL?: string;\n /**\n * Custom headers to include in the requests.\n */\n headers?: Record<string, string>;\n /**\n * Custom fetch implementation. You can use it as a middleware to intercept requests,\n * or to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n}\n\nexport interface LumaProvider extends ProviderV3 {\n /**\n * Creates a model for image generation.\n */\n image(modelId: LumaImageModelId): ImageModelV3;\n\n /**\n * Creates a model for image generation.\n */\n imageModel(modelId: LumaImageModelId): ImageModelV3;\n\n /**\n * @deprecated Use `embeddingModel` instead.\n */\n textEmbeddingModel(modelId: string): never;\n}\n\nconst defaultBaseURL = 'https://api.lumalabs.ai';\n\nexport function createLuma(options: LumaProviderSettings = {}): LumaProvider {\n const baseURL = withoutTrailingSlash(options.baseURL ?? defaultBaseURL);\n const getHeaders = () =>\n withUserAgentSuffix(\n {\n Authorization: `Bearer ${loadApiKey({\n apiKey: options.apiKey,\n environmentVariableName: 'LUMA_API_KEY',\n description: 'Luma',\n })}`,\n ...options.headers,\n },\n `ai-sdk/luma/${VERSION}`,\n );\n\n const createImageModel = (modelId: LumaImageModelId) =>\n new LumaImageModel(modelId, {\n provider: 'luma.image',\n baseURL: baseURL ?? defaultBaseURL,\n headers: getHeaders,\n fetch: options.fetch,\n });\n\n const embeddingModel = (modelId: string) => {\n throw new NoSuchModelError({\n modelId,\n modelType: 'embeddingModel',\n });\n };\n\n return {\n specificationVersion: 'v3' as const,\n image: createImageModel,\n imageModel: createImageModel,\n languageModel: (modelId: string) => {\n throw new NoSuchModelError({\n modelId,\n modelType: 'languageModel',\n });\n },\n embeddingModel,\n textEmbeddingModel: embeddingModel,\n };\n}\n\nexport const luma = createLuma();\n","import {\n ImageModelV3,\n ImageModelV3File,\n SharedV3Warning,\n InvalidResponseDataError,\n} from '@ai-sdk/provider';\nimport {\n FetchFunction,\n combineHeaders,\n createBinaryResponseHandler,\n createJsonResponseHandler,\n createJsonErrorResponseHandler,\n createStatusCodeErrorResponseHandler,\n delay,\n getFromApi,\n postJsonToApi,\n InferSchema,\n lazySchema,\n parseProviderOptions,\n zodSchema,\n} from '@ai-sdk/provider-utils';\nimport { LumaImageSettings, LumaReferenceType } from './luma-image-settings';\nimport { z } from 'zod/v4';\n\nconst DEFAULT_POLL_INTERVAL_MILLIS = 500;\nconst DEFAULT_MAX_POLL_ATTEMPTS = 60000 / DEFAULT_POLL_INTERVAL_MILLIS;\n\ninterface LumaImageModelConfig {\n provider: string;\n baseURL: string;\n headers: () => Record<string, string>;\n fetch?: FetchFunction;\n _internal?: {\n currentDate?: () => Date;\n };\n}\n\nexport class LumaImageModel implements ImageModelV3 {\n readonly specificationVersion = 'v3';\n readonly maxImagesPerCall = 1;\n readonly pollIntervalMillis = DEFAULT_POLL_INTERVAL_MILLIS;\n readonly maxPollAttempts = DEFAULT_MAX_POLL_ATTEMPTS;\n\n get provider(): string {\n return this.config.provider;\n }\n\n constructor(\n readonly modelId: string,\n private readonly config: LumaImageModelConfig,\n ) {}\n\n async doGenerate({\n prompt,\n n,\n size,\n aspectRatio,\n seed,\n providerOptions,\n headers,\n abortSignal,\n files,\n mask,\n }: Parameters<ImageModelV3['doGenerate']>[0]): Promise<\n Awaited<ReturnType<ImageModelV3['doGenerate']>>\n > {\n const warnings: Array<SharedV3Warning> = [];\n\n if (seed != null) {\n warnings.push({\n type: 'unsupported',\n feature: 'seed',\n details: 'This model does not support the `seed` option.',\n });\n }\n\n if (size != null) {\n warnings.push({\n type: 'unsupported',\n feature: 'size',\n details:\n 'This model does not support the `size` option. Use `aspectRatio` instead.',\n });\n }\n\n // Parse and validate provider options\n const lumaOptions = await parseProviderOptions({\n provider: 'luma',\n providerOptions,\n schema: lumaImageModelOptionsSchema,\n });\n\n // Extract non-request options\n const {\n pollIntervalMillis,\n maxPollAttempts,\n referenceType,\n images: imageConfigs,\n ...providerRequestOptions\n } = lumaOptions ?? {};\n\n // Handle image editing via files with reference type support\n const editingOptions = this.getEditingOptions(\n files,\n mask,\n referenceType ?? undefined,\n imageConfigs ?? [],\n );\n\n const currentDate = this.config._internal?.currentDate?.() ?? new Date();\n const fullHeaders = combineHeaders(this.config.headers(), headers);\n const { value: generationResponse, responseHeaders } = await postJsonToApi({\n url: this.getLumaGenerationsUrl(),\n headers: fullHeaders,\n body: {\n prompt,\n ...(aspectRatio ? { aspect_ratio: aspectRatio } : {}),\n model: this.modelId,\n ...editingOptions,\n ...providerRequestOptions,\n },\n abortSignal,\n fetch: this.config.fetch,\n failedResponseHandler: this.createLumaErrorHandler(),\n successfulResponseHandler: createJsonResponseHandler(\n lumaGenerationResponseSchema,\n ),\n });\n\n const imageUrl = await this.pollForImageUrl(\n generationResponse.id,\n fullHeaders,\n abortSignal,\n {\n pollIntervalMillis: pollIntervalMillis ?? undefined,\n maxPollAttempts: maxPollAttempts ?? undefined,\n },\n );\n\n const downloadedImage = await this.downloadImage(imageUrl, abortSignal);\n\n return {\n images: [downloadedImage],\n warnings,\n response: {\n modelId: this.modelId,\n timestamp: currentDate,\n headers: responseHeaders,\n },\n };\n }\n\n private async pollForImageUrl(\n generationId: string,\n headers: Record<string, string | undefined>,\n abortSignal: AbortSignal | undefined,\n pollSettings?: { pollIntervalMillis?: number; maxPollAttempts?: number },\n ): Promise<string> {\n const url = this.getLumaGenerationsUrl(generationId);\n const maxPollAttempts =\n pollSettings?.maxPollAttempts ?? this.maxPollAttempts;\n const pollIntervalMillis =\n pollSettings?.pollIntervalMillis ?? this.pollIntervalMillis;\n\n for (let i = 0; i < maxPollAttempts; i++) {\n const { value: statusResponse } = await getFromApi({\n url,\n headers,\n abortSignal,\n fetch: this.config.fetch,\n failedResponseHandler: this.createLumaErrorHandler(),\n successfulResponseHandler: createJsonResponseHandler(\n lumaGenerationResponseSchema,\n ),\n });\n\n switch (statusResponse.state) {\n case 'completed':\n if (!statusResponse.assets?.image) {\n throw new InvalidResponseDataError({\n data: statusResponse,\n message: `Image generation completed but no image was found.`,\n });\n }\n return statusResponse.assets.image;\n case 'failed':\n throw new InvalidResponseDataError({\n data: statusResponse,\n message: `Image generation failed.`,\n });\n }\n await delay(pollIntervalMillis);\n }\n\n throw new Error(\n `Image generation timed out after ${this.maxPollAttempts} attempts.`,\n );\n }\n\n private createLumaErrorHandler() {\n return createJsonErrorResponseHandler({\n errorSchema: lumaErrorSchema,\n errorToMessage: (error: LumaErrorData) =>\n error.detail[0].msg ?? 'Unknown error',\n });\n }\n\n private getEditingOptions(\n files: ImageModelV3File[] | undefined,\n mask: ImageModelV3File | undefined,\n referenceType: LumaReferenceType = 'image',\n imageConfigs: Array<{ weight?: number | null; id?: string | null }> = [],\n ): Record<string, unknown> {\n const options: Record<string, unknown> = {};\n\n // Luma does not support mask-based inpainting\n if (mask != null) {\n throw new Error(\n 'Luma AI does not support mask-based image editing. ' +\n 'Use the prompt to describe the changes you want to make, along with ' +\n '`prompt.images` containing the source image URL.',\n );\n }\n\n if (files == null || files.length === 0) {\n return options;\n }\n\n // Validate all files are URL-based\n for (const file of files) {\n if (file.type !== 'url') {\n throw new Error(\n 'Luma AI only supports URL-based images. ' +\n 'Please provide image URLs using `prompt.images` with publicly accessible URLs. ' +\n 'Base64 and Uint8Array data are not supported.',\n );\n }\n }\n\n // Default weights per reference type\n const defaultWeights: Record<LumaReferenceType, number> = {\n image: 0.85,\n style: 0.8,\n character: 1.0, // Not used, but defined for completeness\n modify_image: 1.0,\n };\n\n switch (referenceType) {\n case 'image': {\n // Supports up to 4 images\n if (files.length > 4) {\n throw new Error(\n 'Luma AI image supports up to 4 reference images. ' +\n `You provided ${files.length} images.`,\n );\n }\n options.image = files.map((file, index) => ({\n url: (file as { type: 'url'; url: string }).url,\n weight: imageConfigs[index]?.weight ?? defaultWeights.image,\n }));\n break;\n }\n\n case 'style': {\n // Style ref accepts an array but typically uses one style image\n options.style = files.map((file, index) => ({\n url: (file as { type: 'url'; url: string }).url,\n weight: imageConfigs[index]?.weight ?? defaultWeights.style,\n }));\n break;\n }\n\n case 'character': {\n // Group images by identity id\n const identities: Record<string, string[]> = {};\n for (let i = 0; i < files.length; i++) {\n const file = files[i] as { type: 'url'; url: string };\n const identityId = imageConfigs[i]?.id ?? 'identity0';\n if (!identities[identityId]) {\n identities[identityId] = [];\n }\n identities[identityId].push(file.url);\n }\n\n // Validate each identity has at most 4 images\n for (const [identityId, images] of Object.entries(identities)) {\n if (images.length > 4) {\n throw new Error(\n `Luma AI character supports up to 4 images per identity. ` +\n `Identity '${identityId}' has ${images.length} images.`,\n );\n }\n }\n\n options.character = Object.fromEntries(\n Object.entries(identities).map(([id, images]) => [id, { images }]),\n );\n break;\n }\n\n case 'modify_image': {\n // Only supports a single image\n if (files.length > 1) {\n throw new Error(\n 'Luma AI modify_image only supports a single input image. ' +\n `You provided ${files.length} images.`,\n );\n }\n options.modify_image = {\n url: (files[0] as { type: 'url'; url: string }).url,\n weight: imageConfigs[0]?.weight ?? defaultWeights.modify_image,\n };\n break;\n }\n }\n\n return options;\n }\n\n private getLumaGenerationsUrl(generationId?: string) {\n return `${this.config.baseURL}/dream-machine/v1/generations/${\n generationId ?? 'image'\n }`;\n }\n\n private async downloadImage(\n url: string,\n abortSignal: AbortSignal | undefined,\n ): Promise<Uint8Array> {\n const { value: response } = await getFromApi({\n url,\n // No specific headers should be needed for this request as it's a\n // generated image provided by Luma.\n abortSignal,\n failedResponseHandler: createStatusCodeErrorResponseHandler(),\n successfulResponseHandler: createBinaryResponseHandler(),\n fetch: this.config.fetch,\n });\n return response;\n }\n}\n\n// limited version of the schema, focussed on what is needed for the implementation\n// this approach limits breakages when the API changes and increases efficiency\nconst lumaGenerationResponseSchema = lazySchema(() =>\n zodSchema(\n z.object({\n id: z.string(),\n state: z.enum(['queued', 'dreaming', 'completed', 'failed']),\n failure_reason: z.string().nullish(),\n assets: z\n .object({\n image: z.string(), // URL of the generated image\n })\n .nullish(),\n }),\n ),\n);\n\nconst lumaErrorSchema = z.object({\n detail: z.array(\n z.object({\n type: z.string(),\n loc: z.array(z.string()),\n msg: z.string(),\n input: z.string(),\n ctx: z\n .object({\n expected: z.string(),\n })\n .nullish(),\n }),\n ),\n});\n\nexport type LumaErrorData = z.infer<typeof lumaErrorSchema>;\n\n/**\n * Provider options schema for Luma image generation.\n *\n * @see https://docs.lumalabs.ai/docs/image-generation\n */\nexport const lumaImageModelOptionsSchema = lazySchema(() =>\n zodSchema(\n z\n .object({\n /**\n * The type of image reference to use when providing input images.\n * - `image`: Guide generation using reference images (up to 4). Default.\n * - `style`: Apply a specific style from reference image(s).\n * - `character`: Create consistent characters from reference images (up to 4).\n * - `modify_image`: Transform a single input image with prompt guidance.\n */\n referenceType: z\n .enum(['image', 'style', 'character', 'modify_image'])\n .nullish(),\n\n /**\n * Per-image configuration array. Each entry corresponds to an image in `prompt.images`.\n * Allows setting individual weights for each reference image.\n */\n images: z\n .array(\n z.object({\n /**\n * The weight of this image's influence on the generation.\n * - For `image`: Higher weight = closer to reference (default: 0.85)\n * - For `style`: Higher weight = stronger style influence (default: 0.8)\n * - For `modify_image`: Higher weight = closer to input, lower = more creative (default: 1.0)\n */\n weight: z.number().min(0).max(1).nullish(),\n\n /**\n * The identity name for character references.\n * Used with `character` to specify which identity group the image belongs to.\n * Luma supports multiple identities (e.g., 'identity0', 'identity1') for generating\n * images with multiple consistent characters.\n * Default: 'identity0'\n */\n id: z.string().nullish(),\n }),\n )\n .nullish(),\n\n /**\n * Override the polling interval in milliseconds (default 500).\n */\n pollIntervalMillis: z.number().nullish(),\n\n /**\n * Override the maximum number of polling attempts (default 120).\n */\n maxPollAttempts: z.number().nullish(),\n })\n .passthrough(),\n ),\n);\n\nexport type LumaImageModelOptions = InferSchema<\n typeof lumaImageModelOptionsSchema\n>;\n","// Version string of this package injected at build time.\ndeclare const __PACKAGE_VERSION__: string | undefined;\nexport const VERSION: string =\n typeof __PACKAGE_VERSION__ !== 'undefined'\n ? __PACKAGE_VERSION__\n : '0.0.0-test';\n"],"mappings":"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","names":["import_provider","import_provider_utils","_a","_b"]}
1
+ {"version":3,"sources":["../src/luma-provider.ts","../src/luma-image-model.ts","../src/luma-image-model-options.ts","../src/version.ts"],"sourcesContent":["import {\n NoSuchModelError,\n type ImageModelV4,\n type ProviderV4,\n} from '@ai-sdk/provider';\nimport {\n loadApiKey,\n withoutTrailingSlash,\n withUserAgentSuffix,\n type FetchFunction,\n} from '@ai-sdk/provider-utils';\nimport { LumaImageModel } from './luma-image-model';\nimport type { LumaImageModelId } from './luma-image-settings';\nimport { VERSION } from './version';\n\nexport interface LumaProviderSettings {\n /**\n * Luma API key. Default value is taken from the `LUMA_API_KEY` environment\n * variable.\n */\n apiKey?: string;\n /**\n * Base URL for the API calls.\n */\n baseURL?: string;\n /**\n * Custom headers to include in the requests.\n */\n headers?: Record<string, string>;\n /**\n * Custom fetch implementation. You can use it as a middleware to intercept requests,\n * or to provide a custom fetch implementation for e.g. testing.\n */\n fetch?: FetchFunction;\n}\n\nexport interface LumaProvider extends ProviderV4 {\n /**\n * Creates a model for image generation.\n */\n image(modelId: LumaImageModelId): ImageModelV4;\n\n /**\n * Creates a model for image generation.\n */\n imageModel(modelId: LumaImageModelId): ImageModelV4;\n\n /**\n * @deprecated Use `embeddingModel` instead.\n */\n textEmbeddingModel(modelId: string): never;\n}\n\nconst defaultBaseURL = 'https://api.lumalabs.ai';\n\nexport function createLuma(options: LumaProviderSettings = {}): LumaProvider {\n const baseURL = withoutTrailingSlash(options.baseURL ?? defaultBaseURL);\n const getHeaders = () =>\n withUserAgentSuffix(\n {\n Authorization: `Bearer ${loadApiKey({\n apiKey: options.apiKey,\n environmentVariableName: 'LUMA_API_KEY',\n description: 'Luma',\n })}`,\n ...options.headers,\n },\n `ai-sdk/luma/${VERSION}`,\n );\n\n const createImageModel = (modelId: LumaImageModelId) =>\n new LumaImageModel(modelId, {\n provider: 'luma.image',\n baseURL: baseURL ?? defaultBaseURL,\n headers: getHeaders,\n fetch: options.fetch,\n });\n\n const embeddingModel = (modelId: string) => {\n throw new NoSuchModelError({\n modelId,\n modelType: 'embeddingModel',\n });\n };\n\n return {\n specificationVersion: 'v4' as const,\n image: createImageModel,\n imageModel: createImageModel,\n languageModel: (modelId: string) => {\n throw new NoSuchModelError({\n modelId,\n modelType: 'languageModel',\n });\n },\n embeddingModel,\n textEmbeddingModel: embeddingModel,\n };\n}\n\nexport const luma = createLuma();\n","import {\n InvalidResponseDataError,\n type ImageModelV4,\n type ImageModelV4File,\n type SharedV4Warning,\n} from '@ai-sdk/provider';\nimport {\n combineHeaders,\n createBinaryResponseHandler,\n createJsonResponseHandler,\n createJsonErrorResponseHandler,\n createStatusCodeErrorResponseHandler,\n delay,\n getFromApi,\n postJsonToApi,\n lazySchema,\n parseProviderOptions,\n zodSchema,\n serializeModelOptions,\n WORKFLOW_SERIALIZE,\n WORKFLOW_DESERIALIZE,\n type FetchFunction,\n} from '@ai-sdk/provider-utils';\nimport { lumaImageModelOptionsSchema } from './luma-image-model-options';\nimport type { LumaReferenceType } from './luma-image-settings';\nimport { z } from 'zod/v4';\n\nconst DEFAULT_POLL_INTERVAL_MILLIS = 500;\nconst DEFAULT_MAX_POLL_ATTEMPTS = 60000 / DEFAULT_POLL_INTERVAL_MILLIS;\n\ninterface LumaImageModelConfig {\n provider: string;\n baseURL: string;\n headers?: () => Record<string, string>;\n fetch?: FetchFunction;\n _internal?: {\n currentDate?: () => Date;\n };\n}\n\nexport class LumaImageModel implements ImageModelV4 {\n readonly specificationVersion = 'v4';\n readonly maxImagesPerCall = 1;\n readonly pollIntervalMillis = DEFAULT_POLL_INTERVAL_MILLIS;\n readonly maxPollAttempts = DEFAULT_MAX_POLL_ATTEMPTS;\n\n get provider(): string {\n return this.config.provider;\n }\n\n static [WORKFLOW_SERIALIZE](model: LumaImageModel) {\n return serializeModelOptions({\n modelId: model.modelId,\n config: model.config,\n });\n }\n\n static [WORKFLOW_DESERIALIZE](options: {\n modelId: string;\n config: LumaImageModelConfig;\n }) {\n return new LumaImageModel(options.modelId, options.config);\n }\n\n constructor(\n readonly modelId: string,\n private readonly config: LumaImageModelConfig,\n ) {}\n\n async doGenerate({\n prompt,\n size,\n aspectRatio,\n seed,\n providerOptions,\n headers,\n abortSignal,\n files,\n mask,\n }: Parameters<ImageModelV4['doGenerate']>[0]): Promise<\n Awaited<ReturnType<ImageModelV4['doGenerate']>>\n > {\n const warnings: Array<SharedV4Warning> = [];\n\n if (seed != null) {\n warnings.push({\n type: 'unsupported',\n feature: 'seed',\n details: 'This model does not support the `seed` option.',\n });\n }\n\n if (size != null) {\n warnings.push({\n type: 'unsupported',\n feature: 'size',\n details:\n 'This model does not support the `size` option. Use `aspectRatio` instead.',\n });\n }\n\n // Parse and validate provider options\n const lumaOptions = await parseProviderOptions({\n provider: 'luma',\n providerOptions,\n schema: lumaImageModelOptionsSchema,\n });\n\n // Extract non-request options\n const {\n pollIntervalMillis,\n maxPollAttempts,\n referenceType,\n images: imageConfigs,\n ...providerRequestOptions\n } = lumaOptions ?? {};\n\n // Handle image editing via files with reference type support\n const editingOptions = this.getEditingOptions(\n files,\n mask,\n referenceType ?? undefined,\n imageConfigs ?? [],\n );\n\n const currentDate = this.config._internal?.currentDate?.() ?? new Date();\n const fullHeaders = combineHeaders(this.config.headers?.(), headers);\n const { value: generationResponse, responseHeaders } = await postJsonToApi({\n url: this.getLumaGenerationsUrl(),\n headers: fullHeaders,\n body: {\n prompt,\n ...(aspectRatio ? { aspect_ratio: aspectRatio } : {}),\n model: this.modelId,\n ...editingOptions,\n ...providerRequestOptions,\n },\n abortSignal,\n fetch: this.config.fetch,\n failedResponseHandler: this.createLumaErrorHandler(),\n successfulResponseHandler: createJsonResponseHandler(\n lumaGenerationResponseSchema,\n ),\n });\n\n const imageUrl = await this.pollForImageUrl(\n generationResponse.id,\n fullHeaders,\n abortSignal,\n {\n pollIntervalMillis: pollIntervalMillis ?? undefined,\n maxPollAttempts: maxPollAttempts ?? undefined,\n },\n );\n\n const downloadedImage = await this.downloadImage(imageUrl, abortSignal);\n\n return {\n images: [downloadedImage],\n warnings,\n response: {\n modelId: this.modelId,\n timestamp: currentDate,\n headers: responseHeaders,\n },\n };\n }\n\n private async pollForImageUrl(\n generationId: string,\n headers: Record<string, string | undefined>,\n abortSignal: AbortSignal | undefined,\n pollSettings?: { pollIntervalMillis?: number; maxPollAttempts?: number },\n ): Promise<string> {\n const url = this.getLumaGenerationsUrl(generationId);\n const maxPollAttempts =\n pollSettings?.maxPollAttempts ?? this.maxPollAttempts;\n const pollIntervalMillis =\n pollSettings?.pollIntervalMillis ?? this.pollIntervalMillis;\n\n for (let i = 0; i < maxPollAttempts; i++) {\n const { value: statusResponse } = await getFromApi({\n url,\n headers,\n abortSignal,\n fetch: this.config.fetch,\n failedResponseHandler: this.createLumaErrorHandler(),\n successfulResponseHandler: createJsonResponseHandler(\n lumaGenerationResponseSchema,\n ),\n });\n\n switch (statusResponse.state) {\n case 'completed':\n if (!statusResponse.assets?.image) {\n throw new InvalidResponseDataError({\n data: statusResponse,\n message: `Image generation completed but no image was found.`,\n });\n }\n return statusResponse.assets.image;\n case 'failed':\n throw new InvalidResponseDataError({\n data: statusResponse,\n message: `Image generation failed.`,\n });\n }\n await delay(pollIntervalMillis);\n }\n\n throw new Error(\n `Image generation timed out after ${this.maxPollAttempts} attempts.`,\n );\n }\n\n private createLumaErrorHandler() {\n return createJsonErrorResponseHandler({\n errorSchema: lumaErrorSchema,\n errorToMessage: (error: LumaErrorData) =>\n error.detail[0].msg ?? 'Unknown error',\n });\n }\n\n private getEditingOptions(\n files: ImageModelV4File[] | undefined,\n mask: ImageModelV4File | undefined,\n referenceType: LumaReferenceType = 'image',\n imageConfigs: Array<{ weight?: number | null; id?: string | null }> = [],\n ): Record<string, unknown> {\n const options: Record<string, unknown> = {};\n\n // Luma does not support mask-based inpainting\n if (mask != null) {\n throw new Error(\n 'Luma AI does not support mask-based image editing. ' +\n 'Use the prompt to describe the changes you want to make, along with ' +\n '`prompt.images` containing the source image URL.',\n );\n }\n\n if (files == null || files.length === 0) {\n return options;\n }\n\n // Validate all files are URL-based\n for (const file of files) {\n if (file.type !== 'url') {\n throw new Error(\n 'Luma AI only supports URL-based images. ' +\n 'Please provide image URLs using `prompt.images` with publicly accessible URLs. ' +\n 'Base64 and Uint8Array data are not supported.',\n );\n }\n }\n\n // Default weights per reference type\n const defaultWeights: Record<LumaReferenceType, number> = {\n image: 0.85,\n style: 0.8,\n character: 1.0, // Not used, but defined for completeness\n modify_image: 1.0,\n };\n\n switch (referenceType) {\n case 'image': {\n // Supports up to 4 images\n if (files.length > 4) {\n throw new Error(\n 'Luma AI image supports up to 4 reference images. ' +\n `You provided ${files.length} images.`,\n );\n }\n options.image = files.map((file, index) => ({\n url: (file as { type: 'url'; url: string }).url,\n weight: imageConfigs[index]?.weight ?? defaultWeights.image,\n }));\n break;\n }\n\n case 'style': {\n // Style ref accepts an array but typically uses one style image\n options.style = files.map((file, index) => ({\n url: (file as { type: 'url'; url: string }).url,\n weight: imageConfigs[index]?.weight ?? defaultWeights.style,\n }));\n break;\n }\n\n case 'character': {\n // Group images by identity id\n const identities: Record<string, string[]> = {};\n for (let i = 0; i < files.length; i++) {\n const file = files[i] as { type: 'url'; url: string };\n const identityId = imageConfigs[i]?.id ?? 'identity0';\n if (!identities[identityId]) {\n identities[identityId] = [];\n }\n identities[identityId].push(file.url);\n }\n\n // Validate each identity has at most 4 images\n for (const [identityId, images] of Object.entries(identities)) {\n if (images.length > 4) {\n throw new Error(\n `Luma AI character supports up to 4 images per identity. ` +\n `Identity '${identityId}' has ${images.length} images.`,\n );\n }\n }\n\n options.character = Object.fromEntries(\n Object.entries(identities).map(([id, images]) => [id, { images }]),\n );\n break;\n }\n\n case 'modify_image': {\n // Only supports a single image\n if (files.length > 1) {\n throw new Error(\n 'Luma AI modify_image only supports a single input image. ' +\n `You provided ${files.length} images.`,\n );\n }\n options.modify_image = {\n url: (files[0] as { type: 'url'; url: string }).url,\n weight: imageConfigs[0]?.weight ?? defaultWeights.modify_image,\n };\n break;\n }\n }\n\n return options;\n }\n\n private getLumaGenerationsUrl(generationId?: string) {\n return `${this.config.baseURL}/dream-machine/v1/generations/${\n generationId ?? 'image'\n }`;\n }\n\n private async downloadImage(\n url: string,\n abortSignal: AbortSignal | undefined,\n ): Promise<Uint8Array> {\n const { value: response } = await getFromApi({\n url,\n // No specific headers should be needed for this request as it's a\n // generated image provided by Luma.\n abortSignal,\n failedResponseHandler: createStatusCodeErrorResponseHandler(),\n successfulResponseHandler: createBinaryResponseHandler(),\n fetch: this.config.fetch,\n });\n return response;\n }\n}\n\n// limited version of the schema, focussed on what is needed for the implementation\n// this approach limits breakages when the API changes and increases efficiency\nconst lumaGenerationResponseSchema = lazySchema(() =>\n zodSchema(\n z.object({\n id: z.string(),\n state: z.enum(['queued', 'dreaming', 'completed', 'failed']),\n failure_reason: z.string().nullish(),\n assets: z\n .object({\n image: z.string(), // URL of the generated image\n })\n .nullish(),\n }),\n ),\n);\n\nconst lumaErrorSchema = z.object({\n detail: z.array(\n z.object({\n type: z.string(),\n loc: z.array(z.string()),\n msg: z.string(),\n input: z.string(),\n ctx: z\n .object({\n expected: z.string(),\n })\n .nullish(),\n }),\n ),\n});\n\nexport type LumaErrorData = z.infer<typeof lumaErrorSchema>;\n\n/**\n * Provider options schema for Luma image generation.\n *\n * @see https://docs.lumalabs.ai/docs/image-generation\n */\n","import {\n lazySchema,\n zodSchema,\n type InferSchema,\n} from '@ai-sdk/provider-utils';\nimport { z } from 'zod/v4';\n\n/**\n * Provider options schema for Luma image generation.\n *\n * @see https://docs.lumalabs.ai/docs/image-generation\n */\nexport const lumaImageModelOptionsSchema = lazySchema(() =>\n zodSchema(\n z\n .object({\n /**\n * The type of image reference to use when providing input images.\n * - `image`: Guide generation using reference images (up to 4). Default.\n * - `style`: Apply a specific style from reference image(s).\n * - `character`: Create consistent characters from reference images (up to 4).\n * - `modify_image`: Transform a single input image with prompt guidance.\n */\n referenceType: z\n .enum(['image', 'style', 'character', 'modify_image'])\n .nullish(),\n\n /**\n * Per-image configuration array. Each entry corresponds to an image in `prompt.images`.\n * Allows setting individual weights for each reference image.\n */\n images: z\n .array(\n z.object({\n /**\n * The weight of this image's influence on the generation.\n * - For `image`: Higher weight = closer to reference (default: 0.85)\n * - For `style`: Higher weight = stronger style influence (default: 0.8)\n * - For `modify_image`: Higher weight = closer to input, lower = more creative (default: 1.0)\n */\n weight: z.number().min(0).max(1).nullish(),\n\n /**\n * The identity name for character references.\n * Used with `character` to specify which identity group the image belongs to.\n * Luma supports multiple identities (e.g., 'identity0', 'identity1') for generating\n * images with multiple consistent characters.\n * Default: 'identity0'\n */\n id: z.string().nullish(),\n }),\n )\n .nullish(),\n\n /**\n * Override the polling interval in milliseconds (default 500).\n */\n pollIntervalMillis: z.number().nullish(),\n\n /**\n * Override the maximum number of polling attempts (default 120).\n */\n maxPollAttempts: z.number().nullish(),\n })\n .passthrough(),\n ),\n);\n\nexport type LumaImageModelOptions = InferSchema<\n typeof lumaImageModelOptionsSchema\n>;\n","// Version string of this package injected at build time.\ndeclare const __PACKAGE_VERSION__: string | undefined;\nexport const VERSION: string =\n typeof __PACKAGE_VERSION__ !== 'undefined'\n ? __PACKAGE_VERSION__\n : '0.0.0-test';\n"],"mappings":"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","names":["lazySchema","zodSchema","z","_a","_b","lazySchema","zodSchema"]}
package/package.json CHANGED
@@ -1,10 +1,10 @@
1
1
  {
2
2
  "name": "@ai-sdk/luma",
3
- "version": "3.0.0-beta.3",
3
+ "version": "3.0.0-beta.31",
4
+ "type": "module",
4
5
  "license": "Apache-2.0",
5
6
  "sideEffects": false,
6
7
  "main": "./dist/index.js",
7
- "module": "./dist/index.mjs",
8
8
  "types": "./dist/index.d.ts",
9
9
  "files": [
10
10
  "dist/**/*",
@@ -24,20 +24,20 @@
24
24
  "./package.json": "./package.json",
25
25
  ".": {
26
26
  "types": "./dist/index.d.ts",
27
- "import": "./dist/index.mjs",
28
- "require": "./dist/index.js"
27
+ "import": "./dist/index.js",
28
+ "default": "./dist/index.js"
29
29
  }
30
30
  },
31
31
  "dependencies": {
32
- "@ai-sdk/provider": "4.0.0-beta.2",
33
- "@ai-sdk/provider-utils": "5.0.0-beta.3"
32
+ "@ai-sdk/provider-utils": "5.0.0-beta.30",
33
+ "@ai-sdk/provider": "4.0.0-beta.14"
34
34
  },
35
35
  "devDependencies": {
36
36
  "@types/node": "20.17.24",
37
37
  "tsup": "^8",
38
38
  "typescript": "5.8.3",
39
39
  "zod": "3.25.76",
40
- "@ai-sdk/test-server": "2.0.0-beta.0",
40
+ "@ai-sdk/test-server": "2.0.0-beta.3",
41
41
  "@vercel/ai-tsconfig": "0.0.0"
42
42
  },
43
43
  "peerDependencies": {
@@ -47,12 +47,14 @@
47
47
  "node": ">=18"
48
48
  },
49
49
  "publishConfig": {
50
- "access": "public"
50
+ "access": "public",
51
+ "provenance": true
51
52
  },
52
53
  "homepage": "https://ai-sdk.dev/docs",
53
54
  "repository": {
54
55
  "type": "git",
55
- "url": "git+https://github.com/vercel/ai.git"
56
+ "url": "https://github.com/vercel/ai",
57
+ "directory": "packages/luma"
56
58
  },
57
59
  "bugs": {
58
60
  "url": "https://github.com/vercel/ai/issues"
@@ -64,9 +66,7 @@
64
66
  "build": "pnpm clean && tsup --tsconfig tsconfig.build.json",
65
67
  "build:watch": "pnpm clean && tsup --watch",
66
68
  "clean": "del-cli dist docs *.tsbuildinfo",
67
- "lint": "eslint \"./**/*.ts*\"",
68
69
  "type-check": "tsc --build",
69
- "prettier-check": "prettier --check \"./**/*.ts*\"",
70
70
  "test": "pnpm test:node && pnpm test:edge",
71
71
  "test:update": "pnpm test:node -u",
72
72
  "test:watch": "vitest --config vitest.node.config.js",
package/src/index.ts CHANGED
@@ -1,9 +1,9 @@
1
1
  export { createLuma, luma } from './luma-provider';
2
2
  export type { LumaProvider, LumaProviderSettings } from './luma-provider';
3
+ export type { LumaErrorData } from './luma-image-model';
3
4
  export type {
4
- LumaErrorData,
5
5
  LumaImageModelOptions,
6
6
  /** @deprecated Use `LumaImageModelOptions` instead. */
7
7
  LumaImageModelOptions as LumaImageProviderOptions,
8
- } from './luma-image-model';
8
+ } from './luma-image-model-options';
9
9
  export { VERSION } from './version';
@@ -0,0 +1,71 @@
1
+ import {
2
+ lazySchema,
3
+ zodSchema,
4
+ type InferSchema,
5
+ } from '@ai-sdk/provider-utils';
6
+ import { z } from 'zod/v4';
7
+
8
+ /**
9
+ * Provider options schema for Luma image generation.
10
+ *
11
+ * @see https://docs.lumalabs.ai/docs/image-generation
12
+ */
13
+ export const lumaImageModelOptionsSchema = lazySchema(() =>
14
+ zodSchema(
15
+ z
16
+ .object({
17
+ /**
18
+ * The type of image reference to use when providing input images.
19
+ * - `image`: Guide generation using reference images (up to 4). Default.
20
+ * - `style`: Apply a specific style from reference image(s).
21
+ * - `character`: Create consistent characters from reference images (up to 4).
22
+ * - `modify_image`: Transform a single input image with prompt guidance.
23
+ */
24
+ referenceType: z
25
+ .enum(['image', 'style', 'character', 'modify_image'])
26
+ .nullish(),
27
+
28
+ /**
29
+ * Per-image configuration array. Each entry corresponds to an image in `prompt.images`.
30
+ * Allows setting individual weights for each reference image.
31
+ */
32
+ images: z
33
+ .array(
34
+ z.object({
35
+ /**
36
+ * The weight of this image's influence on the generation.
37
+ * - For `image`: Higher weight = closer to reference (default: 0.85)
38
+ * - For `style`: Higher weight = stronger style influence (default: 0.8)
39
+ * - For `modify_image`: Higher weight = closer to input, lower = more creative (default: 1.0)
40
+ */
41
+ weight: z.number().min(0).max(1).nullish(),
42
+
43
+ /**
44
+ * The identity name for character references.
45
+ * Used with `character` to specify which identity group the image belongs to.
46
+ * Luma supports multiple identities (e.g., 'identity0', 'identity1') for generating
47
+ * images with multiple consistent characters.
48
+ * Default: 'identity0'
49
+ */
50
+ id: z.string().nullish(),
51
+ }),
52
+ )
53
+ .nullish(),
54
+
55
+ /**
56
+ * Override the polling interval in milliseconds (default 500).
57
+ */
58
+ pollIntervalMillis: z.number().nullish(),
59
+
60
+ /**
61
+ * Override the maximum number of polling attempts (default 120).
62
+ */
63
+ maxPollAttempts: z.number().nullish(),
64
+ })
65
+ .passthrough(),
66
+ ),
67
+ );
68
+
69
+ export type LumaImageModelOptions = InferSchema<
70
+ typeof lumaImageModelOptionsSchema
71
+ >;