mcp-image 0.1.0
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/LICENSE +21 -0
- package/README.md +163 -0
- package/dist/api/geminiClient.d.ts +55 -0
- package/dist/api/geminiClient.d.ts.map +1 -0
- package/dist/api/geminiClient.js +194 -0
- package/dist/api/geminiClient.js.map +1 -0
- package/dist/api/urlContextClient.d.ts +149 -0
- package/dist/api/urlContextClient.d.ts.map +1 -0
- package/dist/api/urlContextClient.js +320 -0
- package/dist/api/urlContextClient.js.map +1 -0
- package/dist/business/errorHandler.d.ts +97 -0
- package/dist/business/errorHandler.d.ts.map +1 -0
- package/dist/business/errorHandler.js +511 -0
- package/dist/business/errorHandler.js.map +1 -0
- package/dist/business/fileManager.d.ts +20 -0
- package/dist/business/fileManager.d.ts.map +1 -0
- package/dist/business/fileManager.js +112 -0
- package/dist/business/fileManager.js.map +1 -0
- package/dist/business/imageGenerator.d.ts +64 -0
- package/dist/business/imageGenerator.d.ts.map +1 -0
- package/dist/business/imageGenerator.js +147 -0
- package/dist/business/imageGenerator.js.map +1 -0
- package/dist/business/imageGeneratorRobust.d.ts +60 -0
- package/dist/business/imageGeneratorRobust.d.ts.map +1 -0
- package/dist/business/imageGeneratorRobust.js +242 -0
- package/dist/business/imageGeneratorRobust.js.map +1 -0
- package/dist/business/inputValidator.d.ts +29 -0
- package/dist/business/inputValidator.d.ts.map +1 -0
- package/dist/business/inputValidator.js +132 -0
- package/dist/business/inputValidator.js.map +1 -0
- package/dist/business/performanceManager.d.ts +88 -0
- package/dist/business/performanceManager.d.ts.map +1 -0
- package/dist/business/performanceManager.js +142 -0
- package/dist/business/performanceManager.js.map +1 -0
- package/dist/business/responseBuilder.d.ts +20 -0
- package/dist/business/responseBuilder.d.ts.map +1 -0
- package/dist/business/responseBuilder.js +162 -0
- package/dist/business/responseBuilder.js.map +1 -0
- package/dist/business/secureFileManager.d.ts +56 -0
- package/dist/business/secureFileManager.d.ts.map +1 -0
- package/dist/business/secureFileManager.js +185 -0
- package/dist/business/secureFileManager.js.map +1 -0
- package/dist/business/urlExtractor.d.ts +60 -0
- package/dist/business/urlExtractor.d.ts.map +1 -0
- package/dist/business/urlExtractor.js +144 -0
- package/dist/business/urlExtractor.js.map +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +45 -0
- package/dist/index.js.map +1 -0
- package/dist/server/concurrencyManager.d.ts +56 -0
- package/dist/server/concurrencyManager.d.ts.map +1 -0
- package/dist/server/concurrencyManager.js +133 -0
- package/dist/server/concurrencyManager.js.map +1 -0
- package/dist/server/errorHandler.d.ts +29 -0
- package/dist/server/errorHandler.d.ts.map +1 -0
- package/dist/server/errorHandler.js +93 -0
- package/dist/server/errorHandler.js.map +1 -0
- package/dist/server/mcpServer.d.ts +111 -0
- package/dist/server/mcpServer.d.ts.map +1 -0
- package/dist/server/mcpServer.js +353 -0
- package/dist/server/mcpServer.js.map +1 -0
- package/dist/types/mcp.d.ts +72 -0
- package/dist/types/mcp.d.ts.map +1 -0
- package/dist/types/mcp.js +7 -0
- package/dist/types/mcp.js.map +1 -0
- package/dist/types/result.d.ts +27 -0
- package/dist/types/result.d.ts.map +1 -0
- package/dist/types/result.js +31 -0
- package/dist/types/result.js.map +1 -0
- package/dist/utils/config.d.ts +26 -0
- package/dist/utils/config.d.ts.map +1 -0
- package/dist/utils/config.js +53 -0
- package/dist/utils/config.js.map +1 -0
- package/dist/utils/errors.d.ts +84 -0
- package/dist/utils/errors.d.ts.map +1 -0
- package/dist/utils/errors.js +218 -0
- package/dist/utils/errors.js.map +1 -0
- package/dist/utils/logger.d.ts +80 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +223 -0
- package/dist/utils/logger.js.map +1 -0
- package/dist/utils/security.d.ts +50 -0
- package/dist/utils/security.d.ts.map +1 -0
- package/dist/utils/security.js +153 -0
- package/dist/utils/security.js.map +1 -0
- package/package.json +73 -0
- package/vitest.config.mjs +47 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 Shinsuke Kagawa
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
# MCP Image Generator
|
|
2
|
+
|
|
3
|
+
A powerful MCP (Model Context Protocol) server that enables AI assistants to generate and edit images using Google's Gemini 2.5 Flash Image API. Seamlessly integrate advanced image generation capabilities into Claude Code, Cursor, and other MCP-compatible AI tools.
|
|
4
|
+
|
|
5
|
+
## ✨ Features
|
|
6
|
+
|
|
7
|
+
- **AI-Powered Image Generation**: Create images from text prompts using Gemini 2.5 Flash Image Preview
|
|
8
|
+
- **Image Editing**: Transform existing images with natural language instructions
|
|
9
|
+
- **Advanced Options**:
|
|
10
|
+
- Multi-image blending for composite scenes
|
|
11
|
+
- Character consistency across generations
|
|
12
|
+
- World knowledge integration for accurate context
|
|
13
|
+
- **Multiple Output Formats**: PNG, JPEG, WebP support
|
|
14
|
+
- **File Output**: Images are saved as files for easy access and integration
|
|
15
|
+
|
|
16
|
+
## 🔧 Prerequisites
|
|
17
|
+
|
|
18
|
+
- **Node.js** 20 or higher
|
|
19
|
+
- **Gemini API Key** - Get yours at [Google AI Studio](https://aistudio.google.com/apikey)
|
|
20
|
+
- **Claude Code** or **Cursor** (or any MCP-compatible AI tool)
|
|
21
|
+
- Basic terminal/command line knowledge
|
|
22
|
+
|
|
23
|
+
## 🚀 Quick Start
|
|
24
|
+
|
|
25
|
+
### 1. Get Your Gemini API Key
|
|
26
|
+
|
|
27
|
+
Get your API key from [Google AI Studio](https://aistudio.google.com/apikey)
|
|
28
|
+
|
|
29
|
+
### 2. MCP Configuration
|
|
30
|
+
|
|
31
|
+
#### For Claude Code
|
|
32
|
+
|
|
33
|
+
```bash
|
|
34
|
+
claude mcp add mcp-image --env GEMINI_API_KEY=your-api-key --env IMAGE_OUTPUT_DIR=/absolute/path/to/images -- npx -y mcp-image
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
#### For Cursor
|
|
38
|
+
|
|
39
|
+
Add to your Cursor settings (`~/.cursor/mcp.json`):
|
|
40
|
+
|
|
41
|
+
```json
|
|
42
|
+
{
|
|
43
|
+
"mcp": {
|
|
44
|
+
"servers": {
|
|
45
|
+
"mcp-image": {
|
|
46
|
+
"command": "npx",
|
|
47
|
+
"args": ["-y", "mcp-image"],
|
|
48
|
+
"env": {
|
|
49
|
+
"GEMINI_API_KEY": "your_gemini_api_key_here",
|
|
50
|
+
"IMAGE_OUTPUT_DIR": "/absolute/path/to/images"
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
⚠️ **Security Note**: Never commit your API key to version control. Keep it secure and use environment-specific configuration.
|
|
59
|
+
|
|
60
|
+
📁 **Path Requirements**:
|
|
61
|
+
- `IMAGE_OUTPUT_DIR` must be an absolute path (e.g., `/Users/username/images`, not `./images`)
|
|
62
|
+
- Defaults to `./output` in the current working directory if not specified
|
|
63
|
+
- Directory will be created automatically if it doesn't exist
|
|
64
|
+
|
|
65
|
+
## 📖 Usage Examples
|
|
66
|
+
|
|
67
|
+
Once configured, your AI assistant can generate images using natural language:
|
|
68
|
+
|
|
69
|
+
### Basic Image Generation
|
|
70
|
+
|
|
71
|
+
```
|
|
72
|
+
"Generate a serene mountain landscape at sunset with a lake reflection"
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
### Image Editing
|
|
76
|
+
|
|
77
|
+
```
|
|
78
|
+
"Edit this image to make the person face right"
|
|
79
|
+
(with inputImagePath: "/path/to/image.jpg")
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
|
|
83
|
+
### Advanced Features
|
|
84
|
+
|
|
85
|
+
```
|
|
86
|
+
"Generate a portrait of a medieval knight, maintaining character consistency for future variations"
|
|
87
|
+
(with maintainCharacterConsistency: true)
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
## 🔧 API Reference
|
|
91
|
+
|
|
92
|
+
### `generate_image` Tool
|
|
93
|
+
|
|
94
|
+
The MCP server exposes a single tool for all image operations:
|
|
95
|
+
|
|
96
|
+
#### Parameters
|
|
97
|
+
|
|
98
|
+
| Parameter | Type | Required | Description |
|
|
99
|
+
|-----------|------|----------|-------------|
|
|
100
|
+
| `prompt` | string | ✅ | Text description or editing instruction |
|
|
101
|
+
| `inputImagePath` | string | ❌ | Absolute path to input image for editing |
|
|
102
|
+
| `fileName` | string | ❌ | Custom filename for output (auto-generated if not specified) |
|
|
103
|
+
| `blendImages` | boolean | ❌ | Enable multi-image blending |
|
|
104
|
+
| `maintainCharacterConsistency` | boolean | ❌ | Maintain character appearance across generations |
|
|
105
|
+
| `useWorldKnowledge` | boolean | ❌ | Use real-world knowledge for context |
|
|
106
|
+
|
|
107
|
+
#### Response
|
|
108
|
+
|
|
109
|
+
```json
|
|
110
|
+
{
|
|
111
|
+
"type": "resource",
|
|
112
|
+
"resource": {
|
|
113
|
+
"uri": "file:///path/to/generated/image.png",
|
|
114
|
+
"name": "image-filename.png",
|
|
115
|
+
"mimeType": "image/png"
|
|
116
|
+
},
|
|
117
|
+
"metadata": {
|
|
118
|
+
"model": "gemini-2.5-flash-image-preview",
|
|
119
|
+
"processingTime": 5000,
|
|
120
|
+
"timestamp": "2024-01-01T12:00:00.000Z"
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
## 🛠️ Troubleshooting
|
|
126
|
+
|
|
127
|
+
### Common Issues
|
|
128
|
+
|
|
129
|
+
**"API key not found"**
|
|
130
|
+
- Ensure `GEMINI_API_KEY` is set in your environment
|
|
131
|
+
- Verify the API key is valid and has image generation permissions
|
|
132
|
+
|
|
133
|
+
**"Input image file not found"**
|
|
134
|
+
- Use absolute file paths, not relative paths
|
|
135
|
+
- Ensure the file exists and is accessible
|
|
136
|
+
- Supported formats: PNG, JPEG, WebP (max 10MB)
|
|
137
|
+
|
|
138
|
+
**"No image data found in Gemini API response"**
|
|
139
|
+
- Try rephrasing your prompt with more specific details
|
|
140
|
+
- Ensure your prompt is appropriate for image generation
|
|
141
|
+
- Check if your API key has sufficient quota
|
|
142
|
+
|
|
143
|
+
### Performance Tips
|
|
144
|
+
|
|
145
|
+
- Image generation: 30-60 seconds typical
|
|
146
|
+
- Image editing: 15-45 seconds typical
|
|
147
|
+
- Use specific, descriptive prompts for better results
|
|
148
|
+
- Consider enabling `useWorldKnowledge` for historical or factual subjects
|
|
149
|
+
|
|
150
|
+
|
|
151
|
+
## 💰 Usage Notes
|
|
152
|
+
|
|
153
|
+
- This MCP server uses the paid Gemini API for image generation
|
|
154
|
+
- Check current pricing and rate limits at [Google AI Studio](https://aistudio.google.com/)
|
|
155
|
+
- Monitor your API usage to avoid unexpected charges
|
|
156
|
+
|
|
157
|
+
## 📄 License
|
|
158
|
+
|
|
159
|
+
MIT License - see [LICENSE](LICENSE) for details.
|
|
160
|
+
|
|
161
|
+
---
|
|
162
|
+
|
|
163
|
+
**Need help?** [Open an issue](https://github.com/shinpr/mcp-image/issues) or check the [troubleshooting section](#-troubleshooting) above.
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Gemini API client for image generation
|
|
3
|
+
* Integrates with Google's Gemini AI API using the official SDK
|
|
4
|
+
* Supports automatic URL Context processing and feature parameters
|
|
5
|
+
*/
|
|
6
|
+
import type { Result } from '../types/result';
|
|
7
|
+
import type { Config } from '../utils/config';
|
|
8
|
+
import { GeminiAPIError, NetworkError } from '../utils/errors';
|
|
9
|
+
/**
|
|
10
|
+
* Metadata for generated images
|
|
11
|
+
*/
|
|
12
|
+
export interface GeminiGenerationMetadata {
|
|
13
|
+
model: string;
|
|
14
|
+
prompt: string;
|
|
15
|
+
mimeType: string;
|
|
16
|
+
timestamp: Date;
|
|
17
|
+
inputImageProvided: boolean;
|
|
18
|
+
contextMethod: string;
|
|
19
|
+
/** Features usage metadata */
|
|
20
|
+
features?: {
|
|
21
|
+
blendImages: boolean;
|
|
22
|
+
maintainCharacterConsistency: boolean;
|
|
23
|
+
useWorldKnowledge: boolean;
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Parameters for Gemini API image generation (with processed data)
|
|
28
|
+
*/
|
|
29
|
+
export interface GeminiApiParams {
|
|
30
|
+
prompt: string;
|
|
31
|
+
inputImage?: Buffer;
|
|
32
|
+
blendImages?: boolean;
|
|
33
|
+
maintainCharacterConsistency?: boolean;
|
|
34
|
+
useWorldKnowledge?: boolean;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Result of image generation
|
|
38
|
+
*/
|
|
39
|
+
export interface GeneratedImageResult {
|
|
40
|
+
imageData: Buffer;
|
|
41
|
+
metadata: GeminiGenerationMetadata;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Gemini API client interface
|
|
45
|
+
*/
|
|
46
|
+
export interface GeminiClient {
|
|
47
|
+
generateImage(params: GeminiApiParams): Promise<Result<GeneratedImageResult, GeminiAPIError | NetworkError>>;
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Creates a new Gemini API client
|
|
51
|
+
* @param config Configuration containing API key and other settings
|
|
52
|
+
* @returns Result containing the client or an error
|
|
53
|
+
*/
|
|
54
|
+
export declare function createGeminiClient(config: Config): Result<GeminiClient, GeminiAPIError>;
|
|
55
|
+
//# sourceMappingURL=geminiClient.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"geminiClient.d.ts","sourceRoot":"","sources":["../../src/api/geminiClient.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAGH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAA;AAE7C,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAA;AAC7C,OAAO,EAAE,cAAc,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;AAiD9D;;GAEG;AACH,MAAM,WAAW,wBAAwB;IACvC,KAAK,EAAE,MAAM,CAAA;IACb,MAAM,EAAE,MAAM,CAAA;IACd,QAAQ,EAAE,MAAM,CAAA;IAChB,SAAS,EAAE,IAAI,CAAA;IACf,kBAAkB,EAAE,OAAO,CAAA;IAC3B,aAAa,EAAE,MAAM,CAAA;IACrB,8BAA8B;IAC9B,QAAQ,CAAC,EAAE;QACT,WAAW,EAAE,OAAO,CAAA;QACpB,4BAA4B,EAAE,OAAO,CAAA;QACrC,iBAAiB,EAAE,OAAO,CAAA;KAC3B,CAAA;CACF;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAA;IACd,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,WAAW,CAAC,EAAE,OAAO,CAAA;IACrB,4BAA4B,CAAC,EAAE,OAAO,CAAA;IACtC,iBAAiB,CAAC,EAAE,OAAO,CAAA;CAC5B;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,wBAAwB,CAAA;CACnC;AAED;;GAEG;AACH,MAAM,WAAW,YAAY;IAC3B,aAAa,CACX,MAAM,EAAE,eAAe,GACtB,OAAO,CAAC,MAAM,CAAC,oBAAoB,EAAE,cAAc,GAAG,YAAY,CAAC,CAAC,CAAA;CACxE;AAwPD;;;;GAIG;AACH,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAAC,YAAY,EAAE,cAAc,CAAC,CAevF"}
|
|
@@ -0,0 +1,194 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Gemini API client for image generation
|
|
4
|
+
* Integrates with Google's Gemini AI API using the official SDK
|
|
5
|
+
* Supports automatic URL Context processing and feature parameters
|
|
6
|
+
*/
|
|
7
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
|
+
exports.createGeminiClient = createGeminiClient;
|
|
9
|
+
const genai_1 = require("@google/genai");
|
|
10
|
+
const result_1 = require("../types/result");
|
|
11
|
+
const errors_1 = require("../utils/errors");
|
|
12
|
+
/**
|
|
13
|
+
* URL pattern for automatic URL detection
|
|
14
|
+
*/
|
|
15
|
+
const URL_PATTERN = /https?:\/\/(?:[-\w.])+(?:\.[a-zA-Z]{2,})+(?:\/[-\w._~:\/?#[\]@!$&'()*+,;=]*)?/g;
|
|
16
|
+
/**
|
|
17
|
+
* Implementation of Gemini API client
|
|
18
|
+
*/
|
|
19
|
+
class GeminiClientImpl {
|
|
20
|
+
constructor(genai) {
|
|
21
|
+
this.genai = genai;
|
|
22
|
+
this.modelName = 'gemini-2.5-flash-image-preview';
|
|
23
|
+
}
|
|
24
|
+
async generateImage(params) {
|
|
25
|
+
try {
|
|
26
|
+
// Enhance prompt with structured parameters for better accuracy
|
|
27
|
+
let enhancedPrompt = params.prompt;
|
|
28
|
+
// Convert MCP parameters to structured prompt instructions
|
|
29
|
+
if (params.maintainCharacterConsistency) {
|
|
30
|
+
enhancedPrompt +=
|
|
31
|
+
' [INSTRUCTION: Maintain exact character appearance, including facial features, hairstyle, clothing, and all physical characteristics consistent throughout the image]';
|
|
32
|
+
}
|
|
33
|
+
if (params.blendImages) {
|
|
34
|
+
enhancedPrompt +=
|
|
35
|
+
' [INSTRUCTION: Seamlessly blend multiple visual elements into a natural, cohesive composition with smooth transitions]';
|
|
36
|
+
}
|
|
37
|
+
if (params.useWorldKnowledge) {
|
|
38
|
+
enhancedPrompt +=
|
|
39
|
+
' [INSTRUCTION: Apply accurate real-world knowledge including historical facts, geographical accuracy, cultural contexts, and realistic depictions]';
|
|
40
|
+
}
|
|
41
|
+
// Prepare the request content with enhanced prompt
|
|
42
|
+
const requestContent = [enhancedPrompt];
|
|
43
|
+
// Add input image if provided
|
|
44
|
+
if (params.inputImage) {
|
|
45
|
+
requestContent.push({
|
|
46
|
+
inlineData: {
|
|
47
|
+
data: params.inputImage.toString('base64'),
|
|
48
|
+
mimeType: 'image/jpeg', // Assume JPEG for input images
|
|
49
|
+
},
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
// Prepare API configuration
|
|
53
|
+
const config = {};
|
|
54
|
+
// URL detection is maintained for potential future use
|
|
55
|
+
// Note: urlContext tool has been removed as it's not supported by the model
|
|
56
|
+
this.detectUrls(params.prompt);
|
|
57
|
+
// Note: Feature parameters are now handled via prompt enhancement
|
|
58
|
+
// The Gemini API does not directly support these as config parameters
|
|
59
|
+
// Generate content using Gemini API with official URL Context support
|
|
60
|
+
const response = await this.genai.models.generateContent({
|
|
61
|
+
model: this.modelName,
|
|
62
|
+
contents: requestContent,
|
|
63
|
+
config,
|
|
64
|
+
});
|
|
65
|
+
// Extract image data from response
|
|
66
|
+
if (!response || typeof response !== 'object') {
|
|
67
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError('Invalid response from Gemini API', 'The API returned an unexpected response format'));
|
|
68
|
+
}
|
|
69
|
+
// Handle different response structures
|
|
70
|
+
const candidates = response.response?.candidates ||
|
|
71
|
+
response.candidates;
|
|
72
|
+
if (!candidates || candidates.length === 0) {
|
|
73
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError('No image generated by Gemini API', 'Try rephrasing your prompt or check if the model supports your request type'));
|
|
74
|
+
}
|
|
75
|
+
const candidate = candidates[0];
|
|
76
|
+
if (!candidate) {
|
|
77
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError('No candidate found in Gemini API response', 'The API response was malformed. Try again or contact support if the issue persists'));
|
|
78
|
+
}
|
|
79
|
+
const parts = candidate.content?.parts;
|
|
80
|
+
if (!parts || parts.length === 0) {
|
|
81
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError('No image data in response from Gemini API', 'The API response was malformed. Try again or contact support if the issue persists'));
|
|
82
|
+
}
|
|
83
|
+
// Find the image part with proper type guards
|
|
84
|
+
const imagePart = parts.find((part) => {
|
|
85
|
+
const p = part;
|
|
86
|
+
return p.inlineData?.data;
|
|
87
|
+
});
|
|
88
|
+
if (!imagePart?.inlineData) {
|
|
89
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError('No image data found in Gemini API response', 'The model may not have generated an image. Try a different prompt'));
|
|
90
|
+
}
|
|
91
|
+
// Convert base64 image data to Buffer
|
|
92
|
+
const imageBuffer = Buffer.from(imagePart.inlineData.data, 'base64');
|
|
93
|
+
const mimeType = imagePart.inlineData.mimeType || 'image/png';
|
|
94
|
+
// Create metadata with features information
|
|
95
|
+
const metadata = {
|
|
96
|
+
model: this.modelName,
|
|
97
|
+
prompt: params.prompt, // Original prompt, not enhanced
|
|
98
|
+
mimeType,
|
|
99
|
+
timestamp: new Date(),
|
|
100
|
+
inputImageProvided: !!params.inputImage,
|
|
101
|
+
contextMethod: 'prompt_only',
|
|
102
|
+
};
|
|
103
|
+
// Add features usage information if any features are specified (including false)
|
|
104
|
+
if (params.blendImages !== undefined ||
|
|
105
|
+
params.maintainCharacterConsistency !== undefined ||
|
|
106
|
+
params.useWorldKnowledge !== undefined) {
|
|
107
|
+
metadata.features = {
|
|
108
|
+
blendImages: params.blendImages || false,
|
|
109
|
+
maintainCharacterConsistency: params.maintainCharacterConsistency || false,
|
|
110
|
+
useWorldKnowledge: params.useWorldKnowledge || false,
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
return (0, result_1.Ok)({
|
|
114
|
+
imageData: imageBuffer,
|
|
115
|
+
metadata,
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
catch (error) {
|
|
119
|
+
return this.handleError(error, params.prompt);
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
handleError(error, prompt) {
|
|
123
|
+
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
|
|
124
|
+
// Check if it's a network error
|
|
125
|
+
if (this.isNetworkError(error)) {
|
|
126
|
+
return (0, result_1.Err)(new errors_1.NetworkError(`Network error during image generation: ${errorMessage}`, 'Check your internet connection and try again', error instanceof Error ? error : undefined));
|
|
127
|
+
}
|
|
128
|
+
// Check if it's an API-specific error
|
|
129
|
+
if (this.isAPIError(error)) {
|
|
130
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError(`Failed to generate image: ${errorMessage}`, this.getAPIErrorSuggestion(errorMessage), this.extractStatusCode(error)));
|
|
131
|
+
}
|
|
132
|
+
// Generic API error
|
|
133
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError(`Failed to generate image with prompt "${prompt}": ${errorMessage}`, 'Check your API key, quota, and prompt validity. Try again with a different prompt'));
|
|
134
|
+
}
|
|
135
|
+
isNetworkError(error) {
|
|
136
|
+
if (error instanceof Error) {
|
|
137
|
+
const networkErrorCodes = ['ECONNRESET', 'ECONNREFUSED', 'ETIMEDOUT', 'ENOTFOUND'];
|
|
138
|
+
return networkErrorCodes.some((code) => error.message.includes(code) || error.code === code);
|
|
139
|
+
}
|
|
140
|
+
return false;
|
|
141
|
+
}
|
|
142
|
+
isAPIError(error) {
|
|
143
|
+
if (error instanceof Error) {
|
|
144
|
+
const apiErrorKeywords = ['quota', 'rate limit', 'unauthorized', 'forbidden', 'api key'];
|
|
145
|
+
return apiErrorKeywords.some((keyword) => error.message.toLowerCase().includes(keyword));
|
|
146
|
+
}
|
|
147
|
+
return false;
|
|
148
|
+
}
|
|
149
|
+
getAPIErrorSuggestion(errorMessage) {
|
|
150
|
+
const lowerMessage = errorMessage.toLowerCase();
|
|
151
|
+
if (lowerMessage.includes('quota') || lowerMessage.includes('rate limit')) {
|
|
152
|
+
return 'You have exceeded your API quota or rate limit. Wait before making more requests or upgrade your plan';
|
|
153
|
+
}
|
|
154
|
+
if (lowerMessage.includes('unauthorized') || lowerMessage.includes('api key')) {
|
|
155
|
+
return 'Check that your GEMINI_API_KEY is valid and has the necessary permissions';
|
|
156
|
+
}
|
|
157
|
+
if (lowerMessage.includes('forbidden')) {
|
|
158
|
+
return 'Your API key does not have permission for this operation';
|
|
159
|
+
}
|
|
160
|
+
return 'Check your API configuration and try again';
|
|
161
|
+
}
|
|
162
|
+
extractStatusCode(error) {
|
|
163
|
+
if (error && typeof error === 'object' && 'status' in error) {
|
|
164
|
+
return typeof error.status === 'number' ? error.status : undefined;
|
|
165
|
+
}
|
|
166
|
+
return undefined;
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Detect URLs in prompt for automatic URL Context activation
|
|
170
|
+
* @param prompt The prompt text to analyze
|
|
171
|
+
* @returns True if URLs are detected, false otherwise
|
|
172
|
+
*/
|
|
173
|
+
detectUrls(prompt) {
|
|
174
|
+
return URL_PATTERN.test(prompt);
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Creates a new Gemini API client
|
|
179
|
+
* @param config Configuration containing API key and other settings
|
|
180
|
+
* @returns Result containing the client or an error
|
|
181
|
+
*/
|
|
182
|
+
function createGeminiClient(config) {
|
|
183
|
+
try {
|
|
184
|
+
const genai = new genai_1.GoogleGenAI({
|
|
185
|
+
apiKey: config.geminiApiKey,
|
|
186
|
+
});
|
|
187
|
+
return (0, result_1.Ok)(new GeminiClientImpl(genai));
|
|
188
|
+
}
|
|
189
|
+
catch (error) {
|
|
190
|
+
const errorMessage = error instanceof Error ? error.message : 'Unknown error';
|
|
191
|
+
return (0, result_1.Err)(new errors_1.GeminiAPIError(`Failed to initialize Gemini client: ${errorMessage}`, 'Verify your GEMINI_API_KEY is valid and the @google/genai package is properly installed'));
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
//# sourceMappingURL=geminiClient.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"geminiClient.js","sourceRoot":"","sources":["../../src/api/geminiClient.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* URL Context API client for processing URLs and extracting context
|
|
3
|
+
* Uses @google/genai SDK for URL context processing
|
|
4
|
+
*/
|
|
5
|
+
import { type Result } from '../types/result';
|
|
6
|
+
import { NetworkError, URLContextError } from '../utils/errors';
|
|
7
|
+
/**
|
|
8
|
+
* Response from URL context processing
|
|
9
|
+
*/
|
|
10
|
+
export interface UrlContextResponse {
|
|
11
|
+
/** Context content extracted from URLs */
|
|
12
|
+
contextContent: string;
|
|
13
|
+
/** Combined prompt with context and cleaned original prompt */
|
|
14
|
+
combinedPrompt: string;
|
|
15
|
+
/** Additional extracted information */
|
|
16
|
+
extractedInfo: Record<string, unknown>;
|
|
17
|
+
/** Success flag */
|
|
18
|
+
success: boolean;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Mock interface for text generation (to be replaced with real implementation later)
|
|
22
|
+
*/
|
|
23
|
+
interface TextGenerationClient {
|
|
24
|
+
generateText(prompt: string): Promise<Result<{
|
|
25
|
+
text: string;
|
|
26
|
+
}, Error>>;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Client for processing URLs and extracting context
|
|
30
|
+
* Basic implementation for Phase 2 - will be enhanced in later phases
|
|
31
|
+
*/
|
|
32
|
+
export declare class UrlContextClient {
|
|
33
|
+
private textClient;
|
|
34
|
+
/**
|
|
35
|
+
* Maximum number of URLs to process (performance consideration)
|
|
36
|
+
*/
|
|
37
|
+
private static readonly MAX_URLS;
|
|
38
|
+
/**
|
|
39
|
+
* Maximum number of retry attempts
|
|
40
|
+
*/
|
|
41
|
+
private readonly MAX_RETRIES;
|
|
42
|
+
/**
|
|
43
|
+
* Timeout for URL context processing in milliseconds
|
|
44
|
+
*/
|
|
45
|
+
private readonly TIMEOUT_MS;
|
|
46
|
+
constructor(textClient: TextGenerationClient);
|
|
47
|
+
/**
|
|
48
|
+
* Process multiple URLs and extract context for image generation
|
|
49
|
+
* @param urls Array of URLs to process
|
|
50
|
+
* @param originalPrompt Original prompt containing URLs
|
|
51
|
+
* @returns Result containing URL context response with combined prompt or error
|
|
52
|
+
*/
|
|
53
|
+
processUrls(urls: string[], originalPrompt: string): Promise<Result<UrlContextResponse, URLContextError | NetworkError>>;
|
|
54
|
+
/**
|
|
55
|
+
* Process URLs with retry mechanism and timeout
|
|
56
|
+
* @param urls Array of URLs to process
|
|
57
|
+
* @param originalPrompt Original prompt containing URLs
|
|
58
|
+
* @returns Result containing URL context response with retry information
|
|
59
|
+
*/
|
|
60
|
+
processUrlsWithRetry(urls: string[], originalPrompt: string): Promise<Result<UrlContextResponse, URLContextError | NetworkError>>;
|
|
61
|
+
/**
|
|
62
|
+
* Process URLs with timeout protection
|
|
63
|
+
* @param urls Array of URLs to process
|
|
64
|
+
* @param originalPrompt Original prompt containing URLs
|
|
65
|
+
* @returns Result with timeout protection
|
|
66
|
+
*/
|
|
67
|
+
private processUrlsWithTimeout;
|
|
68
|
+
/**
|
|
69
|
+
* Core URL processing logic without retry/timeout
|
|
70
|
+
* @param urls Array of URLs to process
|
|
71
|
+
* @param originalPrompt Original prompt containing URLs
|
|
72
|
+
* @returns Result containing URL context response
|
|
73
|
+
*/
|
|
74
|
+
private processUrlsCore;
|
|
75
|
+
/**
|
|
76
|
+
* Build a context extraction prompt for Gemini API
|
|
77
|
+
* @param urls Array of URLs to process
|
|
78
|
+
* @param originalPrompt Original prompt containing URLs
|
|
79
|
+
* @returns Formatted prompt for context extraction
|
|
80
|
+
*/
|
|
81
|
+
private buildContextPrompt;
|
|
82
|
+
/**
|
|
83
|
+
* Combine URL context with original prompt for image generation
|
|
84
|
+
* @param contextPrompts Array of context content from URLs
|
|
85
|
+
* @param originalPrompt Original prompt containing URLs
|
|
86
|
+
* @param urls Array of processed URLs
|
|
87
|
+
* @returns Combined prompt for image generation
|
|
88
|
+
*/
|
|
89
|
+
private combineContextWithPrompt;
|
|
90
|
+
/**
|
|
91
|
+
* Remove URLs and clean up common action words from prompt
|
|
92
|
+
* @param originalPrompt Original prompt containing URLs
|
|
93
|
+
* @returns Cleaned prompt suitable for final instruction
|
|
94
|
+
*/
|
|
95
|
+
private cleanPromptFromUrls;
|
|
96
|
+
/**
|
|
97
|
+
* Format and clean context content from multiple sources
|
|
98
|
+
* @param contextPrompts Array of raw context content
|
|
99
|
+
* @returns Formatted context content
|
|
100
|
+
*/
|
|
101
|
+
private formatContextContent;
|
|
102
|
+
/**
|
|
103
|
+
* Format the final combined prompt with context and instruction sections
|
|
104
|
+
* @param urls Array of processed URLs
|
|
105
|
+
* @param contextContent Formatted context content
|
|
106
|
+
* @param finalPrompt Final instruction prompt
|
|
107
|
+
* @returns Complete combined prompt
|
|
108
|
+
*/
|
|
109
|
+
private formatCombinedPrompt;
|
|
110
|
+
/**
|
|
111
|
+
* Create a standardized context error from API failure
|
|
112
|
+
* @param originalError The original error from text generation
|
|
113
|
+
* @returns Formatted URLContextError
|
|
114
|
+
*/
|
|
115
|
+
private createContextError;
|
|
116
|
+
/**
|
|
117
|
+
* Create appropriate error based on error type
|
|
118
|
+
* @param error The original error that occurred
|
|
119
|
+
* @returns Formatted error (NetworkError or URLContextError)
|
|
120
|
+
*/
|
|
121
|
+
private createProcessingError;
|
|
122
|
+
/**
|
|
123
|
+
* Parse extracted information from context content
|
|
124
|
+
* @param contextContent The context content to parse
|
|
125
|
+
* @param processedUrlCount Number of URLs that were processed
|
|
126
|
+
* @returns Structured extracted information
|
|
127
|
+
*/
|
|
128
|
+
private parseExtractedInfo;
|
|
129
|
+
/**
|
|
130
|
+
* Check if an error is network-related
|
|
131
|
+
* @param error The error to check
|
|
132
|
+
* @returns True if it's a network error
|
|
133
|
+
*/
|
|
134
|
+
private isNetworkError;
|
|
135
|
+
/**
|
|
136
|
+
* Check if an error is retryable
|
|
137
|
+
* @param error The error to check
|
|
138
|
+
* @returns True if the error should trigger a retry
|
|
139
|
+
*/
|
|
140
|
+
private isRetryableError;
|
|
141
|
+
/**
|
|
142
|
+
* Add a delay for exponential backoff
|
|
143
|
+
* @param ms Milliseconds to delay
|
|
144
|
+
* @returns Promise that resolves after the delay
|
|
145
|
+
*/
|
|
146
|
+
private delay;
|
|
147
|
+
}
|
|
148
|
+
export {};
|
|
149
|
+
//# sourceMappingURL=urlContextClient.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"urlContextClient.d.ts","sourceRoot":"","sources":["../../src/api/urlContextClient.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAGH,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,iBAAiB,CAAA;AACtD,OAAO,EAAE,YAAY,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAA;AAE/D;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,0CAA0C;IAC1C,cAAc,EAAE,MAAM,CAAA;IACtB,+DAA+D;IAC/D,cAAc,EAAE,MAAM,CAAA;IACtB,uCAAuC;IACvC,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;IACtC,mBAAmB;IACnB,OAAO,EAAE,OAAO,CAAA;CACjB;AAED;;GAEG;AACH,UAAU,oBAAoB;IAC5B,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,EAAE,KAAK,CAAC,CAAC,CAAA;CACvE;AAED;;;GAGG;AACH,qBAAa,gBAAgB;IAgBf,OAAO,CAAC,UAAU;IAf9B;;OAEG;IACH,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAK;IAErC;;OAEG;IACH,OAAO,CAAC,QAAQ,CAAC,WAAW,CAAI;IAEhC;;OAEG;IACH,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAQ;gBAEf,UAAU,EAAE,oBAAoB;IAEpD;;;;;OAKG;IACG,WAAW,CACf,IAAI,EAAE,MAAM,EAAE,EACd,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC,MAAM,CAAC,kBAAkB,EAAE,eAAe,GAAG,YAAY,CAAC,CAAC;IAuBtE;;;;;OAKG;IACG,oBAAoB,CACxB,IAAI,EAAE,MAAM,EAAE,EACd,cAAc,EAAE,MAAM,GACrB,OAAO,CAAC,MAAM,CAAC,kBAAkB,EAAE,eAAe,GAAG,YAAY,CAAC,CAAC;IA0DtE;;;;;OAKG;YACW,sBAAsB;IA4BpC;;;;;OAKG;YACW,eAAe;IA2B7B;;;;;OAKG;IACH,OAAO,CAAC,kBAAkB;IAoB1B;;;;;;OAMG;IACH,OAAO,CAAC,wBAAwB;IAYhC;;;;OAIG;IACH,OAAO,CAAC,mBAAmB;IAkB3B;;;;OAIG;IACH,OAAO,CAAC,oBAAoB;IAI5B;;;;;;OAMG;IACH,OAAO,CAAC,oBAAoB;IAW5B;;;;OAIG;IACH,OAAO,CAAC,kBAAkB;IAO1B;;;;OAIG;IACH,OAAO,CAAC,qBAAqB;IAmB7B;;;;;OAKG;IACH,OAAO,CAAC,kBAAkB;IAoB1B;;;;OAIG;IACH,OAAO,CAAC,cAAc;IAqBtB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IAoBxB;;;;OAIG;YACW,KAAK;CAGpB"}
|