@umituz/react-native-ai-gemini-provider 1.8.1 → 1.8.3
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/package.json
CHANGED
|
@@ -14,9 +14,14 @@ export const GEMINI_MODELS = {
|
|
|
14
14
|
PRO: "gemini-1.5-pro",
|
|
15
15
|
},
|
|
16
16
|
|
|
17
|
-
// Image
|
|
18
|
-
|
|
19
|
-
DEFAULT: "imagen-4.0-generate",
|
|
17
|
+
// Text-to-Image models (Imagen 4.0) - generates images from text only
|
|
18
|
+
TEXT_TO_IMAGE: {
|
|
19
|
+
DEFAULT: "imagen-4.0-generate-001",
|
|
20
|
+
},
|
|
21
|
+
|
|
22
|
+
// Image editing models (Gemini) - transforms/edits images with input image + prompt
|
|
23
|
+
IMAGE_EDIT: {
|
|
24
|
+
DEFAULT: "gemini-2.0-flash-exp-image-generation",
|
|
20
25
|
},
|
|
21
26
|
|
|
22
27
|
// Video understanding models
|
|
@@ -30,7 +35,8 @@ export const GEMINI_MODELS = {
|
|
|
30
35
|
*/
|
|
31
36
|
export const DEFAULT_MODELS = {
|
|
32
37
|
TEXT: GEMINI_MODELS.TEXT.FLASH,
|
|
33
|
-
|
|
38
|
+
TEXT_TO_IMAGE: GEMINI_MODELS.TEXT_TO_IMAGE.DEFAULT,
|
|
39
|
+
IMAGE_EDIT: GEMINI_MODELS.IMAGE_EDIT.DEFAULT,
|
|
34
40
|
VIDEO: GEMINI_MODELS.VIDEO.FLASH,
|
|
35
41
|
} as const;
|
|
36
42
|
|
|
@@ -23,7 +23,7 @@ const DEFAULT_CONFIG: Partial<GeminiConfig> = {
|
|
|
23
23
|
maxDelay: 10000,
|
|
24
24
|
defaultTimeoutMs: 60000,
|
|
25
25
|
defaultModel: DEFAULT_MODELS.TEXT,
|
|
26
|
-
imageModel: DEFAULT_MODELS.
|
|
26
|
+
imageModel: DEFAULT_MODELS.TEXT_TO_IMAGE,
|
|
27
27
|
};
|
|
28
28
|
|
|
29
29
|
const RETRYABLE_ERROR_PATTERNS = [
|
|
@@ -264,7 +264,7 @@ class GeminiClientService {
|
|
|
264
264
|
): Promise<GeminiImageGenerationResult> {
|
|
265
265
|
this.validateInitialization();
|
|
266
266
|
|
|
267
|
-
const imageModel = this.config?.imageModel || DEFAULT_MODELS.
|
|
267
|
+
const imageModel = this.config?.imageModel || DEFAULT_MODELS.TEXT_TO_IMAGE;
|
|
268
268
|
const apiKey = this.config?.apiKey;
|
|
269
269
|
|
|
270
270
|
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
@@ -339,6 +339,109 @@ class GeminiClientService {
|
|
|
339
339
|
return result;
|
|
340
340
|
}
|
|
341
341
|
|
|
342
|
+
/**
|
|
343
|
+
* Edit/transform image using Gemini generateContent API
|
|
344
|
+
* Takes input image + prompt and generates new image
|
|
345
|
+
*/
|
|
346
|
+
async editImage(
|
|
347
|
+
prompt: string,
|
|
348
|
+
images: Array<{ base64: string; mimeType: string }>,
|
|
349
|
+
): Promise<GeminiImageGenerationResult> {
|
|
350
|
+
this.validateInitialization();
|
|
351
|
+
|
|
352
|
+
const editModel = DEFAULT_MODELS.IMAGE_EDIT;
|
|
353
|
+
const apiKey = this.config?.apiKey;
|
|
354
|
+
|
|
355
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
356
|
+
// eslint-disable-next-line no-console
|
|
357
|
+
console.log("[GeminiClient] editImage() called", {
|
|
358
|
+
model: editModel,
|
|
359
|
+
promptLength: prompt.length,
|
|
360
|
+
imagesCount: images.length,
|
|
361
|
+
});
|
|
362
|
+
}
|
|
363
|
+
|
|
364
|
+
const url = `https://generativelanguage.googleapis.com/v1beta/models/${editModel}:generateContent`;
|
|
365
|
+
|
|
366
|
+
const parts: Array<Record<string, unknown>> = [];
|
|
367
|
+
|
|
368
|
+
for (const image of images) {
|
|
369
|
+
parts.push({
|
|
370
|
+
inlineData: {
|
|
371
|
+
mimeType: image.mimeType,
|
|
372
|
+
data: extractBase64Data(image.base64),
|
|
373
|
+
},
|
|
374
|
+
});
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
parts.push({ text: prompt });
|
|
378
|
+
|
|
379
|
+
const requestBody = {
|
|
380
|
+
contents: [{ parts }],
|
|
381
|
+
generationConfig: {
|
|
382
|
+
responseModalities: ["TEXT", "IMAGE"],
|
|
383
|
+
},
|
|
384
|
+
};
|
|
385
|
+
|
|
386
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
387
|
+
// eslint-disable-next-line no-console
|
|
388
|
+
console.log("[GeminiClient] editImage() request", {
|
|
389
|
+
url,
|
|
390
|
+
partsCount: parts.length,
|
|
391
|
+
});
|
|
392
|
+
}
|
|
393
|
+
|
|
394
|
+
const response = await this.executeWithRetry(async () => {
|
|
395
|
+
const res = await fetch(url, {
|
|
396
|
+
method: "POST",
|
|
397
|
+
headers: {
|
|
398
|
+
"Content-Type": "application/json",
|
|
399
|
+
"x-goog-api-key": apiKey!,
|
|
400
|
+
},
|
|
401
|
+
body: JSON.stringify(requestBody),
|
|
402
|
+
});
|
|
403
|
+
|
|
404
|
+
if (!res.ok) {
|
|
405
|
+
const errorText = await res.text();
|
|
406
|
+
throw new Error(`Image edit API error (${res.status}): ${errorText}`);
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
return res.json();
|
|
410
|
+
});
|
|
411
|
+
|
|
412
|
+
const result: GeminiImageGenerationResult = {
|
|
413
|
+
text: undefined,
|
|
414
|
+
imageUrl: undefined,
|
|
415
|
+
imageBase64: undefined,
|
|
416
|
+
mimeType: "image/png",
|
|
417
|
+
};
|
|
418
|
+
|
|
419
|
+
const candidate = response.candidates?.[0];
|
|
420
|
+
const responseParts = candidate?.content?.parts || [];
|
|
421
|
+
|
|
422
|
+
for (const part of responseParts) {
|
|
423
|
+
if (part.text) {
|
|
424
|
+
result.text = part.text;
|
|
425
|
+
}
|
|
426
|
+
if (part.inlineData) {
|
|
427
|
+
result.imageBase64 = part.inlineData.data;
|
|
428
|
+
result.mimeType = part.inlineData.mimeType || "image/png";
|
|
429
|
+
result.imageUrl = `data:${result.mimeType};base64,${result.imageBase64}`;
|
|
430
|
+
}
|
|
431
|
+
}
|
|
432
|
+
|
|
433
|
+
if (typeof __DEV__ !== "undefined" && __DEV__) {
|
|
434
|
+
// eslint-disable-next-line no-console
|
|
435
|
+
console.log("[GeminiClient] editImage() completed", {
|
|
436
|
+
hasImage: !!result.imageBase64,
|
|
437
|
+
hasText: !!result.text,
|
|
438
|
+
imageDataLength: result.imageBase64?.length ?? 0,
|
|
439
|
+
});
|
|
440
|
+
}
|
|
441
|
+
|
|
442
|
+
return result;
|
|
443
|
+
}
|
|
444
|
+
|
|
342
445
|
/**
|
|
343
446
|
* Stream content generation
|
|
344
447
|
*/
|
|
@@ -201,14 +201,24 @@ class GeminiProviderService {
|
|
|
201
201
|
}
|
|
202
202
|
|
|
203
203
|
/**
|
|
204
|
-
* Generate image
|
|
205
|
-
*
|
|
204
|
+
* Generate image from text only (Imagen API)
|
|
205
|
+
* Use for text-to-image generation without input images
|
|
206
206
|
*/
|
|
207
207
|
async generateImage(
|
|
208
208
|
prompt: string,
|
|
209
|
-
images?: GeminiImageInput[],
|
|
210
209
|
): Promise<GeminiImageGenerationResult> {
|
|
211
|
-
return geminiClientService.generateImage(prompt
|
|
210
|
+
return geminiClientService.generateImage(prompt);
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
/**
|
|
214
|
+
* Edit/transform image using input image + prompt (Gemini API)
|
|
215
|
+
* Use for image editing, transformation, style transfer
|
|
216
|
+
*/
|
|
217
|
+
async editImage(
|
|
218
|
+
prompt: string,
|
|
219
|
+
images: GeminiImageInput[],
|
|
220
|
+
): Promise<GeminiImageGenerationResult> {
|
|
221
|
+
return geminiClientService.editImage(prompt, images);
|
|
212
222
|
}
|
|
213
223
|
|
|
214
224
|
/**
|