genaicode 0.0.37 → 0.2.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/README.md +3 -1
- package/bin/genaicode-dev.js +11 -0
- package/bin/genaicode.cjs +15 -1
- package/dist/ai-service/ai-studio.d.ts +6 -0
- package/dist/ai-service/ai-studio.js +135 -0
- package/dist/ai-service/ai-studio.js.map +1 -0
- package/dist/ai-service/anthropic.d.ts +6 -0
- package/dist/ai-service/anthropic.js +135 -0
- package/dist/ai-service/anthropic.js.map +1 -0
- package/dist/ai-service/chat-gpt.d.ts +5 -0
- package/dist/ai-service/chat-gpt.js +132 -0
- package/dist/ai-service/chat-gpt.js.map +1 -0
- package/dist/ai-service/common.d.ts +58 -0
- package/dist/ai-service/common.js +38 -0
- package/dist/ai-service/common.js.map +1 -0
- package/dist/ai-service/common.test.d.ts +1 -0
- package/dist/ai-service/common.test.js +85 -0
- package/dist/ai-service/common.test.js.map +1 -0
- package/dist/ai-service/dall-e.d.ts +14 -0
- package/dist/ai-service/dall-e.js +48 -0
- package/dist/ai-service/dall-e.js.map +1 -0
- package/dist/ai-service/vertex-ai-claude.d.ts +5 -0
- package/dist/ai-service/vertex-ai-claude.js +94 -0
- package/dist/ai-service/vertex-ai-claude.js.map +1 -0
- package/dist/ai-service/vertex-ai-imagen.d.ts +14 -0
- package/dist/ai-service/vertex-ai-imagen.js +77 -0
- package/dist/ai-service/vertex-ai-imagen.js.map +1 -0
- package/dist/ai-service/vertex-ai.d.ts +7 -0
- package/dist/ai-service/vertex-ai.js +142 -0
- package/dist/ai-service/vertex-ai.js.map +1 -0
- package/dist/cli/cli-options.d.ts +10 -0
- package/dist/cli/cli-options.js +124 -0
- package/dist/cli/cli-options.js.map +1 -0
- package/dist/cli/cli-options.test.d.ts +1 -0
- package/dist/cli/cli-options.test.js +34 -0
- package/dist/cli/cli-options.test.js.map +1 -0
- package/dist/cli/cli-params.d.ts +30 -0
- package/dist/cli/cli-params.js +109 -0
- package/dist/cli/cli-params.js.map +1 -0
- package/dist/cli/cli-params.test.d.ts +1 -0
- package/dist/cli/cli-params.test.js +38 -0
- package/dist/cli/cli-params.test.js.map +1 -0
- package/dist/cli/service-autodetect.d.ts +2 -0
- package/dist/cli/service-autodetect.js +17 -0
- package/dist/cli/service-autodetect.js.map +1 -0
- package/dist/cli/service-autodetect.test.d.ts +1 -0
- package/dist/cli/service-autodetect.test.js +38 -0
- package/dist/cli/service-autodetect.test.js.map +1 -0
- package/dist/cli/validate-cli-params.d.ts +18 -0
- package/dist/cli/validate-cli-params.js +129 -0
- package/dist/cli/validate-cli-params.js.map +1 -0
- package/dist/cli/validate-cli-params.test.d.ts +1 -0
- package/dist/cli/validate-cli-params.test.js +106 -0
- package/dist/cli/validate-cli-params.test.js.map +1 -0
- package/dist/files/file-utils.d.ts +2 -0
- package/dist/files/file-utils.js +7 -0
- package/dist/files/file-utils.js.map +1 -0
- package/dist/files/file-utils.test.d.ts +1 -0
- package/dist/files/file-utils.test.js +18 -0
- package/dist/files/file-utils.test.js.map +1 -0
- package/dist/files/find-files.d.ts +8 -0
- package/dist/files/find-files.js +76 -0
- package/dist/files/find-files.js.map +1 -0
- package/dist/files/read-files.d.ts +18 -0
- package/dist/files/read-files.js +66 -0
- package/dist/files/read-files.js.map +1 -0
- package/dist/files/read-files.test.d.ts +1 -0
- package/dist/files/read-files.test.js +88 -0
- package/dist/files/read-files.test.js.map +1 -0
- package/dist/files/temp-buffer.d.ts +2 -0
- package/dist/files/temp-buffer.js +12 -0
- package/dist/files/temp-buffer.js.map +1 -0
- package/dist/files/update-files.d.ts +6 -0
- package/dist/files/update-files.js +197 -0
- package/dist/files/update-files.js.map +1 -0
- package/dist/images/ensure-alpha.d.ts +1 -0
- package/dist/images/ensure-alpha.js +5 -0
- package/dist/images/ensure-alpha.js.map +1 -0
- package/dist/images/imgly-remove-background.d.ts +2 -0
- package/dist/images/imgly-remove-background.js +21 -0
- package/dist/images/imgly-remove-background.js.map +1 -0
- package/dist/images/resize-image.d.ts +19 -0
- package/dist/images/resize-image.js +22 -0
- package/dist/images/resize-image.js.map +1 -0
- package/dist/images/split-image.d.ts +18 -0
- package/dist/images/split-image.js +25 -0
- package/dist/images/split-image.js.map +1 -0
- package/dist/main/codegen-interactive-utils.d.ts +8 -0
- package/dist/main/codegen-interactive-utils.js +148 -0
- package/dist/main/codegen-interactive-utils.js.map +1 -0
- package/dist/main/codegen-interactive.d.ts +2 -0
- package/dist/main/codegen-interactive.js +68 -0
- package/dist/main/codegen-interactive.js.map +1 -0
- package/dist/main/codegen-types.d.ts +28 -0
- package/dist/main/codegen-types.js +2 -0
- package/dist/main/codegen-types.js.map +1 -0
- package/dist/main/codegen.d.ts +4 -0
- package/dist/main/codegen.js +164 -0
- package/dist/main/codegen.js.map +1 -0
- package/dist/main/codegen.test.d.ts +2 -0
- package/dist/main/codegen.test.js +273 -0
- package/dist/main/codegen.test.js.map +1 -0
- package/dist/main/config-lib.d.ts +16 -0
- package/dist/main/config-lib.js +28 -0
- package/dist/main/config-lib.js.map +1 -0
- package/dist/main/config-lib.test.d.ts +1 -0
- package/dist/main/config-lib.test.js +64 -0
- package/dist/main/config-lib.test.js.map +1 -0
- package/dist/main/config.d.ts +6 -0
- package/{src → dist}/main/config.js +28 -22
- package/dist/main/config.js.map +1 -0
- package/dist/main/interactive/codegen-interactive.d.ts +2 -0
- package/dist/main/interactive/codegen-interactive.js +55 -0
- package/dist/main/interactive/codegen-interactive.js.map +1 -0
- package/dist/main/interactive/codegen-interactive.test.d.ts +4 -0
- package/dist/main/interactive/codegen-interactive.test.js +77 -0
- package/dist/main/interactive/codegen-interactive.test.js.map +1 -0
- package/dist/main/interactive/codegen-worker.d.ts +3 -0
- package/dist/main/interactive/codegen-worker.js +47 -0
- package/dist/main/interactive/codegen-worker.js.map +1 -0
- package/dist/main/interactive/common.d.ts +5 -0
- package/dist/main/interactive/common.js +51 -0
- package/dist/main/interactive/common.js.map +1 -0
- package/dist/main/interactive/configure.d.ts +2 -0
- package/dist/main/interactive/configure.js +99 -0
- package/dist/main/interactive/configure.js.map +1 -0
- package/dist/main/interactive/error-handling.d.ts +4 -0
- package/dist/main/interactive/error-handling.js +49 -0
- package/dist/main/interactive/error-handling.js.map +1 -0
- package/dist/main/interactive/help.d.ts +1 -0
- package/dist/main/interactive/help.js +22 -0
- package/dist/main/interactive/help.js.map +1 -0
- package/dist/main/interactive/process-comments.d.ts +2 -0
- package/dist/main/interactive/process-comments.js +39 -0
- package/dist/main/interactive/process-comments.js.map +1 -0
- package/dist/main/interactive/select-ai-service.d.ts +2 -0
- package/dist/main/interactive/select-ai-service.js +27 -0
- package/dist/main/interactive/select-ai-service.js.map +1 -0
- package/dist/main/interactive/task-file.d.ts +2 -0
- package/dist/main/interactive/task-file.js +28 -0
- package/dist/main/interactive/task-file.js.map +1 -0
- package/dist/main/interactive/text-prompt.d.ts +2 -0
- package/dist/main/interactive/text-prompt.js +18 -0
- package/dist/main/interactive/text-prompt.js.map +1 -0
- package/dist/main/interactive/user-interrupt.d.ts +1 -0
- package/dist/main/interactive/user-interrupt.js +36 -0
- package/dist/main/interactive/user-interrupt.js.map +1 -0
- package/dist/main/interactive/worker-script.d.ts +1 -0
- package/dist/main/interactive/worker-script.js +24 -0
- package/dist/main/interactive/worker-script.js.map +1 -0
- package/dist/main/interactive/worker.d.ts +2 -0
- package/dist/main/interactive/worker.js +55 -0
- package/dist/main/interactive/worker.js.map +1 -0
- package/dist/prompt/function-calling-validate.d.ts +3 -0
- package/dist/prompt/function-calling-validate.js +33 -0
- package/dist/prompt/function-calling-validate.js.map +1 -0
- package/dist/prompt/function-calling.d.ts +5 -0
- package/{src → dist}/prompt/function-calling.js +25 -24
- package/dist/prompt/function-calling.js.map +1 -0
- package/dist/prompt/function-defs/ask-question.d.ts +65 -0
- package/dist/prompt/function-defs/ask-question.js +67 -0
- package/dist/prompt/function-defs/ask-question.js.map +1 -0
- package/dist/prompt/function-defs/codegen-summary.d.ts +63 -0
- package/dist/prompt/function-defs/codegen-summary.js +80 -0
- package/dist/prompt/function-defs/codegen-summary.js.map +1 -0
- package/dist/prompt/function-defs/create-directory.d.ts +21 -0
- package/dist/prompt/function-defs/create-directory.js +22 -0
- package/dist/prompt/function-defs/create-directory.js.map +1 -0
- package/dist/prompt/function-defs/create-file.d.ts +25 -0
- package/dist/prompt/function-defs/create-file.js +26 -0
- package/dist/prompt/function-defs/create-file.js.map +1 -0
- package/dist/prompt/function-defs/delete-file.d.ts +21 -0
- package/dist/prompt/function-defs/delete-file.js +22 -0
- package/dist/prompt/function-defs/delete-file.js.map +1 -0
- package/dist/prompt/function-defs/download-file.d.ts +25 -0
- package/dist/prompt/function-defs/download-file.js +26 -0
- package/dist/prompt/function-defs/download-file.js.map +1 -0
- package/dist/prompt/function-defs/explanation.d.ts +17 -0
- package/dist/prompt/function-defs/explanation.js +18 -0
- package/dist/prompt/function-defs/explanation.js.map +1 -0
- package/dist/prompt/function-defs/generate-image.d.ts +41 -0
- package/dist/prompt/function-defs/generate-image.js +42 -0
- package/dist/prompt/function-defs/generate-image.js.map +1 -0
- package/dist/prompt/function-defs/get-image-assets.d.ts +20 -0
- package/dist/prompt/function-defs/get-image-assets.js +21 -0
- package/dist/prompt/function-defs/get-image-assets.js.map +1 -0
- package/dist/prompt/function-defs/get-source-code.d.ts +20 -0
- package/dist/prompt/function-defs/get-source-code.js +21 -0
- package/dist/prompt/function-defs/get-source-code.js.map +1 -0
- package/dist/prompt/function-defs/imgly-remove-background.d.ts +25 -0
- package/dist/prompt/function-defs/imgly-remove-background.js +26 -0
- package/dist/prompt/function-defs/imgly-remove-background.js.map +1 -0
- package/dist/prompt/function-defs/move-file.d.ts +25 -0
- package/dist/prompt/function-defs/move-file.js +26 -0
- package/dist/prompt/function-defs/move-file.js.map +1 -0
- package/dist/prompt/function-defs/patch-file.d.ts +25 -0
- package/dist/prompt/function-defs/patch-file.js +39 -0
- package/dist/prompt/function-defs/patch-file.js.map +1 -0
- package/dist/prompt/function-defs/resize-image.d.ts +36 -0
- package/dist/prompt/function-defs/resize-image.js +37 -0
- package/dist/prompt/function-defs/resize-image.js.map +1 -0
- package/dist/prompt/function-defs/split-image.d.ts +57 -0
- package/dist/prompt/function-defs/split-image.js +46 -0
- package/dist/prompt/function-defs/split-image.js.map +1 -0
- package/dist/prompt/function-defs/update-file.d.ts +25 -0
- package/dist/prompt/function-defs/update-file.js +26 -0
- package/dist/prompt/function-defs/update-file.js.map +1 -0
- package/dist/prompt/limits.d.ts +3 -0
- package/dist/prompt/limits.js +19 -0
- package/dist/prompt/limits.js.map +1 -0
- package/dist/prompt/limits.test.d.ts +1 -0
- package/dist/prompt/limits.test.js +35 -0
- package/dist/prompt/limits.test.js.map +1 -0
- package/dist/prompt/prompt-codegen.d.ts +9 -0
- package/dist/prompt/prompt-codegen.js +90 -0
- package/dist/prompt/prompt-codegen.js.map +1 -0
- package/dist/prompt/prompt-codegen.test.d.ts +1 -0
- package/dist/prompt/prompt-codegen.test.js +98 -0
- package/dist/prompt/prompt-codegen.test.js.map +1 -0
- package/dist/prompt/prompt-consts.d.ts +1 -0
- package/{src → dist}/prompt/prompt-consts.js +1 -0
- package/dist/prompt/prompt-consts.js.map +1 -0
- package/dist/prompt/prompt-service-ask-question.test.d.ts +3 -0
- package/dist/prompt/prompt-service-ask-question.test.js +142 -0
- package/dist/prompt/prompt-service-ask-question.test.js.map +1 -0
- package/dist/prompt/prompt-service.d.ts +28 -0
- package/dist/prompt/prompt-service.js +163 -0
- package/dist/prompt/prompt-service.js.map +1 -0
- package/dist/prompt/prompt-service.test.d.ts +1 -0
- package/dist/prompt/prompt-service.test.js +531 -0
- package/dist/prompt/prompt-service.test.js.map +1 -0
- package/dist/prompt/steps/step-ask-question.d.ts +6 -0
- package/dist/prompt/steps/step-ask-question.js +82 -0
- package/dist/prompt/steps/step-ask-question.js.map +1 -0
- package/dist/prompt/steps/step-generate-image.d.ts +2 -0
- package/dist/prompt/steps/step-generate-image.js +29 -0
- package/dist/prompt/steps/step-generate-image.js.map +1 -0
- package/dist/prompt/steps/step-validate-recover.d.ts +13 -0
- package/dist/prompt/steps/step-validate-recover.js +51 -0
- package/dist/prompt/steps/step-validate-recover.js.map +1 -0
- package/dist/prompt/steps/step-verify-patch.d.ts +7 -0
- package/dist/prompt/steps/step-verify-patch.js +41 -0
- package/dist/prompt/steps/step-verify-patch.js.map +1 -0
- package/dist/prompt/steps/steps-types.d.ts +4 -0
- package/dist/prompt/steps/steps-types.js +6 -0
- package/dist/prompt/steps/steps-types.js.map +1 -0
- package/dist/prompt/systemprompt.d.ts +3 -0
- package/dist/prompt/systemprompt.js +47 -0
- package/dist/prompt/systemprompt.js.map +1 -0
- package/dist/prompt/systemprompt.test.d.ts +3 -0
- package/dist/prompt/systemprompt.test.js +46 -0
- package/dist/prompt/systemprompt.test.js.map +1 -0
- package/package.json +15 -5
- package/bin/genaicode.js +0 -5
- package/bin/vertex-monkey-patch.cjs +0 -33
- package/src/ai-service/anthropic.js +0 -126
- package/src/ai-service/chat-gpt.js +0 -126
- package/src/ai-service/common.js +0 -49
- package/src/ai-service/common.test.js +0 -107
- package/src/ai-service/dall-e.js +0 -50
- package/src/ai-service/vertex-ai-claude.js +0 -99
- package/src/ai-service/vertex-ai-imagen.js +0 -78
- package/src/ai-service/vertex-ai.js +0 -156
- package/src/cli/cli-options.js +0 -132
- package/src/cli/cli-options.test.js +0 -50
- package/src/cli/cli-params.js +0 -114
- package/src/cli/cli-params.test.js +0 -43
- package/src/cli/service-autodetect.js +0 -11
- package/src/cli/service-autodetect.test.js +0 -43
- package/src/cli/validate-cli-params.js +0 -137
- package/src/cli/validate-cli-params.test.js +0 -134
- package/src/files/file-utils.js +0 -7
- package/src/files/file-utils.test.js +0 -21
- package/src/files/find-files.js +0 -86
- package/src/files/read-files.js +0 -65
- package/src/files/read-files.test.js +0 -103
- package/src/files/temp-buffer.js +0 -13
- package/src/files/update-files.js +0 -205
- package/src/images/ensure-alpha.js +0 -5
- package/src/images/imgly-remove-background.js +0 -23
- package/src/images/resize-image.js +0 -23
- package/src/images/split-image.js +0 -26
- package/src/main/codegen.js +0 -120
- package/src/main/codegen.test.js +0 -335
- package/src/main/config-lib.js +0 -33
- package/src/main/config-lib.test.js +0 -80
- package/src/prompt/function-calling-validate.js +0 -25
- package/src/prompt/function-defs/ask-question.js +0 -33
- package/src/prompt/function-defs/codegen-summary.js +0 -87
- package/src/prompt/function-defs/create-directory.js +0 -21
- package/src/prompt/function-defs/create-file.js +0 -26
- package/src/prompt/function-defs/delete-file.js +0 -21
- package/src/prompt/function-defs/download-file.js +0 -25
- package/src/prompt/function-defs/explanation.js +0 -17
- package/src/prompt/function-defs/generate-image.js +0 -51
- package/src/prompt/function-defs/get-image-assets.js +0 -21
- package/src/prompt/function-defs/get-source-code.js +0 -21
- package/src/prompt/function-defs/imgly-remove-background.js +0 -25
- package/src/prompt/function-defs/move-file.js +0 -25
- package/src/prompt/function-defs/patch-file.js +0 -39
- package/src/prompt/function-defs/resize-image.js +0 -36
- package/src/prompt/function-defs/split-image.js +0 -45
- package/src/prompt/function-defs/update-file.js +0 -26
- package/src/prompt/limits.js +0 -23
- package/src/prompt/limits.test.js +0 -40
- package/src/prompt/prompt-codegen.js +0 -106
- package/src/prompt/prompt-codegen.test.js +0 -116
- package/src/prompt/prompt-service-ask-question.test.js +0 -163
- package/src/prompt/prompt-service.js +0 -335
- package/src/prompt/prompt-service.test.js +0 -602
- package/src/prompt/systemprompt.js +0 -39
- package/src/prompt/systemprompt.test.js +0 -64
|
@@ -1,126 +0,0 @@
|
|
|
1
|
-
import OpenAI from 'openai';
|
|
2
|
-
import { printTokenUsageAndCost, processFunctionCalls } from './common.js';
|
|
3
|
-
|
|
4
|
-
/**
|
|
5
|
-
* This function generates content using the OpenAI chat model.
|
|
6
|
-
*/
|
|
7
|
-
export async function generateContent(prompt, functionDefs, requiredFunctionName, temperature, cheap = false) {
|
|
8
|
-
const openai = new OpenAI();
|
|
9
|
-
|
|
10
|
-
const messages = prompt
|
|
11
|
-
.map((item) => {
|
|
12
|
-
if (item.type === 'systemPrompt') {
|
|
13
|
-
return {
|
|
14
|
-
role: 'system',
|
|
15
|
-
content: item.systemPrompt,
|
|
16
|
-
};
|
|
17
|
-
} else if (item.type === 'user') {
|
|
18
|
-
return [
|
|
19
|
-
...(item.functionResponses ?? []).map((response) => ({
|
|
20
|
-
role: 'tool',
|
|
21
|
-
name: response.name,
|
|
22
|
-
content: response.content ?? '',
|
|
23
|
-
tool_call_id: response.name,
|
|
24
|
-
})),
|
|
25
|
-
{
|
|
26
|
-
role: 'user',
|
|
27
|
-
content:
|
|
28
|
-
item.images?.length > 0
|
|
29
|
-
? [
|
|
30
|
-
...item.images.map((image) => ({
|
|
31
|
-
type: 'image_url',
|
|
32
|
-
image_url: {
|
|
33
|
-
url: 'data:' + image.mediaType + ';base64,' + image.base64url,
|
|
34
|
-
},
|
|
35
|
-
})),
|
|
36
|
-
{
|
|
37
|
-
type: 'text',
|
|
38
|
-
text: item.text,
|
|
39
|
-
},
|
|
40
|
-
]
|
|
41
|
-
: item.text,
|
|
42
|
-
},
|
|
43
|
-
];
|
|
44
|
-
} else if (item.type === 'assistant') {
|
|
45
|
-
return {
|
|
46
|
-
role: 'assistant',
|
|
47
|
-
...(item.text ? { content: item.text } : {}),
|
|
48
|
-
tool_calls: item.functionCalls.map((call) => ({
|
|
49
|
-
type: 'function',
|
|
50
|
-
function: { name: call.name, arguments: JSON.stringify(call.args ?? {}) },
|
|
51
|
-
id: call.name,
|
|
52
|
-
})),
|
|
53
|
-
};
|
|
54
|
-
}
|
|
55
|
-
})
|
|
56
|
-
.flat();
|
|
57
|
-
|
|
58
|
-
const model = cheap ? 'gpt-4o-mini' : 'gpt-4o-2024-08-06';
|
|
59
|
-
console.log(`Using OpenAI model: ${model}`);
|
|
60
|
-
|
|
61
|
-
let retryCount = 0;
|
|
62
|
-
let response;
|
|
63
|
-
while (retryCount < 3) {
|
|
64
|
-
try {
|
|
65
|
-
response = await openai.chat.completions.create({
|
|
66
|
-
model: model,
|
|
67
|
-
messages,
|
|
68
|
-
tools: functionDefs.map((funDef) => ({ type: 'function', function: funDef })),
|
|
69
|
-
tool_choice: requiredFunctionName ? { type: 'function', function: { name: requiredFunctionName } } : 'required',
|
|
70
|
-
temperature: temperature,
|
|
71
|
-
});
|
|
72
|
-
break; // Exit loop if successful
|
|
73
|
-
} catch (error) {
|
|
74
|
-
if (error.response?.headers?.['x-ratelimit-limit-tokens']) {
|
|
75
|
-
const rateLimitTokens = parseInt(error.response.headers['x-ratelimit-limit-tokens'], 10);
|
|
76
|
-
const retryAfter = error.response.headers['retry-after']
|
|
77
|
-
? parseInt(error.response.headers['retry-after'], 10)
|
|
78
|
-
: 1;
|
|
79
|
-
console.log(
|
|
80
|
-
`Rate limited. Token limit: ${rateLimitTokens}. Retrying after ${retryAfter} seconds. Attempt ${retryCount + 1} of 3.`,
|
|
81
|
-
);
|
|
82
|
-
await new Promise((resolve) => setTimeout(resolve, retryAfter * 1000));
|
|
83
|
-
retryCount++;
|
|
84
|
-
} else {
|
|
85
|
-
console.error('An error occurred:', error);
|
|
86
|
-
throw error; // Re-throw the error if it's not a rate limit error
|
|
87
|
-
}
|
|
88
|
-
}
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
if (retryCount === 3) {
|
|
92
|
-
console.error('Failed to complete request after 3 attempts due to rate limiting.');
|
|
93
|
-
throw new Error('Rate limit exceeded. Operation aborted.');
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
// Print token usage for chat gpt
|
|
97
|
-
const usage = {
|
|
98
|
-
inputTokens: response.usage.prompt_tokens,
|
|
99
|
-
outputTokens: response.usage.completion_tokens,
|
|
100
|
-
totalTokens: response.usage.total_tokens,
|
|
101
|
-
};
|
|
102
|
-
printTokenUsageAndCost(usage, 0.000005, 0.000015);
|
|
103
|
-
|
|
104
|
-
const responseMessage = response.choices[0].message;
|
|
105
|
-
|
|
106
|
-
if (responseMessage.content?.message) {
|
|
107
|
-
console.log('Message', responseMessage.content.message);
|
|
108
|
-
}
|
|
109
|
-
|
|
110
|
-
const toolCalls = responseMessage.tool_calls;
|
|
111
|
-
if (responseMessage.tool_calls) {
|
|
112
|
-
const functionCalls = toolCalls.map((call) => {
|
|
113
|
-
const name = call.function.name;
|
|
114
|
-
const args = JSON.parse(call.function.arguments);
|
|
115
|
-
|
|
116
|
-
return {
|
|
117
|
-
name,
|
|
118
|
-
args,
|
|
119
|
-
};
|
|
120
|
-
});
|
|
121
|
-
|
|
122
|
-
return processFunctionCalls(functionCalls);
|
|
123
|
-
} else {
|
|
124
|
-
throw new Error('No tool calls found in response');
|
|
125
|
-
}
|
|
126
|
-
}
|
package/src/ai-service/common.js
DELETED
|
@@ -1,49 +0,0 @@
|
|
|
1
|
-
import assert from 'node:assert';
|
|
2
|
-
import { functionDefs } from '../prompt/function-calling.js';
|
|
3
|
-
|
|
4
|
-
/**
|
|
5
|
-
* Common function to print token usage and estimated cost
|
|
6
|
-
* @param {Object} usage Token usage object
|
|
7
|
-
* @param {number} inputCostPerToken Cost per input token
|
|
8
|
-
* @param {number} outputCostPerToken Cost per output token
|
|
9
|
-
*/
|
|
10
|
-
export function printTokenUsageAndCost(usage, inputCostPerToken, outputCostPerToken) {
|
|
11
|
-
console.log('Token Usage:');
|
|
12
|
-
console.log(' - Input tokens: ', usage.inputTokens);
|
|
13
|
-
console.log(' - Output tokens: ', usage.outputTokens);
|
|
14
|
-
console.log(' - Total tokens: ', usage.totalTokens);
|
|
15
|
-
if (usage.cacheCreateTokens) {
|
|
16
|
-
console.log(' - Cache create tokens: ', usage.cacheCreateTokens);
|
|
17
|
-
}
|
|
18
|
-
if (usage.cacheReadTokens) {
|
|
19
|
-
console.log(' - Cache read tokens: ', usage.cacheReadTokens);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
const inputCost =
|
|
23
|
-
usage.inputTokens * inputCostPerToken +
|
|
24
|
-
(usage.cacheCreateTokens ?? 0) * inputCostPerToken * 1.25 +
|
|
25
|
-
(usage.cacheReadTokens ?? 0) * inputCostPerToken * 0.2;
|
|
26
|
-
const outputCost = usage.outputTokens * outputCostPerToken;
|
|
27
|
-
const totalCost = inputCost + outputCost;
|
|
28
|
-
console.log(' - Estimated cost: ', totalCost.toFixed(6), ' USD');
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
/**
|
|
32
|
-
* Common function to process function calls and explanations
|
|
33
|
-
* @param {Array} functionCalls Array of function calls
|
|
34
|
-
* @returns {Array} Processed function calls
|
|
35
|
-
*/
|
|
36
|
-
export function processFunctionCalls(functionCalls) {
|
|
37
|
-
const unknownFunctionCalls = functionCalls.filter((call) => !functionDefs.some((fd) => fd.name === call.name));
|
|
38
|
-
assert(
|
|
39
|
-
unknownFunctionCalls.length === 0,
|
|
40
|
-
'Unknown function name: ' + unknownFunctionCalls.map((call) => call.name).join(', '),
|
|
41
|
-
);
|
|
42
|
-
|
|
43
|
-
console.log(
|
|
44
|
-
'Explanations:',
|
|
45
|
-
functionCalls.filter((fn) => fn.name === 'explanation').map((call) => call.args.text),
|
|
46
|
-
);
|
|
47
|
-
|
|
48
|
-
return functionCalls; //.filter((fn) => fn.name !== 'explanation');
|
|
49
|
-
}
|
|
@@ -1,107 +0,0 @@
|
|
|
1
|
-
import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { printTokenUsageAndCost, processFunctionCalls } from './common.js';
|
|
3
|
-
import { functionDefs } from '../prompt/function-calling.js';
|
|
4
|
-
|
|
5
|
-
// Mock cli-params.js
|
|
6
|
-
vi.mock('../cli/cli-params.js', () => ({
|
|
7
|
-
chatGpt: true,
|
|
8
|
-
anthropic: false,
|
|
9
|
-
vertexAi: false,
|
|
10
|
-
vertexAiClaude: false,
|
|
11
|
-
temperature: 0.7,
|
|
12
|
-
cheap: false,
|
|
13
|
-
geminiBlockNone: false,
|
|
14
|
-
requireExplanations: false,
|
|
15
|
-
vision: false,
|
|
16
|
-
}));
|
|
17
|
-
|
|
18
|
-
describe('printTokenUsageAndCost', () => {
|
|
19
|
-
let consoleLogSpy;
|
|
20
|
-
|
|
21
|
-
beforeEach(() => {
|
|
22
|
-
consoleLogSpy = vi.spyOn(console, 'log').mockImplementation(() => {});
|
|
23
|
-
});
|
|
24
|
-
|
|
25
|
-
afterEach(() => {
|
|
26
|
-
consoleLogSpy.mockRestore();
|
|
27
|
-
});
|
|
28
|
-
|
|
29
|
-
it('should correctly log token usage and estimated cost', () => {
|
|
30
|
-
const usage = {
|
|
31
|
-
inputTokens: 100,
|
|
32
|
-
outputTokens: 50,
|
|
33
|
-
totalTokens: 150,
|
|
34
|
-
};
|
|
35
|
-
const inputCostPerToken = 0.0001;
|
|
36
|
-
const outputCostPerToken = 0.0002;
|
|
37
|
-
|
|
38
|
-
printTokenUsageAndCost(usage, inputCostPerToken, outputCostPerToken);
|
|
39
|
-
|
|
40
|
-
expect(consoleLogSpy).toHaveBeenCalledTimes(5);
|
|
41
|
-
expect(consoleLogSpy).toHaveBeenCalledWith('Token Usage:');
|
|
42
|
-
expect(consoleLogSpy).toHaveBeenCalledWith(' - Input tokens: ', 100);
|
|
43
|
-
expect(consoleLogSpy).toHaveBeenCalledWith(' - Output tokens: ', 50);
|
|
44
|
-
expect(consoleLogSpy).toHaveBeenCalledWith(' - Total tokens: ', 150);
|
|
45
|
-
expect(consoleLogSpy).toHaveBeenCalledWith(' - Estimated cost: ', '0.020000', ' USD');
|
|
46
|
-
});
|
|
47
|
-
|
|
48
|
-
it('should handle zero tokens correctly', () => {
|
|
49
|
-
const usage = {
|
|
50
|
-
inputTokens: 0,
|
|
51
|
-
outputTokens: 0,
|
|
52
|
-
totalTokens: 0,
|
|
53
|
-
};
|
|
54
|
-
const inputCostPerToken = 0.0001;
|
|
55
|
-
const outputCostPerToken = 0.0002;
|
|
56
|
-
|
|
57
|
-
printTokenUsageAndCost(usage, inputCostPerToken, outputCostPerToken);
|
|
58
|
-
|
|
59
|
-
expect(consoleLogSpy).toHaveBeenCalledWith(' - Estimated cost: ', '0.000000', ' USD');
|
|
60
|
-
});
|
|
61
|
-
});
|
|
62
|
-
|
|
63
|
-
describe('processFunctionCalls', () => {
|
|
64
|
-
it('should process valid function calls correctly', () => {
|
|
65
|
-
const validFunctionCalls = [
|
|
66
|
-
{ name: 'explanation', args: { text: 'This is an explanation' } },
|
|
67
|
-
{ name: functionDefs[0].name, args: {} },
|
|
68
|
-
];
|
|
69
|
-
|
|
70
|
-
const result = processFunctionCalls(validFunctionCalls);
|
|
71
|
-
|
|
72
|
-
expect(result).toEqual(validFunctionCalls);
|
|
73
|
-
});
|
|
74
|
-
|
|
75
|
-
it('should throw an error for unknown function names', () => {
|
|
76
|
-
const invalidFunctionCalls = [{ name: 'unknownFunction', args: {} }];
|
|
77
|
-
|
|
78
|
-
expect(() => processFunctionCalls(invalidFunctionCalls)).toThrow('Unknown function name: unknownFunction');
|
|
79
|
-
});
|
|
80
|
-
|
|
81
|
-
it('should correctly handle explanations', () => {
|
|
82
|
-
const consoleLogSpy = vi.spyOn(console, 'log').mockImplementation(() => {});
|
|
83
|
-
|
|
84
|
-
const functionCallsWithExplanation = [
|
|
85
|
-
{ name: 'explanation', args: { text: 'This is an explanation' } },
|
|
86
|
-
{ name: functionDefs[0].name, args: {} },
|
|
87
|
-
];
|
|
88
|
-
|
|
89
|
-
processFunctionCalls(functionCallsWithExplanation);
|
|
90
|
-
|
|
91
|
-
expect(consoleLogSpy).toHaveBeenCalledWith('Explanations:', ['This is an explanation']);
|
|
92
|
-
|
|
93
|
-
consoleLogSpy.mockRestore();
|
|
94
|
-
});
|
|
95
|
-
|
|
96
|
-
it('should return all function calls including explanations', () => {
|
|
97
|
-
const functionCalls = [
|
|
98
|
-
{ name: 'explanation', args: { text: 'This is an explanation' } },
|
|
99
|
-
{ name: functionDefs[0].name, args: {} },
|
|
100
|
-
];
|
|
101
|
-
|
|
102
|
-
const result = processFunctionCalls(functionCalls);
|
|
103
|
-
|
|
104
|
-
expect(result).toEqual(functionCalls);
|
|
105
|
-
expect(result.length).toBe(2);
|
|
106
|
-
});
|
|
107
|
-
});
|
package/src/ai-service/dall-e.js
DELETED
|
@@ -1,50 +0,0 @@
|
|
|
1
|
-
import OpenAI, { toFile } from 'openai';
|
|
2
|
-
|
|
3
|
-
import { setTempBuffer } from '../files/temp-buffer.js';
|
|
4
|
-
import { resizeImageBuffer } from '../images/resize-image.js';
|
|
5
|
-
import { ensureAlpha } from '../images/ensure-alpha.js';
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* Generate an image using OpenAI's DALL-E model and save it to a file
|
|
9
|
-
* @param {string} prompt - The description of the image to generate
|
|
10
|
-
* @param {string|undefined} contextImagePath - The image to be used as a context
|
|
11
|
-
* @param {{width: number, height: number}} size - The size of the image to generate
|
|
12
|
-
* @param {boolean} cheap - Whether to use a cheaper model
|
|
13
|
-
* @returns {Promise<string>} - The url of the image
|
|
14
|
-
*/
|
|
15
|
-
export async function generateImage(prompt, contextImagePath, size, cheap = false) {
|
|
16
|
-
const openai = new OpenAI();
|
|
17
|
-
|
|
18
|
-
try {
|
|
19
|
-
const model = contextImagePath ? 'dall-e-2' : cheap ? 'dall-e-2' : 'dall-e-3';
|
|
20
|
-
console.log(`Using DALL-E model: ${model}`);
|
|
21
|
-
|
|
22
|
-
const options = {
|
|
23
|
-
model: model,
|
|
24
|
-
prompt: prompt,
|
|
25
|
-
n: 1,
|
|
26
|
-
size: '1024x1024',
|
|
27
|
-
response_format: 'url',
|
|
28
|
-
};
|
|
29
|
-
const response = contextImagePath
|
|
30
|
-
? await openai.images.edit({ ...options, image: await toFile(await ensureAlpha(contextImagePath)) })
|
|
31
|
-
: await openai.images.generate(options);
|
|
32
|
-
|
|
33
|
-
let imageUrl = response.data[0].url;
|
|
34
|
-
|
|
35
|
-
if ((size.width !== 1024) | (size.height !== 1024)) {
|
|
36
|
-
console.log('Resizing image to desired size', size);
|
|
37
|
-
const imageResponse = await fetch(imageUrl);
|
|
38
|
-
const arrayBuffer = await imageResponse.arrayBuffer();
|
|
39
|
-
const buffer = Buffer.from(arrayBuffer);
|
|
40
|
-
|
|
41
|
-
imageUrl = setTempBuffer(await resizeImageBuffer(buffer, size));
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
console.log(`Image generated, url: ${imageUrl}`);
|
|
45
|
-
return imageUrl;
|
|
46
|
-
} catch (error) {
|
|
47
|
-
console.error('Error generating image:', error);
|
|
48
|
-
throw error;
|
|
49
|
-
}
|
|
50
|
-
}
|
|
@@ -1,99 +0,0 @@
|
|
|
1
|
-
import { AnthropicVertex } from '@anthropic-ai/vertex-sdk';
|
|
2
|
-
import { printTokenUsageAndCost, processFunctionCalls } from './common.js';
|
|
3
|
-
|
|
4
|
-
/**
|
|
5
|
-
* This function generates content using the Anthropic Claude model via Vertex AI.
|
|
6
|
-
*/
|
|
7
|
-
export async function generateContent(prompt, functionDefs, requiredFunctionName, temperature, cheap = false) {
|
|
8
|
-
const projectId = process.env.GOOGLE_CLOUD_PROJECT;
|
|
9
|
-
const region = process.env.GOOGLE_CLOUD_REGION;
|
|
10
|
-
|
|
11
|
-
if (!projectId || !region) {
|
|
12
|
-
throw new Error('GOOGLE_CLOUD_PROJECT and GOOGLE_CLOUD_REGION environment variables must be set');
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
const client = new AnthropicVertex({
|
|
16
|
-
projectId,
|
|
17
|
-
region,
|
|
18
|
-
});
|
|
19
|
-
|
|
20
|
-
const messages = prompt
|
|
21
|
-
.filter((item) => item.type !== 'systemPrompt')
|
|
22
|
-
.map((item) => {
|
|
23
|
-
if (item.type === 'user') {
|
|
24
|
-
return {
|
|
25
|
-
role: 'user',
|
|
26
|
-
content: [
|
|
27
|
-
...(item.functionResponses ?? []).map((response) => ({
|
|
28
|
-
type: 'tool_result',
|
|
29
|
-
tool_use_id: response.call_id ?? response.name,
|
|
30
|
-
content: response.content,
|
|
31
|
-
is_error: response.isError === true,
|
|
32
|
-
})),
|
|
33
|
-
...(item.images ?? []).map((image) => ({
|
|
34
|
-
type: 'image',
|
|
35
|
-
source: {
|
|
36
|
-
type: 'base64',
|
|
37
|
-
media_type: image.mediaType,
|
|
38
|
-
data: image.base64url,
|
|
39
|
-
},
|
|
40
|
-
})),
|
|
41
|
-
{ type: 'text', text: item.text },
|
|
42
|
-
],
|
|
43
|
-
};
|
|
44
|
-
} else if (item.type === 'assistant') {
|
|
45
|
-
return {
|
|
46
|
-
role: 'assistant',
|
|
47
|
-
content: [
|
|
48
|
-
...(item.text ? [{ type: 'text', text: item.text }] : []),
|
|
49
|
-
...item.functionCalls.map((call) => ({
|
|
50
|
-
type: 'tool_use',
|
|
51
|
-
id: call.id ?? call.name,
|
|
52
|
-
name: call.name,
|
|
53
|
-
input: call.args ?? {},
|
|
54
|
-
})),
|
|
55
|
-
],
|
|
56
|
-
};
|
|
57
|
-
}
|
|
58
|
-
});
|
|
59
|
-
|
|
60
|
-
const model = cheap ? 'claude-3-haiku@20240307' : 'claude-3-5-sonnet@20240620';
|
|
61
|
-
console.log(`Using Vertex AI Claude model: ${model}`);
|
|
62
|
-
|
|
63
|
-
const response = await client.messages.create({
|
|
64
|
-
model: model,
|
|
65
|
-
max_tokens: 4096,
|
|
66
|
-
temperature: temperature,
|
|
67
|
-
system: prompt.find((item) => item.type === 'systemPrompt').systemPrompt,
|
|
68
|
-
messages,
|
|
69
|
-
tools: functionDefs.map((fd) => ({
|
|
70
|
-
name: fd.name,
|
|
71
|
-
description: fd.description,
|
|
72
|
-
input_schema: fd.parameters,
|
|
73
|
-
})),
|
|
74
|
-
tool_choice: requiredFunctionName ? { type: 'tool', name: requiredFunctionName } : { type: 'any' },
|
|
75
|
-
});
|
|
76
|
-
|
|
77
|
-
// Print token usage for Anthropic Vertex AI
|
|
78
|
-
const usage = {
|
|
79
|
-
inputTokens: response.usage.input_tokens,
|
|
80
|
-
outputTokens: response.usage.output_tokens,
|
|
81
|
-
totalTokens: response.usage.input_tokens + response.usage.output_tokens,
|
|
82
|
-
};
|
|
83
|
-
printTokenUsageAndCost(usage, 3 / 1000 / 1000, 15 / 1000 / 1000);
|
|
84
|
-
|
|
85
|
-
const responseMessages = response.content.filter((item) => item.type !== 'tool_use');
|
|
86
|
-
if (responseMessages.length > 0) {
|
|
87
|
-
console.log('Response messages', responseMessages);
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
const functionCalls = response.content
|
|
91
|
-
.filter((item) => item.type === 'tool_use')
|
|
92
|
-
.map((item) => ({
|
|
93
|
-
id: item.id,
|
|
94
|
-
name: item.name,
|
|
95
|
-
args: item.input,
|
|
96
|
-
}));
|
|
97
|
-
|
|
98
|
-
return processFunctionCalls(functionCalls);
|
|
99
|
-
}
|
|
@@ -1,78 +0,0 @@
|
|
|
1
|
-
import fs from 'fs';
|
|
2
|
-
import mime from 'mime-types';
|
|
3
|
-
import { PredictionServiceClient, helpers } from '@google-cloud/aiplatform';
|
|
4
|
-
import { setTempBuffer } from '../files/temp-buffer.js';
|
|
5
|
-
import { resizeImageBuffer } from '../images/resize-image.js';
|
|
6
|
-
|
|
7
|
-
/**
|
|
8
|
-
* Generate an image using Vertex AI's Imagen model and return the image URL
|
|
9
|
-
* @param {string} prompt - The description of the image to generate
|
|
10
|
-
* @param {string|undefined} contextImagePath - The image to be used as a context
|
|
11
|
-
* @param {{width: number, height: number}} size - The size of the image to generate
|
|
12
|
-
* @param {boolean} cheap - Whether to use a cheaper model
|
|
13
|
-
* @returns {Promise<string>} - The url of the generated image
|
|
14
|
-
*/
|
|
15
|
-
export async function generateImage(prompt, contextImagePath, size, cheap = false) {
|
|
16
|
-
// Initialize the PredictionServiceClient
|
|
17
|
-
const client = new PredictionServiceClient({
|
|
18
|
-
apiEndpoint: `${process.env.GOOGLE_CLOUD_REGION}-aiplatform.googleapis.com`,
|
|
19
|
-
});
|
|
20
|
-
|
|
21
|
-
// Set the project and location
|
|
22
|
-
const projectId = process.env.GOOGLE_CLOUD_PROJECT;
|
|
23
|
-
const location = process.env.GOOGLE_CLOUD_REGION;
|
|
24
|
-
|
|
25
|
-
// Set the model name based on the cheap parameter
|
|
26
|
-
const modelName = contextImagePath
|
|
27
|
-
? 'imagegeneration@002'
|
|
28
|
-
: cheap
|
|
29
|
-
? 'imagen-3.0-fast-generate-001'
|
|
30
|
-
: 'imagen-3.0-generate-001';
|
|
31
|
-
console.log(`Using Vertex AI Imagen model: ${modelName}`);
|
|
32
|
-
|
|
33
|
-
try {
|
|
34
|
-
// Prepare the request
|
|
35
|
-
const request = {
|
|
36
|
-
endpoint: `projects/${projectId}/locations/${location}/publishers/google/models/${modelName}`,
|
|
37
|
-
instances: [
|
|
38
|
-
helpers.toValue({
|
|
39
|
-
prompt: prompt,
|
|
40
|
-
...(contextImagePath
|
|
41
|
-
? {
|
|
42
|
-
image: {
|
|
43
|
-
bytesBase64Encoded: fs.readFileSync(contextImagePath, 'base64'),
|
|
44
|
-
mediaType: mime.lookup(contextImagePath),
|
|
45
|
-
},
|
|
46
|
-
}
|
|
47
|
-
: {}),
|
|
48
|
-
}),
|
|
49
|
-
],
|
|
50
|
-
parameters: helpers.toValue({
|
|
51
|
-
sampleCount: 1,
|
|
52
|
-
safetySetting: 'block_most',
|
|
53
|
-
personGeneration: 'allow_adult',
|
|
54
|
-
includeRaiReason: true,
|
|
55
|
-
language: 'auto',
|
|
56
|
-
aspectRatio: '1:1',
|
|
57
|
-
addWatermark: false,
|
|
58
|
-
}),
|
|
59
|
-
};
|
|
60
|
-
|
|
61
|
-
// Make the prediction request
|
|
62
|
-
const [response] = await client.predict(request);
|
|
63
|
-
|
|
64
|
-
if (response.predictions && response.predictions.length > 0) {
|
|
65
|
-
const prediction = helpers.fromValue(response.predictions[0]);
|
|
66
|
-
if (prediction.bytesBase64Encoded) {
|
|
67
|
-
console.log(`Image generated successfully, resizing to desired dimension`, size);
|
|
68
|
-
const buffer = Buffer.from(prediction.bytesBase64Encoded, 'base64');
|
|
69
|
-
return setTempBuffer(await resizeImageBuffer(buffer, size));
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
throw new Error('No image generated in the response');
|
|
74
|
-
} catch (error) {
|
|
75
|
-
console.error('Error generating image:', error);
|
|
76
|
-
throw error;
|
|
77
|
-
}
|
|
78
|
-
}
|
|
@@ -1,156 +0,0 @@
|
|
|
1
|
-
import assert from 'node:assert';
|
|
2
|
-
import { VertexAI } from '@google-cloud/vertexai';
|
|
3
|
-
import { printTokenUsageAndCost, processFunctionCalls } from './common.js';
|
|
4
|
-
import { geminiBlockNone } from '../cli/cli-params.js';
|
|
5
|
-
|
|
6
|
-
/**
|
|
7
|
-
* This function generates content using the Gemini Pro model.
|
|
8
|
-
*/
|
|
9
|
-
|
|
10
|
-
export async function generateContent(prompt, functionDefs, requiredFunctionName, temperature, cheap = false) {
|
|
11
|
-
const messages = prompt
|
|
12
|
-
.filter((item) => item.type !== 'systemPrompt')
|
|
13
|
-
.map((item) => {
|
|
14
|
-
if (item.type === 'user') {
|
|
15
|
-
return {
|
|
16
|
-
role: 'user',
|
|
17
|
-
parts: [
|
|
18
|
-
...(item.functionResponses ?? []).map((response) => ({
|
|
19
|
-
functionResponse: {
|
|
20
|
-
name: response.name,
|
|
21
|
-
response: { name: response.name, content: response.content },
|
|
22
|
-
},
|
|
23
|
-
})),
|
|
24
|
-
...(item.images ?? []).map((image) => ({
|
|
25
|
-
inlineData: {
|
|
26
|
-
mimeType: image.mediaType,
|
|
27
|
-
data: image.base64url,
|
|
28
|
-
},
|
|
29
|
-
})),
|
|
30
|
-
{ text: item.text },
|
|
31
|
-
],
|
|
32
|
-
};
|
|
33
|
-
} else if (item.type === 'assistant') {
|
|
34
|
-
return {
|
|
35
|
-
role: 'model',
|
|
36
|
-
parts: [
|
|
37
|
-
...(item.text ? [{ text: item.text }] : []),
|
|
38
|
-
...item.functionCalls.map((call) => ({
|
|
39
|
-
functionCall: {
|
|
40
|
-
name: call.name,
|
|
41
|
-
args: call.args ?? {},
|
|
42
|
-
},
|
|
43
|
-
})),
|
|
44
|
-
],
|
|
45
|
-
};
|
|
46
|
-
}
|
|
47
|
-
});
|
|
48
|
-
|
|
49
|
-
const req = {
|
|
50
|
-
contents: messages,
|
|
51
|
-
tools: [
|
|
52
|
-
{
|
|
53
|
-
functionDeclarations: functionDefs,
|
|
54
|
-
},
|
|
55
|
-
],
|
|
56
|
-
toolConfig: {
|
|
57
|
-
functionCallingConfig: {
|
|
58
|
-
mode: cheap ? undefined : 'ANY',
|
|
59
|
-
...(!cheap && requiredFunctionName ? { allowedFunctionNames: [requiredFunctionName] } : {}),
|
|
60
|
-
},
|
|
61
|
-
},
|
|
62
|
-
};
|
|
63
|
-
|
|
64
|
-
const model = await getGenModel(prompt.find((item) => item.type === 'systemPrompt').systemPrompt, temperature, cheap);
|
|
65
|
-
|
|
66
|
-
assert(await verifyVertexMonkeyPatch(), 'Vertex AI Tool Config was not monkey patched');
|
|
67
|
-
|
|
68
|
-
const result = await model.generateContent(req);
|
|
69
|
-
|
|
70
|
-
// Print token usage
|
|
71
|
-
const usageMetadata = result.response.usageMetadata;
|
|
72
|
-
const usage = {
|
|
73
|
-
inputTokens: usageMetadata.promptTokenCount,
|
|
74
|
-
outputTokens: usageMetadata.candidatesTokenCount,
|
|
75
|
-
totalTokens: usageMetadata.totalTokenCount,
|
|
76
|
-
};
|
|
77
|
-
printTokenUsageAndCost(usage, 0.000125 / 1000, 0.000375 / 1000);
|
|
78
|
-
|
|
79
|
-
if (result.response.promptFeedback) {
|
|
80
|
-
console.log('Prompt feedback:');
|
|
81
|
-
console.log(JSON.stringify(result.response.promptFeedback, null, 2));
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
if (!result.response.candidates?.length > 0) {
|
|
85
|
-
console.log('Response:', result);
|
|
86
|
-
throw new Error('No candidates found');
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
const functionCalls = result.response.candidates
|
|
90
|
-
.map((candidate) => candidate.content.parts?.map((part) => part.functionCall))
|
|
91
|
-
.flat()
|
|
92
|
-
.filter((functionCall) => !!functionCall);
|
|
93
|
-
|
|
94
|
-
if (functionCalls.length === 0) {
|
|
95
|
-
const textResponse = result.response.candidates
|
|
96
|
-
.map((candidate) => candidate.content.parts?.map((part) => part.text))
|
|
97
|
-
.flat()
|
|
98
|
-
.filter((text) => !!text)
|
|
99
|
-
.join('\n');
|
|
100
|
-
console.log('No function calls, output text response if it exists:', textResponse);
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
return processFunctionCalls(functionCalls);
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
// A function to get the generative model
|
|
107
|
-
// Modified to accept temperature parameter and cheap flag
|
|
108
|
-
export function getGenModel(systemPrompt, temperature, cheap = false) {
|
|
109
|
-
// Initialize Vertex with your Cloud project and location
|
|
110
|
-
const vertex_ai = new VertexAI({});
|
|
111
|
-
const model = cheap ? 'gemini-1.5-flash-001' : 'gemini-1.5-pro-001';
|
|
112
|
-
|
|
113
|
-
console.log(`Using Vertex AI model: ${model}`);
|
|
114
|
-
|
|
115
|
-
// Instantiate the models
|
|
116
|
-
return vertex_ai.preview.getGenerativeModel({
|
|
117
|
-
model: model,
|
|
118
|
-
generationConfig: {
|
|
119
|
-
maxOutputTokens: 8192,
|
|
120
|
-
temperature: temperature,
|
|
121
|
-
topP: 0.95,
|
|
122
|
-
},
|
|
123
|
-
safetySettings: [
|
|
124
|
-
{
|
|
125
|
-
category: 'HARM_CATEGORY_HATE_SPEECH',
|
|
126
|
-
threshold: geminiBlockNone ? 'BLOCK_NONE' : 'BLOCK_LOW_AND_ABOVE',
|
|
127
|
-
},
|
|
128
|
-
{
|
|
129
|
-
category: 'HARM_CATEGORY_DANGEROUS_CONTENT',
|
|
130
|
-
threshold: geminiBlockNone ? 'BLOCK_NONE' : 'BLOCK_LOW_AND_ABOVE',
|
|
131
|
-
},
|
|
132
|
-
{
|
|
133
|
-
category: 'HARM_CATEGORY_SEXUALLY_EXPLICIT',
|
|
134
|
-
threshold: geminiBlockNone ? 'BLOCK_NONE' : 'BLOCK_LOW_AND_ABOVE',
|
|
135
|
-
},
|
|
136
|
-
{
|
|
137
|
-
category: 'HARM_CATEGORY_HARASSMENT',
|
|
138
|
-
threshold: geminiBlockNone ? 'BLOCK_NONE' : 'BLOCK_LOW_AND_ABOVE',
|
|
139
|
-
},
|
|
140
|
-
],
|
|
141
|
-
systemInstruction: {
|
|
142
|
-
role: 'system',
|
|
143
|
-
parts: [
|
|
144
|
-
{
|
|
145
|
-
text: systemPrompt,
|
|
146
|
-
},
|
|
147
|
-
],
|
|
148
|
-
},
|
|
149
|
-
});
|
|
150
|
-
}
|
|
151
|
-
|
|
152
|
-
export async function verifyVertexMonkeyPatch() {
|
|
153
|
-
return (await import('@google-cloud/vertexai/build/src/functions/generate_content.js')).generateContent
|
|
154
|
-
.toString()
|
|
155
|
-
.includes('// MONKEY PATCH TOOL_CONFIG');
|
|
156
|
-
}
|