@cobrowser/chatgpt 0.7.31 → 0.7.32-dev.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/dist/constants.d.ts +2 -2
- package/dist/constants.js +19 -23
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/models/ConversationHistory.d.ts +3 -3
- package/dist/models/Item.d.ts +2 -2
- package/dist/services/AssistantService/AssistantService.d.ts +3 -3
- package/dist/services/AssistantService/AssistantService.js +14 -13
- package/dist/services/BaseService/BaseService.d.ts +6 -14
- package/dist/services/BaseService/BaseService.js +7 -65
- package/dist/services/ChatService/ChatService.d.ts +1 -2
- package/dist/services/ChatService/ChatService.js +9 -14
- package/dist/services/CopilotService/CopilotService.d.ts +14 -8
- package/dist/services/CopilotService/CopilotService.js +145 -54
- package/dist/services/ResponseService/ResponseService.d.ts +37 -0
- package/dist/services/ResponseService/ResponseService.js +213 -0
- package/dist/services/TranslationService/TranslationService.d.ts +4 -4
- package/dist/services/TranslationService/TranslationService.js +11 -14
- package/package.json +4 -5
- package/dist/models/ChatGPTMessage.d.ts +0 -17
- package/dist/models/ChatGPTMessage.js +0 -9
- package/dist/models/ChatGPTResponse.d.ts +0 -8
- package/dist/models/ChatGPTResponse.js +0 -2
- package/dist/models/ChatGPTUsageTokens.d.ts +0 -6
- package/dist/models/ChatGPTUsageTokens.js +0 -2
- package/dist/models/Response.d.ts +0 -3
- package/dist/models/Response.js +0 -2
- package/dist/utils/Response.d.ts +0 -4
- package/dist/utils/Response.js +0 -11
- package/dist/utils/constants.d.ts +0 -13
- package/dist/utils/constants.js +0 -66
|
@@ -8,25 +8,18 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
8
8
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
9
|
});
|
|
10
10
|
};
|
|
11
|
-
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
12
|
-
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
13
|
-
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
14
|
-
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
15
|
-
};
|
|
16
11
|
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
17
12
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
18
13
|
};
|
|
19
|
-
var _CopilotService_instances, _CopilotService_processSuggestions;
|
|
20
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
21
15
|
exports.CopilotService = void 0;
|
|
22
|
-
const
|
|
16
|
+
const BaseService_1 = __importDefault(require("../BaseService/BaseService"));
|
|
23
17
|
const logger_1 = __importDefault(require("../logger"));
|
|
18
|
+
const ChatGptMessage_1 = require("../../models/ChatGptMessage");
|
|
24
19
|
const openai_1 = __importDefault(require("openai"));
|
|
25
|
-
const BaseService_1 = __importDefault(require("../BaseService/BaseService"));
|
|
26
20
|
class CopilotService extends BaseService_1.default {
|
|
27
21
|
constructor(apiKey, model, assistantId, threadId, apiUrl, maxNumberOfChoices) {
|
|
28
22
|
super(apiKey, model, apiUrl, maxNumberOfChoices);
|
|
29
|
-
_CopilotService_instances.add(this);
|
|
30
23
|
Object.defineProperty(this, "assistantId", {
|
|
31
24
|
enumerable: true,
|
|
32
25
|
configurable: true,
|
|
@@ -39,6 +32,12 @@ class CopilotService extends BaseService_1.default {
|
|
|
39
32
|
writable: true,
|
|
40
33
|
value: void 0
|
|
41
34
|
});
|
|
35
|
+
Object.defineProperty(this, "conversationId", {
|
|
36
|
+
enumerable: true,
|
|
37
|
+
configurable: true,
|
|
38
|
+
writable: true,
|
|
39
|
+
value: void 0
|
|
40
|
+
});
|
|
42
41
|
this.assistantId = assistantId;
|
|
43
42
|
this.threadId = threadId;
|
|
44
43
|
}
|
|
@@ -57,14 +56,43 @@ class CopilotService extends BaseService_1.default {
|
|
|
57
56
|
suggest(conversation) {
|
|
58
57
|
return __awaiter(this, void 0, void 0, function* () {
|
|
59
58
|
if (!(conversation === null || conversation === void 0 ? void 0 : conversation.length)) {
|
|
60
|
-
logger_1.default.error('
|
|
61
|
-
return Promise.reject(new Error('
|
|
59
|
+
logger_1.default.error('conversation must be provided');
|
|
60
|
+
return Promise.reject(new Error('conversation must be provided'));
|
|
62
61
|
}
|
|
63
62
|
try {
|
|
64
63
|
if (this.assistantId) {
|
|
65
|
-
|
|
64
|
+
// Here we get the last customer message as we dont need the whole conversation
|
|
65
|
+
// as we are doing with the other approach
|
|
66
|
+
const conversationArray = conversation.split('\n');
|
|
67
|
+
const lastCustomerMessage = conversationArray.reverse().find(e => e.includes('customer:'));
|
|
68
|
+
if (!lastCustomerMessage) {
|
|
69
|
+
logger_1.default.error('last customer message not found');
|
|
70
|
+
return Promise.reject(new Error('last customer message not found'));
|
|
71
|
+
}
|
|
72
|
+
// Route based on id shape: asst_* => Assistant API, prompt_* => Responses API
|
|
73
|
+
if (this.isAssistantIdFormat(this.assistantId)) {
|
|
74
|
+
return yield this.getAssistantReply(lastCustomerMessage);
|
|
75
|
+
}
|
|
76
|
+
return yield this.getPromptReply(lastCustomerMessage);
|
|
66
77
|
}
|
|
67
|
-
|
|
78
|
+
// main prompt used to instruct chatGPT to suggest some quick replies
|
|
79
|
+
const mainPrompt = `Propose some quick replies for the agent to be used on the following conversation
|
|
80
|
+
Your response must only contains a valid JSON array of strings like this:
|
|
81
|
+
["Reply 1", "Reply 2", "Reply 3"]. the conversation is:-\n${conversation}`,
|
|
82
|
+
// main prompt will be the whole conversation as string
|
|
83
|
+
mainPromptMessage = {
|
|
84
|
+
role: ChatGptMessage_1.ChatGptRole.USER,
|
|
85
|
+
content: mainPrompt,
|
|
86
|
+
},
|
|
87
|
+
// the body we need to send to the request
|
|
88
|
+
requestBody = {
|
|
89
|
+
model: this.chatGptModel,
|
|
90
|
+
messages: [mainPromptMessage],
|
|
91
|
+
}, response = yield this.request.post('', requestBody);
|
|
92
|
+
return {
|
|
93
|
+
firstChoice: this.getResponseFirstChoice(response),
|
|
94
|
+
usageTokens: this.getResponseUsageTokens(response),
|
|
95
|
+
};
|
|
68
96
|
}
|
|
69
97
|
catch (e) {
|
|
70
98
|
this.handleErrors(e);
|
|
@@ -73,30 +101,35 @@ class CopilotService extends BaseService_1.default {
|
|
|
73
101
|
});
|
|
74
102
|
}
|
|
75
103
|
/**
|
|
76
|
-
*
|
|
77
|
-
*
|
|
78
|
-
* @param
|
|
104
|
+
* this will request chatGPT to recommend product or item based on the whole conversation
|
|
105
|
+
* @param conversation the whole chat conversation
|
|
106
|
+
* @param items the items to recommend from
|
|
79
107
|
*/
|
|
80
|
-
|
|
108
|
+
recommend(conversation, items) {
|
|
81
109
|
return __awaiter(this, void 0, void 0, function* () {
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
110
|
+
if (!(items === null || items === void 0 ? void 0 : items.length) || !(conversation === null || conversation === void 0 ? void 0 : conversation.length)) {
|
|
111
|
+
logger_1.default.error('conversation or items not found');
|
|
112
|
+
return Promise.reject(new Error('conversation and items must be provided'));
|
|
113
|
+
}
|
|
114
|
+
try {
|
|
115
|
+
// main prompt used to instruct chatGPT to recommend products
|
|
116
|
+
const mainPrompt = `we have this list of Items: ${JSON.stringify(items)}, what to recommend for you`,
|
|
117
|
+
// main prompt will be the first message of the whole conversation
|
|
118
|
+
firstMessage = {
|
|
119
|
+
role: ChatGptMessage_1.ChatGptRole.ASSISTANT,
|
|
120
|
+
content: mainPrompt,
|
|
121
|
+
},
|
|
122
|
+
// the body we need to send to the request
|
|
123
|
+
requestBody = {
|
|
124
|
+
model: this.chatGptModel,
|
|
125
|
+
messages: [firstMessage, ...conversation],
|
|
126
|
+
}, response = yield this.request.post('', requestBody);
|
|
127
|
+
return this.getResponseFirstChoice(response);
|
|
128
|
+
}
|
|
129
|
+
catch (e) {
|
|
130
|
+
this.handleErrors(e);
|
|
131
|
+
return Promise.reject(e);
|
|
132
|
+
}
|
|
100
133
|
});
|
|
101
134
|
}
|
|
102
135
|
/**
|
|
@@ -104,42 +137,38 @@ class CopilotService extends BaseService_1.default {
|
|
|
104
137
|
*
|
|
105
138
|
* @param message
|
|
106
139
|
*/
|
|
107
|
-
|
|
140
|
+
getAssistantReply(message) {
|
|
108
141
|
var _a;
|
|
109
142
|
return __awaiter(this, void 0, void 0, function* () {
|
|
110
|
-
// Here we get the last customer message as we dont need the whole conversation
|
|
111
|
-
// as we are doing with the other approach.
|
|
112
|
-
const conversationArray = conversation.split('\n'), lastCustomerMessage = conversationArray.reverse().find(e => e.includes('customer:'));
|
|
113
|
-
if (!lastCustomerMessage) {
|
|
114
|
-
logger_1.default.error('Last customer message not found');
|
|
115
|
-
return Promise.reject(new Error('Last customer message not found'));
|
|
116
|
-
}
|
|
117
143
|
const openai = new openai_1.default({ apiKey: this.openaiApiKey });
|
|
118
144
|
let run;
|
|
119
145
|
if (!this.threadId) {
|
|
120
146
|
const thread = yield openai.beta.threads.create();
|
|
121
147
|
this.threadId = thread.id;
|
|
122
148
|
}
|
|
123
|
-
const lastThreadMessasges = yield openai.beta.threads.messages.list(this.threadId, { order: "desc", limit: 2 })
|
|
149
|
+
const lastThreadMessasges = yield openai.beta.threads.messages.list(this.threadId, { order: "desc", limit: 2 });
|
|
150
|
+
const isRepeatedMessage = lastThreadMessasges.data.find(msg => msg.content[0].type === 'text' && msg.content[0].text.value === message);
|
|
124
151
|
// making sure that we're not saving repeated messages
|
|
125
152
|
if (isRepeatedMessage) {
|
|
126
153
|
const runs = yield openai.beta.threads.runs.list(this.threadId, { order: "desc", limit: 1 });
|
|
127
154
|
run = runs.data[0];
|
|
128
155
|
}
|
|
129
156
|
else {
|
|
130
|
-
yield openai.beta.threads.messages.create(this.threadId, { role: "user", content:
|
|
157
|
+
yield openai.beta.threads.messages.create(this.threadId, { role: "user", content: message });
|
|
131
158
|
run = yield openai.beta.threads.runs.create(this.threadId, { assistant_id: (_a = this.assistantId) !== null && _a !== void 0 ? _a : '' });
|
|
132
159
|
}
|
|
133
160
|
while (['queued', 'in_progress', 'cancelling'].includes(run.status)) {
|
|
134
161
|
yield new Promise(resolve => setTimeout(resolve, 500));
|
|
135
|
-
run = yield openai.beta.threads.runs.retrieve(run.
|
|
162
|
+
run = yield openai.beta.threads.runs.retrieve(run.id, { thread_id: run.thread_id });
|
|
136
163
|
}
|
|
137
164
|
if (run.status === 'completed') {
|
|
138
|
-
const { data } = yield openai.beta.threads.messages.list(run.thread_id, { order: 'desc', limit: 1 })
|
|
165
|
+
const { data } = yield openai.beta.threads.messages.list(run.thread_id, { order: 'desc', limit: 1 });
|
|
166
|
+
const messages = data.flatMap((message) => message === null || message === void 0 ? void 0 : message.content.map((content) => ((content.type === 'text' && message.role === 'assistant') ? content.text : '')));
|
|
167
|
+
const assistantMessages = messages.filter(message => typeof message === 'object' && 'value' in message && typeof message.value === 'string');
|
|
139
168
|
if (assistantMessages.length) {
|
|
140
|
-
|
|
169
|
+
let answers = assistantMessages.map(message => message.value);
|
|
141
170
|
return {
|
|
142
|
-
|
|
171
|
+
firstChoice: JSON.stringify(answers),
|
|
143
172
|
threadId: run.thread_id,
|
|
144
173
|
usageTokens: run.usage,
|
|
145
174
|
};
|
|
@@ -148,10 +177,72 @@ class CopilotService extends BaseService_1.default {
|
|
|
148
177
|
return undefined;
|
|
149
178
|
});
|
|
150
179
|
}
|
|
180
|
+
isAssistantIdFormat(id) {
|
|
181
|
+
return !!id && /^asst_[A-Za-z0-9]+$/.test(id);
|
|
182
|
+
}
|
|
183
|
+
isPromptIdFormat(id) {
|
|
184
|
+
return !!id && /^pmpt_[A-Za-z0-9]+$/.test(id);
|
|
185
|
+
}
|
|
186
|
+
ensureConversation(openai) {
|
|
187
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
188
|
+
if (this.conversationId) {
|
|
189
|
+
return this.conversationId;
|
|
190
|
+
}
|
|
191
|
+
const conv = yield openai.conversations.create();
|
|
192
|
+
this.conversationId = conv.id;
|
|
193
|
+
return conv.id;
|
|
194
|
+
});
|
|
195
|
+
}
|
|
196
|
+
getPromptReply(message) {
|
|
197
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o;
|
|
198
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
199
|
+
const openai = new openai_1.default({ apiKey: this.openaiApiKey });
|
|
200
|
+
const conversationId = yield this.ensureConversation(openai);
|
|
201
|
+
const request = {
|
|
202
|
+
//model: this.chatGptModel || 'gpt-4o-mini',
|
|
203
|
+
input: message,
|
|
204
|
+
store: true,
|
|
205
|
+
conversation: conversationId,
|
|
206
|
+
include: ['file_search_call.results'],
|
|
207
|
+
};
|
|
208
|
+
if (this.assistantId && this.isPromptIdFormat(this.assistantId)) {
|
|
209
|
+
request.prompt = { id: this.assistantId };
|
|
210
|
+
}
|
|
211
|
+
const response = yield openai.responses.create(request);
|
|
212
|
+
response.output.forEach((item, index) => {
|
|
213
|
+
});
|
|
214
|
+
if ((_a = response.conversation) === null || _a === void 0 ? void 0 : _a.id) {
|
|
215
|
+
this.conversationId = response.conversation.id;
|
|
216
|
+
}
|
|
217
|
+
// Sometimes if the prompt needs a file search, the output will be an array of messages
|
|
218
|
+
// which includes multiple messages (some of them are not useful for the user, but the last one is)
|
|
219
|
+
const output = response.output || [];
|
|
220
|
+
const assistantMessages = output.filter((item) => item.type === 'message' && item.role === 'assistant');
|
|
221
|
+
if (assistantMessages.length) {
|
|
222
|
+
const text = assistantMessages.flatMap((m) => { var _a, _b; return ((_b = (_a = m.content) === null || _a === void 0 ? void 0 : _a.filter((c) => c.type === 'output_text')) === null || _b === void 0 ? void 0 : _b.map((c) => c.text)) || []; });
|
|
223
|
+
return {
|
|
224
|
+
firstChoice: text.pop(),
|
|
225
|
+
threadId: this.conversationId,
|
|
226
|
+
usageTokens: {
|
|
227
|
+
prompt_tokens: Number((_c = ((_b = response.usage) === null || _b === void 0 ? void 0 : _b.prompt_tokens)) !== null && _c !== void 0 ? _c : 0),
|
|
228
|
+
completion_tokens: Number((_e = ((_d = response.usage) === null || _d === void 0 ? void 0 : _d.completion_tokens)) !== null && _e !== void 0 ? _e : 0),
|
|
229
|
+
total_tokens: Number((_g = ((_f = response.usage) === null || _f === void 0 ? void 0 : _f.total_tokens)) !== null && _g !== void 0 ? _g : 0),
|
|
230
|
+
},
|
|
231
|
+
};
|
|
232
|
+
}
|
|
233
|
+
if (response.output_text) {
|
|
234
|
+
return {
|
|
235
|
+
firstChoice: response.output_text,
|
|
236
|
+
threadId: this.conversationId,
|
|
237
|
+
usageTokens: {
|
|
238
|
+
prompt_tokens: Number((_j = ((_h = response.usage) === null || _h === void 0 ? void 0 : _h.prompt_tokens)) !== null && _j !== void 0 ? _j : 0),
|
|
239
|
+
completion_tokens: Number((_l = ((_k = response.usage) === null || _k === void 0 ? void 0 : _k.completion_tokens)) !== null && _l !== void 0 ? _l : 0),
|
|
240
|
+
total_tokens: Number((_o = ((_m = response.usage) === null || _m === void 0 ? void 0 : _m.total_tokens)) !== null && _o !== void 0 ? _o : 0),
|
|
241
|
+
},
|
|
242
|
+
};
|
|
243
|
+
}
|
|
244
|
+
return undefined;
|
|
245
|
+
});
|
|
246
|
+
}
|
|
151
247
|
}
|
|
152
248
|
exports.CopilotService = CopilotService;
|
|
153
|
-
_CopilotService_instances = new WeakSet(), _CopilotService_processSuggestions = function _CopilotService_processSuggestions(suggestions) {
|
|
154
|
-
suggestions = suggestions ? suggestions : [];
|
|
155
|
-
suggestions = suggestions.filter(suggestion => !!suggestion.trim());
|
|
156
|
-
return suggestions;
|
|
157
|
-
};
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import ChatGptResponse from '../../models/ChatGptResponse';
|
|
2
|
+
import OpenAI from "openai";
|
|
3
|
+
import BaseService from '../BaseService/BaseService';
|
|
4
|
+
interface ResponseServiceOptions {
|
|
5
|
+
instructions?: string;
|
|
6
|
+
tools?: any[];
|
|
7
|
+
functionOutputs?: string;
|
|
8
|
+
definedSchema?: any;
|
|
9
|
+
conversationId?: string;
|
|
10
|
+
}
|
|
11
|
+
export declare class ResponseService extends BaseService {
|
|
12
|
+
promptId: string | undefined;
|
|
13
|
+
conversationId: string | undefined;
|
|
14
|
+
lastResponseId: string | undefined;
|
|
15
|
+
constructor(apiKey?: string, promptId?: string, conversationId?: string);
|
|
16
|
+
/**
|
|
17
|
+
* Create a new conversation/response chain
|
|
18
|
+
*/
|
|
19
|
+
createConversation(): Promise<string>;
|
|
20
|
+
/**
|
|
21
|
+
* Get the reply using the Response API
|
|
22
|
+
*
|
|
23
|
+
* @param message
|
|
24
|
+
* @param runOptions
|
|
25
|
+
*/
|
|
26
|
+
getReply(message: string, runOptions?: ResponseServiceOptions): Promise<ChatGptResponse | undefined>;
|
|
27
|
+
handleFunctionOutputs(openai: OpenAI, functionOutputs: string, runOptions?: ResponseServiceOptions): Promise<ChatGptResponse>;
|
|
28
|
+
processResponseOutput(response: any): ChatGptResponse;
|
|
29
|
+
reset(): void;
|
|
30
|
+
getConversationId(): string | undefined;
|
|
31
|
+
getLastResponseId(): string | undefined;
|
|
32
|
+
getPromptId(): string | undefined;
|
|
33
|
+
setPromptId(promptId: string): void;
|
|
34
|
+
setConversationId(conversationId: string): void;
|
|
35
|
+
setLastResponseId(lastResponseId: string): void;
|
|
36
|
+
}
|
|
37
|
+
export {};
|
|
@@ -0,0 +1,213 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
5
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
6
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
7
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
8
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
|
+
});
|
|
10
|
+
};
|
|
11
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
12
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
13
|
+
};
|
|
14
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
+
exports.ResponseService = void 0;
|
|
16
|
+
const logger_1 = __importDefault(require("../logger"));
|
|
17
|
+
const openai_1 = __importDefault(require("openai"));
|
|
18
|
+
const BaseService_1 = __importDefault(require("../BaseService/BaseService"));
|
|
19
|
+
class ResponseService extends BaseService_1.default {
|
|
20
|
+
constructor(apiKey, promptId, conversationId) {
|
|
21
|
+
super(apiKey);
|
|
22
|
+
Object.defineProperty(this, "promptId", {
|
|
23
|
+
enumerable: true,
|
|
24
|
+
configurable: true,
|
|
25
|
+
writable: true,
|
|
26
|
+
value: void 0
|
|
27
|
+
});
|
|
28
|
+
Object.defineProperty(this, "conversationId", {
|
|
29
|
+
enumerable: true,
|
|
30
|
+
configurable: true,
|
|
31
|
+
writable: true,
|
|
32
|
+
value: void 0
|
|
33
|
+
});
|
|
34
|
+
Object.defineProperty(this, "lastResponseId", {
|
|
35
|
+
enumerable: true,
|
|
36
|
+
configurable: true,
|
|
37
|
+
writable: true,
|
|
38
|
+
value: void 0
|
|
39
|
+
});
|
|
40
|
+
this.promptId = promptId;
|
|
41
|
+
this.conversationId = conversationId;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Create a new conversation/response chain
|
|
45
|
+
*/
|
|
46
|
+
createConversation() {
|
|
47
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
48
|
+
// Create a real conversation using the Conversations API
|
|
49
|
+
const openai = new openai_1.default({ apiKey: this.openaiApiKey });
|
|
50
|
+
const conversation = yield openai.conversations.create();
|
|
51
|
+
this.conversationId = conversation.id;
|
|
52
|
+
return this.conversationId;
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
/**
|
|
56
|
+
* Get the reply using the Response API
|
|
57
|
+
*
|
|
58
|
+
* @param message
|
|
59
|
+
* @param runOptions
|
|
60
|
+
*/
|
|
61
|
+
getReply(message, runOptions = {}) {
|
|
62
|
+
var _a, _b;
|
|
63
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
64
|
+
if (!this.promptId) {
|
|
65
|
+
logger_1.default.error('Prompt ID is required for Response API');
|
|
66
|
+
return Promise.reject(new Error('Prompt ID is required for Response API'));
|
|
67
|
+
}
|
|
68
|
+
logger_1.default.info(`New response with message: ${message} & options: ${JSON.stringify(runOptions)}`);
|
|
69
|
+
const openai = new openai_1.default({ apiKey: this.openaiApiKey });
|
|
70
|
+
try {
|
|
71
|
+
if (runOptions.functionOutputs) {
|
|
72
|
+
return yield this.handleFunctionOutputs(openai, runOptions.functionOutputs, runOptions);
|
|
73
|
+
}
|
|
74
|
+
if (!runOptions.conversationId && !this.conversationId) {
|
|
75
|
+
const createdId = yield this.createConversation();
|
|
76
|
+
this.conversationId = createdId;
|
|
77
|
+
}
|
|
78
|
+
const responseRequest = {
|
|
79
|
+
input: message,
|
|
80
|
+
store: true,
|
|
81
|
+
include: ['file_search_call.results'],
|
|
82
|
+
};
|
|
83
|
+
if (this.promptId) {
|
|
84
|
+
responseRequest.prompt = {
|
|
85
|
+
id: this.promptId
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
if (runOptions.instructions) {
|
|
89
|
+
responseRequest.instructions = runOptions.instructions;
|
|
90
|
+
}
|
|
91
|
+
const conversationIdToUse = runOptions.conversationId || this.conversationId;
|
|
92
|
+
if (conversationIdToUse) {
|
|
93
|
+
responseRequest.conversation = conversationIdToUse;
|
|
94
|
+
}
|
|
95
|
+
if ((_a = runOptions.tools) === null || _a === void 0 ? void 0 : _a.length) {
|
|
96
|
+
responseRequest.tools = runOptions.tools;
|
|
97
|
+
}
|
|
98
|
+
if (runOptions.definedSchema) {
|
|
99
|
+
responseRequest.text = {
|
|
100
|
+
format: runOptions.definedSchema
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
const response = yield openai.responses.create(responseRequest);
|
|
104
|
+
this.lastResponseId = response.id;
|
|
105
|
+
if ((_b = response.conversation) === null || _b === void 0 ? void 0 : _b.id) {
|
|
106
|
+
this.conversationId = response.conversation.id;
|
|
107
|
+
}
|
|
108
|
+
else if (runOptions.conversationId) {
|
|
109
|
+
this.conversationId = runOptions.conversationId;
|
|
110
|
+
}
|
|
111
|
+
return this.processResponseOutput(response);
|
|
112
|
+
}
|
|
113
|
+
catch (error) {
|
|
114
|
+
logger_1.default.error('Error in ResponseService.getReply:', error);
|
|
115
|
+
return Promise.reject(error);
|
|
116
|
+
}
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
handleFunctionOutputs(openai, functionOutputs, runOptions = {}) {
|
|
120
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
121
|
+
try {
|
|
122
|
+
const toolOutputs = JSON.parse(functionOutputs);
|
|
123
|
+
const formattedInputs = toolOutputs.map((output) => ({
|
|
124
|
+
type: 'function_call_output',
|
|
125
|
+
call_id: output.call_id,
|
|
126
|
+
output: output.output
|
|
127
|
+
}));
|
|
128
|
+
const responseRequest = {
|
|
129
|
+
input: formattedInputs,
|
|
130
|
+
store: true,
|
|
131
|
+
};
|
|
132
|
+
const conversationIdToUse = runOptions.conversationId || this.conversationId;
|
|
133
|
+
if (!conversationIdToUse) {
|
|
134
|
+
const createdId = yield this.createConversation();
|
|
135
|
+
this.conversationId = createdId;
|
|
136
|
+
}
|
|
137
|
+
responseRequest.conversation = runOptions.conversationId || this.conversationId;
|
|
138
|
+
if (this.promptId) {
|
|
139
|
+
responseRequest.prompt = {
|
|
140
|
+
id: this.promptId
|
|
141
|
+
};
|
|
142
|
+
}
|
|
143
|
+
const response = yield openai.responses.create(responseRequest);
|
|
144
|
+
this.lastResponseId = response.id;
|
|
145
|
+
return this.processResponseOutput(response);
|
|
146
|
+
}
|
|
147
|
+
catch (error) {
|
|
148
|
+
logger_1.default.error('Error handling function outputs:', error);
|
|
149
|
+
throw error;
|
|
150
|
+
}
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
processResponseOutput(response) {
|
|
154
|
+
const output = response.output || [];
|
|
155
|
+
const assistantMessages = output.filter((item) => item.type === 'message' && item.role === 'assistant');
|
|
156
|
+
const functionCalls = output.filter((item) => item.type === 'function_call');
|
|
157
|
+
if (functionCalls.length > 0) {
|
|
158
|
+
return {
|
|
159
|
+
requiredActions: JSON.stringify(functionCalls),
|
|
160
|
+
threadId: this.conversationId,
|
|
161
|
+
usageTokens: response.usage,
|
|
162
|
+
};
|
|
163
|
+
}
|
|
164
|
+
if (assistantMessages.length > 0) {
|
|
165
|
+
const textContent = assistantMessages
|
|
166
|
+
.flatMap((msg) => msg.content || [])
|
|
167
|
+
.filter((content) => content.type === 'output_text' || content.type === 'text')
|
|
168
|
+
.map((content) => content.text || content.value)
|
|
169
|
+
.filter((text) => text);
|
|
170
|
+
if (textContent) {
|
|
171
|
+
return {
|
|
172
|
+
firstChoice: textContent.pop().replace(/【.*?】/g, ''),
|
|
173
|
+
threadId: this.conversationId,
|
|
174
|
+
usageTokens: response.usage,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
if (response.output_text) {
|
|
179
|
+
return {
|
|
180
|
+
firstChoice: response.output_text.replace(/【.*?】/g, ''),
|
|
181
|
+
threadId: this.conversationId,
|
|
182
|
+
usageTokens: response.usage,
|
|
183
|
+
};
|
|
184
|
+
}
|
|
185
|
+
return {
|
|
186
|
+
threadId: this.conversationId,
|
|
187
|
+
usageTokens: response.usage,
|
|
188
|
+
};
|
|
189
|
+
}
|
|
190
|
+
reset() {
|
|
191
|
+
this.lastResponseId = undefined;
|
|
192
|
+
this.conversationId = undefined;
|
|
193
|
+
}
|
|
194
|
+
getConversationId() {
|
|
195
|
+
return this.conversationId;
|
|
196
|
+
}
|
|
197
|
+
getLastResponseId() {
|
|
198
|
+
return this.lastResponseId;
|
|
199
|
+
}
|
|
200
|
+
getPromptId() {
|
|
201
|
+
return this.promptId;
|
|
202
|
+
}
|
|
203
|
+
setPromptId(promptId) {
|
|
204
|
+
this.promptId = promptId;
|
|
205
|
+
}
|
|
206
|
+
setConversationId(conversationId) {
|
|
207
|
+
this.conversationId = conversationId;
|
|
208
|
+
}
|
|
209
|
+
setLastResponseId(lastResponseId) {
|
|
210
|
+
this.lastResponseId = lastResponseId;
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
exports.ResponseService = ResponseService;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import BaseService from '../BaseService/BaseService';
|
|
2
|
-
import
|
|
2
|
+
import ChatGptResponse from '../../models/ChatGptResponse';
|
|
3
3
|
export declare class TranslationService extends BaseService {
|
|
4
4
|
constructor(apiKey?: string, model?: string, apiUrl?: string, maxNumberOfChoices?: number);
|
|
5
5
|
/**
|
|
@@ -9,17 +9,17 @@ export declare class TranslationService extends BaseService {
|
|
|
9
9
|
* @param toLanguage the desired language to translate to ( English is the default )
|
|
10
10
|
* @param fromLanguage if we want to specify the language of the text, we can use this ( optional)
|
|
11
11
|
*/
|
|
12
|
-
translate(text: string, toLanguage?: string, fromLanguage?: string): Promise<
|
|
12
|
+
translate(text: string, toLanguage?: string, fromLanguage?: string): Promise<ChatGptResponse | undefined>;
|
|
13
13
|
/**
|
|
14
14
|
* Detects the ISO language code of a text
|
|
15
15
|
*
|
|
16
16
|
* @param text text to detect
|
|
17
17
|
*/
|
|
18
|
-
findTextLanguage(text: string): Promise<
|
|
18
|
+
findTextLanguage(text: string): Promise<ChatGptResponse | undefined>;
|
|
19
19
|
/**
|
|
20
20
|
* Detects the ISO language code of a text based on frequency of words
|
|
21
21
|
*
|
|
22
22
|
* @param text text to detect
|
|
23
23
|
*/
|
|
24
|
-
findTextLanguageBasedOnFrequency(text: string): Promise<
|
|
24
|
+
findTextLanguageBasedOnFrequency(text: string): Promise<ChatGptResponse | undefined>;
|
|
25
25
|
}
|
|
@@ -13,8 +13,8 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
13
13
|
};
|
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
15
|
exports.TranslationService = void 0;
|
|
16
|
-
const constants_1 = require("../../
|
|
17
|
-
const
|
|
16
|
+
const constants_1 = require("../../constants");
|
|
17
|
+
const ChatGptMessage_1 = require("../../models/ChatGptMessage");
|
|
18
18
|
const logger_1 = __importDefault(require("../logger"));
|
|
19
19
|
const BaseService_1 = __importDefault(require("../BaseService/BaseService"));
|
|
20
20
|
class TranslationService extends BaseService_1.default {
|
|
@@ -42,20 +42,19 @@ class TranslationService extends BaseService_1.default {
|
|
|
42
42
|
response_format: { type: 'json_object' },
|
|
43
43
|
messages: [
|
|
44
44
|
{
|
|
45
|
-
role:
|
|
45
|
+
role: ChatGptMessage_1.ChatGptRole.SYSTEM,
|
|
46
46
|
content: constants_1.TRANSLATION_SYSTEM_ROLE,
|
|
47
47
|
},
|
|
48
48
|
{
|
|
49
|
-
role:
|
|
49
|
+
role: ChatGptMessage_1.ChatGptRole.USER,
|
|
50
50
|
content: translateText,
|
|
51
51
|
},
|
|
52
52
|
],
|
|
53
53
|
};
|
|
54
54
|
try {
|
|
55
|
-
logger_1.default.info({ requestBody }, ':: TranslationServicee.translate :: Translating ::');
|
|
56
55
|
const response = yield this.request.post('', requestBody);
|
|
57
56
|
return {
|
|
58
|
-
|
|
57
|
+
firstChoice: this.getResponseFirstChoice(response),
|
|
59
58
|
usageTokens: this.getResponseUsageTokens(response),
|
|
60
59
|
};
|
|
61
60
|
}
|
|
@@ -81,20 +80,19 @@ class TranslationService extends BaseService_1.default {
|
|
|
81
80
|
response_format: { type: 'json_object' },
|
|
82
81
|
messages: [
|
|
83
82
|
{
|
|
84
|
-
role:
|
|
83
|
+
role: ChatGptMessage_1.ChatGptRole.SYSTEM,
|
|
85
84
|
content: constants_1.LANGUAGE_DETECTION_SYSTEM_ROLE,
|
|
86
85
|
},
|
|
87
86
|
{
|
|
88
|
-
role:
|
|
87
|
+
role: ChatGptMessage_1.ChatGptRole.USER,
|
|
89
88
|
content: translateText,
|
|
90
89
|
}
|
|
91
90
|
],
|
|
92
91
|
};
|
|
93
92
|
try {
|
|
94
|
-
logger_1.default.info({ requestBody }, ':: TranslationServicee.findTextLanguage :: Finding text language ::');
|
|
95
93
|
const response = yield this.request.post('', requestBody);
|
|
96
94
|
return {
|
|
97
|
-
|
|
95
|
+
firstChoice: this.getResponseFirstChoice(response),
|
|
98
96
|
usageTokens: this.getResponseUsageTokens(response),
|
|
99
97
|
};
|
|
100
98
|
}
|
|
@@ -120,20 +118,19 @@ class TranslationService extends BaseService_1.default {
|
|
|
120
118
|
response_format: { type: 'json_object' },
|
|
121
119
|
messages: [
|
|
122
120
|
{
|
|
123
|
-
role:
|
|
121
|
+
role: ChatGptMessage_1.ChatGptRole.SYSTEM,
|
|
124
122
|
content: constants_1.WORD_FREQUENCY_LANGUAGE_DETECTION_SYSTEM_ROLE,
|
|
125
123
|
},
|
|
126
124
|
{
|
|
127
|
-
role:
|
|
125
|
+
role: ChatGptMessage_1.ChatGptRole.USER,
|
|
128
126
|
content: translateText,
|
|
129
127
|
}
|
|
130
128
|
],
|
|
131
129
|
};
|
|
132
130
|
try {
|
|
133
|
-
logger_1.default.info({ requestBody }, ':: TranslationServicee.findTextLanguageBasedOnFrequency :: Finding text language ::');
|
|
134
131
|
const response = yield this.request.post('', requestBody);
|
|
135
132
|
return {
|
|
136
|
-
|
|
133
|
+
firstChoice: this.getResponseFirstChoice(response),
|
|
137
134
|
usageTokens: this.getResponseUsageTokens(response),
|
|
138
135
|
};
|
|
139
136
|
}
|