@smythos/sre 1.5.32 → 1.5.34
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 +10 -10
- package/dist/index.js.map +1 -1
- package/dist/types/Components/ImageGenerator.class.d.ts +2 -2
- package/dist/types/constants.d.ts +1 -0
- package/dist/types/index.d.ts +1 -1
- package/dist/types/subsystems/LLMManager/LLM.service/connectors/GoogleAI.class.d.ts +3 -0
- package/dist/types/subsystems/LLMManager/LLM.service/connectors/xAI.class.d.ts +121 -0
- package/package.json +2 -1
- package/src/Components/DataSourceLookup.class.ts +2 -1
- package/src/Components/ImageGenerator.class.ts +97 -6
- package/src/Components/LogicAtLeast.class.ts +2 -2
- package/src/Components/LogicAtMost.class.ts +2 -2
- package/src/constants.ts +1 -0
- package/src/index.ts +185 -185
- package/src/index.ts.bak +1 -1
- package/src/subsystems/LLMManager/LLM.service/LLMConnector.ts +3 -3
- package/src/subsystems/LLMManager/LLM.service/connectors/GoogleAI.class.ts +59 -0
- package/src/subsystems/LLMManager/LLM.service/index.ts +1 -1
- package/src/subsystems/Security/Vault.service/connectors/JSONFileVault.class.ts +3 -1
- /package/src/subsystems/LLMManager/LLM.service/connectors/{xAI.ts → xAI.class.ts} +0 -0
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import { IAgent
|
|
1
|
+
import { IAgent } from '@sre/types/Agent.types';
|
|
2
2
|
import Joi from 'joi';
|
|
3
3
|
import { Component } from './Component.class';
|
|
4
4
|
export declare class ImageGenerator extends Component {
|
|
5
5
|
protected configSchema: Joi.ObjectSchema<any>;
|
|
6
6
|
constructor();
|
|
7
7
|
init(): void;
|
|
8
|
-
process(input: any, config: any, agent:
|
|
8
|
+
process(input: any, config: any, agent: IAgent): Promise<{
|
|
9
9
|
_error: string;
|
|
10
10
|
_debug: string;
|
|
11
11
|
Output?: undefined;
|
package/dist/types/index.d.ts
CHANGED
|
@@ -165,7 +165,7 @@ export * from './subsystems/LLMManager/LLM.service/connectors/Groq.class';
|
|
|
165
165
|
export * from './subsystems/LLMManager/LLM.service/connectors/OpenAI.class';
|
|
166
166
|
export * from './subsystems/LLMManager/LLM.service/connectors/Perplexity.class';
|
|
167
167
|
export * from './subsystems/LLMManager/LLM.service/connectors/VertexAI.class';
|
|
168
|
-
export * from './subsystems/LLMManager/LLM.service/connectors/xAI';
|
|
168
|
+
export * from './subsystems/LLMManager/LLM.service/connectors/xAI.class';
|
|
169
169
|
export * from './subsystems/LLMManager/ModelsProvider.service/connectors/JSONModelsProvider.class';
|
|
170
170
|
export * from './subsystems/MemoryManager/Cache.service/connectors/LocalStorageCache.class';
|
|
171
171
|
export * from './subsystems/MemoryManager/Cache.service/connectors/RAMCache.class';
|
|
@@ -12,6 +12,8 @@ export declare class GoogleAIConnector extends LLMConnector {
|
|
|
12
12
|
protected request({ acRequest, body, context }: ILLMRequestFuncParams): Promise<TLLMChatResponse>;
|
|
13
13
|
protected streamRequest({ acRequest, body, context }: ILLMRequestFuncParams): Promise<EventEmitter>;
|
|
14
14
|
protected webSearchRequest({ acRequest, body, context }: ILLMRequestFuncParams): Promise<any>;
|
|
15
|
+
protected imageGenRequest({ body, context }: ILLMRequestFuncParams): Promise<any>;
|
|
16
|
+
protected imageEditRequest({ body, context }: ILLMRequestFuncParams): Promise<any>;
|
|
15
17
|
protected reqBodyAdapter(params: TLLMParams): Promise<TGoogleAIRequestBody>;
|
|
16
18
|
protected reportUsage(usage: UsageMetadataWithThoughtsToken, metadata: {
|
|
17
19
|
modelEntryName: string;
|
|
@@ -49,6 +51,7 @@ export declare class GoogleAIConnector extends LLMConnector {
|
|
|
49
51
|
private prepareMessagesWithFiles;
|
|
50
52
|
private prepareMessagesWithTools;
|
|
51
53
|
private prepareMessagesWithTextQuery;
|
|
54
|
+
private prepareBodyForImageGenRequest;
|
|
52
55
|
private sanitizeFunctionName;
|
|
53
56
|
private uploadFile;
|
|
54
57
|
private getValidFiles;
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
import EventEmitter from 'events';
|
|
2
|
+
import { TLLMParams, ToolData, TLLMMessageBlock, TLLMToolResultMessageBlock, TLLMMessageRole, APIKeySource, ILLMRequestFuncParams, TLLMChatResponse } from '@sre/types/LLM.types';
|
|
3
|
+
import { LLMConnector } from '../LLMConnector';
|
|
4
|
+
type ChatCompletionParams = {
|
|
5
|
+
model: string;
|
|
6
|
+
messages: any[];
|
|
7
|
+
max_tokens?: number;
|
|
8
|
+
temperature?: number;
|
|
9
|
+
top_p?: number;
|
|
10
|
+
frequency_penalty?: number;
|
|
11
|
+
presence_penalty?: number;
|
|
12
|
+
stop?: string | string[];
|
|
13
|
+
response_format?: {
|
|
14
|
+
type: string;
|
|
15
|
+
};
|
|
16
|
+
stream?: boolean;
|
|
17
|
+
stream_options?: {
|
|
18
|
+
include_usage: boolean;
|
|
19
|
+
};
|
|
20
|
+
tools?: any[];
|
|
21
|
+
tool_choice?: any;
|
|
22
|
+
search_parameters?: {
|
|
23
|
+
mode?: 'auto' | 'on' | 'off';
|
|
24
|
+
return_citations?: boolean;
|
|
25
|
+
max_search_results?: number;
|
|
26
|
+
sources?: Array<{
|
|
27
|
+
type: 'web' | 'x' | 'news' | 'rss';
|
|
28
|
+
country?: string;
|
|
29
|
+
excluded_websites?: string[];
|
|
30
|
+
allowed_websites?: string[];
|
|
31
|
+
safe_search?: boolean;
|
|
32
|
+
included_x_handles?: string[];
|
|
33
|
+
excluded_x_handles?: string[];
|
|
34
|
+
post_favorite_count?: number;
|
|
35
|
+
post_view_count?: number;
|
|
36
|
+
links?: string[];
|
|
37
|
+
}>;
|
|
38
|
+
from_date?: string;
|
|
39
|
+
to_date?: string;
|
|
40
|
+
};
|
|
41
|
+
};
|
|
42
|
+
type TUsage = {
|
|
43
|
+
prompt_tokens: number;
|
|
44
|
+
completion_tokens: number;
|
|
45
|
+
total_tokens: number;
|
|
46
|
+
prompt_tokens_details?: {
|
|
47
|
+
text_tokens?: number;
|
|
48
|
+
audio_tokens?: number;
|
|
49
|
+
image_tokens?: number;
|
|
50
|
+
cached_tokens?: number;
|
|
51
|
+
};
|
|
52
|
+
completion_tokens_details?: {
|
|
53
|
+
reasoning_tokens?: number;
|
|
54
|
+
audio_tokens?: number;
|
|
55
|
+
accepted_prediction_tokens?: number;
|
|
56
|
+
rejected_prediction_tokens?: number;
|
|
57
|
+
};
|
|
58
|
+
reasoning_tokens?: number;
|
|
59
|
+
num_sources_used?: number;
|
|
60
|
+
};
|
|
61
|
+
export declare class xAIConnector extends LLMConnector {
|
|
62
|
+
name: string;
|
|
63
|
+
private getClient;
|
|
64
|
+
protected request({ acRequest, body, context }: ILLMRequestFuncParams): Promise<TLLMChatResponse>;
|
|
65
|
+
protected streamRequest({ acRequest, body, context }: ILLMRequestFuncParams): Promise<EventEmitter>;
|
|
66
|
+
protected webSearchRequest({ acRequest, body, context }: ILLMRequestFuncParams): Promise<EventEmitter>;
|
|
67
|
+
protected reqBodyAdapter(params: TLLMParams): Promise<ChatCompletionParams>;
|
|
68
|
+
protected reportUsage(usage: TUsage, metadata: {
|
|
69
|
+
modelEntryName: string;
|
|
70
|
+
keySource: APIKeySource;
|
|
71
|
+
agentId: string;
|
|
72
|
+
teamId: string;
|
|
73
|
+
}): {
|
|
74
|
+
sourceId: string;
|
|
75
|
+
input_tokens: number;
|
|
76
|
+
output_tokens: number;
|
|
77
|
+
input_tokens_cache_write: number;
|
|
78
|
+
input_tokens_cache_read: number;
|
|
79
|
+
reasoning_tokens: number;
|
|
80
|
+
keySource: APIKeySource;
|
|
81
|
+
agentId: string;
|
|
82
|
+
teamId: string;
|
|
83
|
+
};
|
|
84
|
+
formatToolsConfig({ type, toolDefinitions, toolChoice }: {
|
|
85
|
+
type?: string;
|
|
86
|
+
toolDefinitions: any;
|
|
87
|
+
toolChoice?: string;
|
|
88
|
+
}): {
|
|
89
|
+
tools: any[];
|
|
90
|
+
tool_choice: string;
|
|
91
|
+
} | {
|
|
92
|
+
tools?: undefined;
|
|
93
|
+
tool_choice?: undefined;
|
|
94
|
+
};
|
|
95
|
+
transformToolMessageBlocks({ messageBlock, toolsData, }: {
|
|
96
|
+
messageBlock: TLLMMessageBlock;
|
|
97
|
+
toolsData: ToolData[];
|
|
98
|
+
}): TLLMToolResultMessageBlock[];
|
|
99
|
+
getConsistentMessages(messages: any): {
|
|
100
|
+
role: TLLMMessageRole;
|
|
101
|
+
content?: string | {
|
|
102
|
+
text: string;
|
|
103
|
+
}[] | Array<import("@anthropic-ai/sdk/resources").TextBlockParam | import("@anthropic-ai/sdk/resources").ImageBlockParam | import("@anthropic-ai/sdk/resources").ToolUseBlockParam | import("@anthropic-ai/sdk/resources").ToolResultBlockParam>;
|
|
104
|
+
parts?: {
|
|
105
|
+
text?: string;
|
|
106
|
+
functionCall?: {
|
|
107
|
+
name: string;
|
|
108
|
+
args: string;
|
|
109
|
+
};
|
|
110
|
+
functionResponse?: {
|
|
111
|
+
name: string;
|
|
112
|
+
response: {
|
|
113
|
+
name: string;
|
|
114
|
+
content: string;
|
|
115
|
+
};
|
|
116
|
+
};
|
|
117
|
+
}[];
|
|
118
|
+
tool_calls?: ToolData[];
|
|
119
|
+
}[];
|
|
120
|
+
}
|
|
121
|
+
export {};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@smythos/sre",
|
|
3
|
-
"version": "1.5.
|
|
3
|
+
"version": "1.5.34",
|
|
4
4
|
"description": "Smyth Runtime Environment",
|
|
5
5
|
"author": "Alaa-eddine KADDOURI",
|
|
6
6
|
"license": "MIT",
|
|
@@ -51,6 +51,7 @@
|
|
|
51
51
|
"@faker-js/faker": "^9.8.0",
|
|
52
52
|
"@google-cloud/vertexai": "^1.7.0",
|
|
53
53
|
"@google/generative-ai": "^0.14.1",
|
|
54
|
+
"@google/genai": "^1.10.0",
|
|
54
55
|
"@huggingface/inference": "^2.8.0",
|
|
55
56
|
"@modelcontextprotocol/sdk": "^1.10.1",
|
|
56
57
|
"@pinecone-database/pinecone": "^3.0.0",
|
|
@@ -17,7 +17,8 @@ class LLMInference {
|
|
|
17
17
|
|
|
18
18
|
export class DataSourceLookup extends Component {
|
|
19
19
|
protected configSchema = Joi.object({
|
|
20
|
-
topK: Joi.string()
|
|
20
|
+
topK: Joi.alternatives([Joi.string(), Joi.number()]) // Value is now a number; keep string fallback for backward compatibility.
|
|
21
|
+
|
|
21
22
|
.custom(validateInteger({ min: 0 }), 'custom range validation')
|
|
22
23
|
.label('Result Count'),
|
|
23
24
|
model: Joi.string().valid('gpt-4o-mini', 'gpt-4', 'gpt-3.5-turbo', 'gpt-4', 'gpt-3.5-turbo-16k').optional(),
|
|
@@ -5,7 +5,7 @@ import { OpenAI } from 'openai';
|
|
|
5
5
|
|
|
6
6
|
import { TemplateString } from '@sre/helpers/TemplateString.helper';
|
|
7
7
|
import { LLMInference } from '@sre/LLMManager/LLM.inference';
|
|
8
|
-
import { IAgent
|
|
8
|
+
import { IAgent } from '@sre/types/Agent.types';
|
|
9
9
|
import { APIKeySource, GenerateImageConfig } from '@sre/types/LLM.types';
|
|
10
10
|
import Joi from 'joi';
|
|
11
11
|
import { Component } from './Component.class';
|
|
@@ -13,7 +13,6 @@ import { Component } from './Component.class';
|
|
|
13
13
|
import { SystemEvents } from '@sre/Core/SystemEvents';
|
|
14
14
|
import { AccessCandidate } from '@sre/Security/AccessControl/AccessCandidate.class';
|
|
15
15
|
|
|
16
|
-
import appConfig from '@sre/config';
|
|
17
16
|
import { BUILT_IN_MODEL_PREFIX, SUPPORTED_MIME_TYPES_MAP } from '@sre/constants';
|
|
18
17
|
import { BinaryInput } from '@sre/helpers/BinaryInput.helper';
|
|
19
18
|
import { normalizeImageInput } from '@sre/utils/data.utils';
|
|
@@ -45,6 +44,12 @@ const IMAGE_GEN_COST_MAP = {
|
|
|
45
44
|
},
|
|
46
45
|
};
|
|
47
46
|
|
|
47
|
+
// Imagen 4 cost map - fixed cost per image
|
|
48
|
+
const IMAGEN_4_COST_MAP = {
|
|
49
|
+
'imagen-4': 0.04, // Standard Imagen 4
|
|
50
|
+
'imagen-4-ultra': 0.06, // Imagen 4 Ultra
|
|
51
|
+
};
|
|
52
|
+
|
|
48
53
|
export class ImageGenerator extends Component {
|
|
49
54
|
protected configSchema = Joi.object({
|
|
50
55
|
model: Joi.string().max(100).required(),
|
|
@@ -73,12 +78,17 @@ export class ImageGenerator extends Component {
|
|
|
73
78
|
// #region GPT model
|
|
74
79
|
size: Joi.string().optional().allow('').max(100).label('Size'),
|
|
75
80
|
// #endregion
|
|
81
|
+
|
|
82
|
+
// #region Google AI model
|
|
83
|
+
aspectRatio: Joi.string().valid('1:1', '3:4', '4:3', '9:16', '16:9').optional().allow('').label('Aspect Ratio'),
|
|
84
|
+
personGeneration: Joi.string().valid('dont_allow', 'allow_adult', 'allow_all').optional().allow('').label('Person Generation'),
|
|
85
|
+
// #endregion
|
|
76
86
|
});
|
|
77
87
|
constructor() {
|
|
78
88
|
super();
|
|
79
89
|
}
|
|
80
90
|
init() {}
|
|
81
|
-
async process(input, config, agent:
|
|
91
|
+
async process(input, config, agent: IAgent) {
|
|
82
92
|
await super.process(input, config, agent);
|
|
83
93
|
|
|
84
94
|
const logger = this.createComponentLogger(agent, config);
|
|
@@ -134,6 +144,7 @@ enum MODEL_FAMILY {
|
|
|
134
144
|
GPT = 'gpt',
|
|
135
145
|
RUNWARE = 'runware',
|
|
136
146
|
DALL_E = 'dall-e',
|
|
147
|
+
IMAGEN = 'imagen',
|
|
137
148
|
}
|
|
138
149
|
|
|
139
150
|
const imageGenerator = {
|
|
@@ -319,6 +330,75 @@ const imageGenerator = {
|
|
|
319
330
|
await runware.disconnect();
|
|
320
331
|
}
|
|
321
332
|
},
|
|
333
|
+
[MODEL_FAMILY.IMAGEN]: async ({ model, prompt, config, logger, agent, input }) => {
|
|
334
|
+
try {
|
|
335
|
+
const llmInference: LLMInference = await LLMInference.getInstance(model, AccessCandidate.agent(agent.id));
|
|
336
|
+
|
|
337
|
+
// if the llm is undefined, then it means we removed the model from our system
|
|
338
|
+
if (!llmInference.connector) {
|
|
339
|
+
return {
|
|
340
|
+
_error: `The model '${model}' is not available. Please try a different one.`,
|
|
341
|
+
_debug: logger.output,
|
|
342
|
+
};
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
const files: any[] = parseFiles(input, config);
|
|
346
|
+
|
|
347
|
+
// Imagen models only support image generation, not image editing
|
|
348
|
+
if (files.length > 0) {
|
|
349
|
+
throw new Error('Google AI Image Generation Error: Image editing is not supported. Imagen models only support image generation.');
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
let args: GenerateImageConfig & {
|
|
353
|
+
aspectRatio?: string;
|
|
354
|
+
numberOfImages?: number;
|
|
355
|
+
personGeneration?: string;
|
|
356
|
+
} = {
|
|
357
|
+
model,
|
|
358
|
+
aspectRatio: config?.data?.aspectRatio || config?.data?.size || '1:1',
|
|
359
|
+
numberOfImages: config?.data?.numberOfImages || 1,
|
|
360
|
+
personGeneration: config?.data?.personGeneration || 'allow_adult',
|
|
361
|
+
};
|
|
362
|
+
|
|
363
|
+
const response = await llmInference.imageGenRequest({ query: prompt, params: { ...args, agentId: agent.id } });
|
|
364
|
+
|
|
365
|
+
// Calculate fixed cost for Imagen 4
|
|
366
|
+
const modelName = model.replace(BUILT_IN_MODEL_PREFIX, '');
|
|
367
|
+
const cost = IMAGEN_4_COST_MAP[modelName];
|
|
368
|
+
|
|
369
|
+
if (cost && cost > 0) {
|
|
370
|
+
// Multiply by number of images generated
|
|
371
|
+
const numberOfImages = args.numberOfImages || 1;
|
|
372
|
+
const totalCost = cost * numberOfImages;
|
|
373
|
+
|
|
374
|
+
// Report fixed cost usage
|
|
375
|
+
imageGenerator.reportUsage(
|
|
376
|
+
{ cost: totalCost },
|
|
377
|
+
{
|
|
378
|
+
modelEntryName: model,
|
|
379
|
+
keySource: model.startsWith(BUILT_IN_MODEL_PREFIX) ? APIKeySource.Smyth : APIKeySource.User,
|
|
380
|
+
agentId: agent.id,
|
|
381
|
+
teamId: agent.teamId,
|
|
382
|
+
}
|
|
383
|
+
);
|
|
384
|
+
}
|
|
385
|
+
|
|
386
|
+
let output = response?.data?.[0]?.b64_json;
|
|
387
|
+
|
|
388
|
+
if (output) {
|
|
389
|
+
const binaryInput = BinaryInput.from(output);
|
|
390
|
+
const agentId = typeof agent == 'object' && agent.id ? agent.id : agent;
|
|
391
|
+
const smythFile = await binaryInput.getJsonData(AccessCandidate.agent(agentId));
|
|
392
|
+
return { output: smythFile };
|
|
393
|
+
} else {
|
|
394
|
+
// Handle URL response format
|
|
395
|
+
output = response?.data?.[0]?.url;
|
|
396
|
+
return { output };
|
|
397
|
+
}
|
|
398
|
+
} catch (error: any) {
|
|
399
|
+
throw new Error(`Google AI Image Generation Error: ${error?.message || JSON.stringify(error)}`);
|
|
400
|
+
}
|
|
401
|
+
},
|
|
322
402
|
reportTokenUsage(usage: TokenUsage, metadata: { modelEntryName: string; keySource: APIKeySource; agentId: string; teamId: string }) {
|
|
323
403
|
// SmythOS (built-in) models have a prefix, so we need to remove it to get the model name
|
|
324
404
|
const modelName = metadata.modelEntryName.replace(BUILT_IN_MODEL_PREFIX, '');
|
|
@@ -361,6 +441,7 @@ const imageGenerator = {
|
|
|
361
441
|
enum PROVIDERS {
|
|
362
442
|
OPENAI = 'OpenAI',
|
|
363
443
|
RUNWARE = 'Runware',
|
|
444
|
+
GOOGLEAI = 'GoogleAI',
|
|
364
445
|
}
|
|
365
446
|
|
|
366
447
|
/**
|
|
@@ -368,10 +449,11 @@ enum PROVIDERS {
|
|
|
368
449
|
* @param model The model identifier
|
|
369
450
|
* @returns The model family or null if not recognized
|
|
370
451
|
*/
|
|
371
|
-
async function getModelFamily(model: string, agent:
|
|
452
|
+
async function getModelFamily(model: string, agent: IAgent): Promise<string | null> {
|
|
372
453
|
if (await isGPTModel(model)) return MODEL_FAMILY.GPT;
|
|
373
454
|
if (await isRunwareModel(model, agent)) return MODEL_FAMILY.RUNWARE;
|
|
374
455
|
if (await isDallEModel(model)) return MODEL_FAMILY.DALL_E;
|
|
456
|
+
if (await isGoogleAIModel(model, agent)) return MODEL_FAMILY.IMAGEN;
|
|
375
457
|
|
|
376
458
|
return null;
|
|
377
459
|
}
|
|
@@ -380,15 +462,24 @@ function isGPTModel(model: string) {
|
|
|
380
462
|
return model?.replace(BUILT_IN_MODEL_PREFIX, '')?.startsWith(MODEL_FAMILY.GPT);
|
|
381
463
|
}
|
|
382
464
|
|
|
383
|
-
async function isRunwareModel(model: string, agent:
|
|
465
|
+
async function isRunwareModel(model: string, agent: IAgent): Promise<boolean> {
|
|
384
466
|
const provider = await agent.modelsProvider.getProvider(model);
|
|
385
|
-
return provider === PROVIDERS.RUNWARE || provider
|
|
467
|
+
return provider === PROVIDERS.RUNWARE || provider?.toLowerCase() === PROVIDERS.RUNWARE.toLowerCase();
|
|
386
468
|
}
|
|
387
469
|
|
|
388
470
|
function isDallEModel(model: string) {
|
|
389
471
|
return model?.replace(BUILT_IN_MODEL_PREFIX, '')?.startsWith(MODEL_FAMILY.DALL_E);
|
|
390
472
|
}
|
|
391
473
|
|
|
474
|
+
async function isGoogleAIModel(model: string, agent: IAgent): Promise<boolean> {
|
|
475
|
+
const provider = await agent.modelsProvider.getProvider(model);
|
|
476
|
+
return (
|
|
477
|
+
provider === PROVIDERS.GOOGLEAI ||
|
|
478
|
+
provider?.toLowerCase() === PROVIDERS.GOOGLEAI.toLowerCase() ||
|
|
479
|
+
model?.replace(BUILT_IN_MODEL_PREFIX, '')?.includes('imagen')
|
|
480
|
+
);
|
|
481
|
+
}
|
|
482
|
+
|
|
392
483
|
function parseFiles(input: any, config: any) {
|
|
393
484
|
const mediaTypes = ['Image', 'Audio', 'Video', 'Binary'];
|
|
394
485
|
|
|
@@ -6,7 +6,7 @@ import { Component } from './Component.class';
|
|
|
6
6
|
export class LogicAtLeast extends Component {
|
|
7
7
|
protected configSchema = Joi.object({
|
|
8
8
|
// TODO (Forhad): Need to check if min and max work instead of the custom validateInteger
|
|
9
|
-
minSetInputs: Joi.string()
|
|
9
|
+
minSetInputs: Joi.alternatives([Joi.string(), Joi.number()]) // Value is now a number; keep string fallback for backward compatibility.
|
|
10
10
|
.custom(validateInteger({ min: 0, max: 9 }), 'custom range validation')
|
|
11
11
|
.label('Minimum Inputs'),
|
|
12
12
|
});
|
|
@@ -21,7 +21,7 @@ export class LogicAtLeast extends Component {
|
|
|
21
21
|
const logger = this.createComponentLogger(agent, config);
|
|
22
22
|
const result: any = { Output: undefined };
|
|
23
23
|
|
|
24
|
-
if (
|
|
24
|
+
if (config.data.minSetInputs === '' || isNaN(Number(config.data.minSetInputs))) {
|
|
25
25
|
return result;
|
|
26
26
|
}
|
|
27
27
|
|
|
@@ -6,7 +6,7 @@ import { Component } from './Component.class';
|
|
|
6
6
|
export class LogicAtMost extends Component {
|
|
7
7
|
protected configSchema = Joi.object({
|
|
8
8
|
// TODO (Forhad): Need to check if min and max work instead of the custom validateInteger
|
|
9
|
-
maxSetInputs: Joi.string()
|
|
9
|
+
maxSetInputs: Joi.alternatives([Joi.string(), Joi.number()]) // Value is now a number; keep string fallback for backward compatibility.
|
|
10
10
|
.custom(validateInteger({ min: 0, max: 9 }), 'custom range validation')
|
|
11
11
|
.label('Maximum Inputs'),
|
|
12
12
|
});
|
|
@@ -20,7 +20,7 @@ export class LogicAtMost extends Component {
|
|
|
20
20
|
await super.process(input, config, agent);
|
|
21
21
|
const result: any = { Output: undefined };
|
|
22
22
|
|
|
23
|
-
if (
|
|
23
|
+
if (config.data.maxSetInputs === '' || isNaN(Number(config.data.maxSetInputs))) {
|
|
24
24
|
return result;
|
|
25
25
|
}
|
|
26
26
|
|
package/src/constants.ts
CHANGED
|
@@ -76,6 +76,7 @@ export const SUPPORTED_MIME_TYPES_MAP = {
|
|
|
76
76
|
},
|
|
77
77
|
GoogleAI: {
|
|
78
78
|
image: ['image/png', 'image/jpeg', 'image/jpg', 'image/webp', 'image/heic', 'image/heif'],
|
|
79
|
+
imageGen: ['image/png', 'image/jpeg', 'image/jpg', 'image/webp'],
|
|
79
80
|
video: [
|
|
80
81
|
'video/mp4',
|
|
81
82
|
'video/mpeg',
|