@futdevpro/nts-dynamo 1.14.35 → 1.14.36
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/build/_modules/ai/_models/ai-input-interfaces.d.ts +20 -28
- package/build/_modules/ai/_models/ai-input-interfaces.d.ts.map +1 -1
- package/build/_modules/ai/_models/ai-input-interfaces.js +3 -0
- package/build/_modules/ai/_models/ai-input-interfaces.js.map +1 -1
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.d.ts +14 -58
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.d.ts.map +1 -1
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.js +138 -147
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.js.map +1 -1
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.d.ts +27 -180
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.d.ts.map +1 -1
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.js +147 -328
- package/build/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.js.map +1 -1
- package/build/_modules/ai/_services/ai-llm-chat.service-base.d.ts +22 -14
- package/build/_modules/ai/_services/ai-llm-chat.service-base.d.ts.map +1 -1
- package/build/_modules/ai/_services/ai-llm-chat.service-base.js.map +1 -1
- package/build/_modules/ai/_services/ai-llm.service-base.d.ts +52 -21
- package/build/_modules/ai/_services/ai-llm.service-base.d.ts.map +1 -1
- package/build/_modules/ai/_services/ai-llm.service-base.js +171 -0
- package/build/_modules/ai/_services/ai-llm.service-base.js.map +1 -1
- package/build/_modules/ai/_services/ai-provider.service-base.d.ts +1 -1
- package/build/_modules/ai/_services/ai-provider.service-base.d.ts.map +1 -1
- package/build/_modules/assistant/_services/ass-io.control-service.js +2 -2
- package/build/_modules/assistant/_services/ass-io.control-service.js.map +1 -1
- package/build/_modules/discord-assistant/_services/dias-chunk.data-service.js +9 -9
- package/build/_modules/discord-assistant/_services/dias-chunk.data-service.js.map +1 -1
- package/build/_modules/discord-assistant/_services/dias-io.control-service.js +2 -2
- package/build/_modules/discord-assistant/_services/dias-io.control-service.js.map +1 -1
- package/package.json +1 -1
- package/src/_modules/ai/_models/ai-input-interfaces.ts +63 -26
- package/src/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.ts +99 -139
- package/src/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.ts +246 -294
- package/src/_modules/ai/_services/ai-llm-chat.service-base.ts +36 -16
- package/src/_modules/ai/_services/ai-llm.service-base.ts +272 -28
- package/src/_modules/ai/_services/ai-provider.service-base.ts +1 -1
- package/src/_modules/assistant/_services/ass-io.control-service.ts +2 -2
- package/src/_modules/discord-assistant/_services/dias-chunk.data-service.ts +9 -9
- package/src/_modules/discord-assistant/_services/dias-io.control-service.ts +2 -2
|
@@ -1,21 +1,23 @@
|
|
|
1
1
|
import { DyNTS_AI_LLM_ServiceBase } from './ai-llm.service-base';
|
|
2
|
-
import { DyFM_AI_Message } from '@futdevpro/fsm-dynamo/ai';
|
|
2
|
+
import { DyFM_AI_Message, DyFM_AI_CallSettings } from '@futdevpro/fsm-dynamo/ai';
|
|
3
3
|
import {
|
|
4
|
-
|
|
4
|
+
DyFM_AI_ConversationBase_Input,
|
|
5
5
|
DyFM_AI_ConversationSelect_Input,
|
|
6
6
|
DyFM_AI_ConversationGenericSelect_Input,
|
|
7
7
|
DyFM_AI_ConversationMultiSelect_Input,
|
|
8
8
|
DyFM_AI_ConversationGenericMultiSelect_Input,
|
|
9
9
|
DyFM_AI_ConversationJSONKeysDescription_Input,
|
|
10
10
|
DyFM_AI_ConversationJSONExactKeys_Input,
|
|
11
|
-
DyFM_AI_ConversationGetAnswer_Input
|
|
12
11
|
} from '../_models/ai-input-interfaces';
|
|
12
|
+
import { DyFM_getLocalStackLocation, DyFM_Log } from '@futdevpro/fsm-dynamo';
|
|
13
13
|
|
|
14
14
|
/**
|
|
15
15
|
* Abstract base class for LLM Chat services
|
|
16
16
|
* Extends LLM service with conversation management capabilities
|
|
17
17
|
*/
|
|
18
|
-
export abstract class DyNTS_AI_LLMChat_ServiceBase
|
|
18
|
+
export abstract class DyNTS_AI_LLMChat_ServiceBase<
|
|
19
|
+
T_AISettings extends DyFM_AI_CallSettings = DyFM_AI_CallSettings
|
|
20
|
+
> extends DyNTS_AI_LLM_ServiceBase<T_AISettings> {
|
|
19
21
|
// History management
|
|
20
22
|
/**
|
|
21
23
|
* Add a message to the conversation history
|
|
@@ -33,16 +35,34 @@ export abstract class DyNTS_AI_LLMChat_ServiceBase extends DyNTS_AI_LLM_ServiceB
|
|
|
33
35
|
/* abstract getHistory(issuer: string): DyFM_AI_Message[]; */
|
|
34
36
|
|
|
35
37
|
// Conversation methods (from OAI_LLMChat_ServiceBase)
|
|
36
|
-
abstract
|
|
37
|
-
abstract
|
|
38
|
-
abstract
|
|
39
|
-
|
|
40
|
-
abstract
|
|
41
|
-
abstract
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
abstract
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
abstract
|
|
38
|
+
abstract requestSimpleMessageInConversation(set: DyFM_AI_ConversationBase_Input<T_AISettings>): Promise<string>;
|
|
39
|
+
abstract requestYesNoInConversation(set: DyFM_AI_ConversationBase_Input<T_AISettings>): Promise<boolean>;
|
|
40
|
+
abstract requestPercentageInConversation(set: DyFM_AI_ConversationBase_Input<T_AISettings>): Promise<number>;
|
|
41
|
+
|
|
42
|
+
/* abstract selectQuestionInConversation(set: DyFM_AI_ConversationSelect_Input): Promise<string>; */
|
|
43
|
+
abstract requestSelectInConversation<T>(
|
|
44
|
+
set: DyFM_AI_ConversationGenericSelect_Input<T, T_AISettings>
|
|
45
|
+
): Promise<T | { unparsableResult: string }>;
|
|
46
|
+
/* abstract multipleSelectQuestionInConversationWithOptions(
|
|
47
|
+
set: DyFM_AI_ConversationMultiSelect_Input<T_AISettings>
|
|
48
|
+
): Promise<string[]>; */
|
|
49
|
+
abstract requestMultiselectInConversation<T>(
|
|
50
|
+
set: DyFM_AI_ConversationGenericMultiSelect_Input<T, T_AISettings>
|
|
51
|
+
): Promise<T[] | { unparsableResult: string }>;
|
|
52
|
+
|
|
53
|
+
abstract requestJSONInConversation<T = any>(
|
|
54
|
+
set: DyFM_AI_ConversationBase_Input<T_AISettings>
|
|
55
|
+
): Promise<T | { unparsableResult: string }>;
|
|
56
|
+
abstract requestJSONInConversationWithKeysDescription<T>(
|
|
57
|
+
set: DyFM_AI_ConversationJSONKeysDescription_Input<T_AISettings>
|
|
58
|
+
): Promise<T | { unparsableResult: string }>;
|
|
59
|
+
abstract requestJSONInConversationWithExactKeys<T>(
|
|
60
|
+
set: DyFM_AI_ConversationJSONExactKeys_Input<T_AISettings>
|
|
61
|
+
): Promise<T | { unparsableResult: string }>;
|
|
62
|
+
//abstract getQuestionAnswerInConversation(set: DyFM_AI_ConversationQuestion_Input): Promise<string>;
|
|
63
|
+
//abstract getAnswerInConversation(set: DyFM_AI_ConversationGetAnswer_Input): Promise<string>;
|
|
64
|
+
|
|
65
|
+
abstract requestListInConversation(
|
|
66
|
+
set: DyFM_AI_ConversationBase_Input<T_AISettings>
|
|
67
|
+
): Promise<string[] | { unparsableResult: string }>;
|
|
48
68
|
}
|
|
@@ -1,72 +1,101 @@
|
|
|
1
1
|
import { DyNTS_AI_Provider_ServiceBase } from './ai-provider.service-base';
|
|
2
|
-
import { DyFM_AI_CallSettings, DyFM_AI_Message, DyFM_AI_LLM_Response } from '@futdevpro/fsm-dynamo/ai';
|
|
3
|
-
import { DyFM_Error_Settings } from '@futdevpro/fsm-dynamo';
|
|
2
|
+
import { DyFM_AI_CallSettings, DyFM_AI_Message, DyFM_AI_LLM_Response, DyFM_AI_MessageRole } from '@futdevpro/fsm-dynamo/ai';
|
|
3
|
+
import { DyFM_Error, DyFM_Error_Settings, DyFM_getLocalStackLocation, DyFM_Log, DyFM_Object } from '@futdevpro/fsm-dynamo';
|
|
4
4
|
import {
|
|
5
|
-
DyFM_AI_Question_Input,
|
|
6
|
-
DyFM_AI_ListSelect_Input,
|
|
7
5
|
DyFM_AI_GenericSelect_Input,
|
|
8
|
-
DyFM_AI_MultiSelect_Input,
|
|
9
6
|
DyFM_AI_GenericMultiSelect_Input,
|
|
10
7
|
DyFM_AI_JSONKeysDescription_Input,
|
|
11
8
|
DyFM_AI_JSONExactKeys_Input,
|
|
12
|
-
|
|
9
|
+
DyFM_AI_Message_Input,
|
|
13
10
|
} from '../_models/ai-input-interfaces';
|
|
11
|
+
import { Items } from 'openai/resources/conversations/items';
|
|
14
12
|
|
|
15
13
|
/**
|
|
16
14
|
* Abstract base class for LLM services
|
|
17
15
|
* Defines all methods that must be implemented by AI providers
|
|
18
16
|
*/
|
|
19
|
-
export abstract class DyNTS_AI_LLM_ServiceBase
|
|
17
|
+
export abstract class DyNTS_AI_LLM_ServiceBase<
|
|
18
|
+
T_AISettings extends DyFM_AI_CallSettings = DyFM_AI_CallSettings
|
|
19
|
+
> extends DyNTS_AI_Provider_ServiceBase {
|
|
20
20
|
/** Default settings for LLM calls */
|
|
21
|
-
abstract readonly defaultSettings:
|
|
21
|
+
abstract readonly defaultSettings: T_AISettings;
|
|
22
22
|
|
|
23
23
|
/** Default model to use for LLM calls */
|
|
24
|
-
abstract readonly defaultModel: string;
|
|
24
|
+
/* abstract readonly defaultModel: string; */
|
|
25
25
|
|
|
26
26
|
/** Provider-specific predefined requests */
|
|
27
27
|
abstract readonly predefinedRequests: any;
|
|
28
|
+
|
|
29
|
+
_debugLog: boolean = false;
|
|
30
|
+
get debugLog(): boolean {
|
|
31
|
+
return this.defaultSettings?.debugLog ?? this._debugLog;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
get defaultSystemPrompt(): string {
|
|
35
|
+
return this.defaultSettings.systemPrompt;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
get defaultModel(): string {
|
|
39
|
+
return this.defaultSettings.useModel;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
defaultLogReplacer: string = '...long-context...';
|
|
28
43
|
|
|
29
44
|
// Core abstract methods
|
|
30
45
|
/**
|
|
31
46
|
* Call LLM with system and user messages
|
|
32
47
|
*/
|
|
33
|
-
abstract callLLM(
|
|
48
|
+
/* abstract callLLM(
|
|
34
49
|
systemMessage: string,
|
|
35
50
|
userMessage: string,
|
|
36
51
|
settings?: DyFM_AI_CallSettings,
|
|
37
52
|
issuer?: string
|
|
38
|
-
): Promise<string>;
|
|
53
|
+
): Promise<string>; */
|
|
39
54
|
|
|
40
55
|
/**
|
|
41
56
|
* Call LLM with message history
|
|
42
57
|
*/
|
|
43
|
-
abstract callLLMWithHistory(
|
|
58
|
+
/* abstract callLLMWithHistory(
|
|
44
59
|
messages: DyFM_AI_Message[],
|
|
45
60
|
settings?: DyFM_AI_CallSettings,
|
|
46
61
|
issuer?: string
|
|
47
|
-
): Promise<string>;
|
|
62
|
+
): Promise<string>; */
|
|
48
63
|
|
|
49
64
|
/**
|
|
50
65
|
* Call LLM and return raw response
|
|
51
66
|
*/
|
|
52
|
-
abstract callLLMRaw(
|
|
67
|
+
/* abstract callLLMRaw(
|
|
53
68
|
messages: DyFM_AI_Message[],
|
|
54
69
|
settings?: DyFM_AI_CallSettings,
|
|
55
70
|
issuer?: string
|
|
56
|
-
): Promise<DyFM_AI_LLM_Response>;
|
|
71
|
+
): Promise<DyFM_AI_LLM_Response>; */
|
|
57
72
|
|
|
58
73
|
// Question methods (from OAI_LLM_ServiceBase)
|
|
59
|
-
abstract
|
|
60
|
-
abstract
|
|
61
|
-
abstract
|
|
62
|
-
|
|
63
|
-
abstract
|
|
64
|
-
abstract
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
abstract
|
|
68
|
-
abstract
|
|
69
|
-
|
|
74
|
+
abstract requestSimpleMessage(set: DyFM_AI_Message_Input<T_AISettings>): Promise<string>;
|
|
75
|
+
abstract requestYesNo(set: DyFM_AI_Message_Input<T_AISettings>): Promise<boolean>;
|
|
76
|
+
abstract requestPercentage(set: DyFM_AI_Message_Input<T_AISettings>): Promise<number>;
|
|
77
|
+
|
|
78
|
+
/* abstract askSelectQuestion(set: DyFM_AI_ListSelect_Input): Promise<string>; */
|
|
79
|
+
abstract requestSelect<T>(
|
|
80
|
+
set: DyFM_AI_GenericSelect_Input<T, T_AISettings>
|
|
81
|
+
): Promise<T | { unparsableResult: string }>;
|
|
82
|
+
/* abstract askMultipleSelectQuestionWithOptions(set: DyFM_AI_MultiSelect_Input): Promise<string[]>; */
|
|
83
|
+
abstract requestMultiselect<T>(
|
|
84
|
+
set: DyFM_AI_GenericMultiSelect_Input<T, T_AISettings>
|
|
85
|
+
): Promise<T[] | { unparsableResult: string }>;
|
|
86
|
+
|
|
87
|
+
abstract requestJSON<T>(set: DyFM_AI_Message_Input<T_AISettings>): Promise<T | { unparsableResult: string }>;
|
|
88
|
+
abstract requestJSONQuestionWithKeysDescription<T>(
|
|
89
|
+
set: DyFM_AI_JSONKeysDescription_Input<T_AISettings>
|
|
90
|
+
): Promise<T | { unparsableResult: string }>;
|
|
91
|
+
/* abstract askJSONQuestionWithExactKeys(set: DyFM_AI_JSONExactKeys_Input): Promise<object>; */
|
|
92
|
+
abstract requestJSONWithExactKeys<T>(
|
|
93
|
+
set: DyFM_AI_JSONExactKeys_Input<T_AISettings>
|
|
94
|
+
): Promise<T | { unparsableResult: string }>;
|
|
95
|
+
/* abstract sendMessage(set: DyFM_AI_SimpleMessage_Input): Promise<string>; */
|
|
96
|
+
|
|
97
|
+
/* abstract requestStringList(set: DyFM_AI_Base_Input<T_AISettings>): Promise<string[] | { unparsableResult: string }>; */
|
|
98
|
+
abstract requestList<T>(set: DyFM_AI_Message_Input<T_AISettings>): Promise<T[] | { unparsableResult: string }>;
|
|
70
99
|
|
|
71
100
|
// Helper methods
|
|
72
101
|
/* protected abstract getDefaultErrorSettings(
|
|
@@ -75,7 +104,222 @@ export abstract class DyNTS_AI_LLM_ServiceBase extends DyNTS_AI_Provider_Service
|
|
|
75
104
|
issuer?: string
|
|
76
105
|
): DyFM_Error_Settings; */
|
|
77
106
|
|
|
78
|
-
protected abstract getTextListAsText(list: string[]): string;
|
|
107
|
+
/* protected abstract getTextListAsText(list: string[]): string; */
|
|
79
108
|
|
|
80
|
-
protected abstract logQuestion(set:
|
|
109
|
+
/* protected abstract logQuestion(set: DyFM_AI_Base_Input<T_AISettings>): void; */
|
|
110
|
+
|
|
111
|
+
protected convertAnswerToBoolean(answer: string): boolean {
|
|
112
|
+
return answer.toUpperCase().includes(this.predefinedRequests.yesNo.upperCaseYes);
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
protected convertAnswerToNumber(answer: string, message: string): number {
|
|
116
|
+
if (this.isAnswerValid(answer, message)) {
|
|
117
|
+
return null;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
if (isNaN(+answer)) {
|
|
121
|
+
DyFM_Log.T_error(
|
|
122
|
+
'DyNTS_AI_LLMChat_ServiceBase.convertAnswerToNumber got an invalid answer',
|
|
123
|
+
{
|
|
124
|
+
question: message,
|
|
125
|
+
answer: answer,
|
|
126
|
+
}
|
|
127
|
+
);
|
|
128
|
+
|
|
129
|
+
return null;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
return +answer;
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
protected convertAnswerToSelectOption<T>(answer: string, message: string, options: T[]): T {
|
|
136
|
+
if (this.isAnswerValid(answer, message)) {
|
|
137
|
+
return null;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
answer = answer.toLocaleUpperCase();
|
|
141
|
+
|
|
142
|
+
const stringifiedOptions: string[] = this.stringifySelectOptions(options);
|
|
143
|
+
for (const stringifiedItem of stringifiedOptions) {
|
|
144
|
+
if (answer.includes(stringifiedItem.toLocaleUpperCase())) {
|
|
145
|
+
const parsedItem: T | { unparsableResult: string } = DyFM_Object.safeParseJSON<T>(stringifiedItem);
|
|
146
|
+
|
|
147
|
+
if ((parsedItem as { unparsableResult: string }).unparsableResult) {
|
|
148
|
+
DyFM_Log.T_error(
|
|
149
|
+
'DyNTS_AI_LLMChat_ServiceBase.convertAnswerToSelectOption got an invalid answer',
|
|
150
|
+
{
|
|
151
|
+
question: message,
|
|
152
|
+
answer: answer,
|
|
153
|
+
}
|
|
154
|
+
);
|
|
155
|
+
|
|
156
|
+
return stringifiedItem as T;
|
|
157
|
+
} else {
|
|
158
|
+
return parsedItem as T;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
return null;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
protected convertAnswerToSelectOptions<T>(answer: string, message: string, options: T[]): T[] {
|
|
167
|
+
if (this.isAnswerValid(answer, message)) {
|
|
168
|
+
return null;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const enrichedOptions: { stringifiedOption: string, parsedOption: T }[] = options.map(
|
|
172
|
+
(option: T) => ({
|
|
173
|
+
stringifiedOption: this.stringifySelectOption(option),
|
|
174
|
+
parsedOption: option
|
|
175
|
+
})
|
|
176
|
+
);
|
|
177
|
+
const result: T[] = [];
|
|
178
|
+
|
|
179
|
+
for (const item of enrichedOptions) {
|
|
180
|
+
if (answer.includes(item.stringifiedOption)) {
|
|
181
|
+
result.push(item.parsedOption);
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
return result;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
protected convertAnswerToJSON<T>(answer: string, message: string): T {
|
|
189
|
+
if (this.isAnswerValid(answer, message)) {
|
|
190
|
+
return null;
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
const parsedItem: T | { unparsableResult: string } = DyFM_Object.safeParseJSON<T>(answer);
|
|
194
|
+
if ((parsedItem as { unparsableResult: string }).unparsableResult) {
|
|
195
|
+
DyFM_Log.T_error(
|
|
196
|
+
'DyNTS_AI_LLMChat_ServiceBase.convertAnswerToJSON got an invalid answer',
|
|
197
|
+
{
|
|
198
|
+
question: message,
|
|
199
|
+
answer: answer,
|
|
200
|
+
}
|
|
201
|
+
);
|
|
202
|
+
|
|
203
|
+
return null;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
return parsedItem as T;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
protected convertAnswerToList<T>(answer: string, message: string): T[] {
|
|
210
|
+
if (this.isAnswerValid(answer, message)) {
|
|
211
|
+
return null;
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
return DyFM_Object.safeParseList<T[]>(answer);
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
protected stringifySelectOptions<T>(options: T[]): string[] {
|
|
218
|
+
return options.map(item => this.stringifySelectOption(item));
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
protected stringifySelectOption<T>(option: T): string {
|
|
222
|
+
return JSON.stringify(option);
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
protected isAnswerValid(answer: string, message: string): boolean {
|
|
226
|
+
if (!answer?.trim?.()?.length) {
|
|
227
|
+
DyFM_Log.T_error(
|
|
228
|
+
'DyNTS_AI_LLMChat_ServiceBase.convertAnswerToSelectOption got an invalid answer',
|
|
229
|
+
{
|
|
230
|
+
question: message,
|
|
231
|
+
answer: answer,
|
|
232
|
+
}
|
|
233
|
+
);
|
|
234
|
+
|
|
235
|
+
return true;
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
return false;
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
/**
|
|
242
|
+
* olvasható mondatszerű-listaszerű formába teszi a listaelemeket
|
|
243
|
+
* pl.: ['a', 'b', 'c'] -> '"a", "b" or "c"'
|
|
244
|
+
*/
|
|
245
|
+
protected getTextListAsText(list: string[]): string {
|
|
246
|
+
list = list.filter(item => item?.trim()).map(item => `"${item}"`);
|
|
247
|
+
|
|
248
|
+
/* list = list.map(item => item.toLocaleLowerCase()); */
|
|
249
|
+
|
|
250
|
+
list.push(list.pop() + ' or ' + list.pop());
|
|
251
|
+
|
|
252
|
+
return list.join(', ');
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
protected logQuestion(
|
|
256
|
+
set: DyFM_AI_Message_Input<T_AISettings>
|
|
257
|
+
): void {
|
|
258
|
+
if (set.settings?.debugLog ?? this._debugLog) {
|
|
259
|
+
console.log('\n - ', set.message);
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
protected getDefaultSystemMessage(settings: T_AISettings): DyFM_AI_Message {
|
|
264
|
+
return {
|
|
265
|
+
role: DyFM_AI_MessageRole.system,
|
|
266
|
+
content: settings?.systemPrompt || this.defaultSystemPrompt,
|
|
267
|
+
};
|
|
268
|
+
}
|
|
269
|
+
|
|
270
|
+
protected validateConversation(conversation: DyFM_AI_Message[]): void {
|
|
271
|
+
conversation.forEach((message: DyFM_AI_Message, index: number) => {
|
|
272
|
+
if (!message.role) {
|
|
273
|
+
throw new DyFM_Error({
|
|
274
|
+
message: `Message has no role at index ${index}`,
|
|
275
|
+
additionalContent: {
|
|
276
|
+
invalidMessage: message,
|
|
277
|
+
conversation: conversation,
|
|
278
|
+
}
|
|
279
|
+
});
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
if (!message.content) {
|
|
283
|
+
throw new DyFM_Error({
|
|
284
|
+
message: `Message has no content at index ${index}`,
|
|
285
|
+
additionalContent: {
|
|
286
|
+
invalidMessage: message,
|
|
287
|
+
conversation: conversation,
|
|
288
|
+
}
|
|
289
|
+
});
|
|
290
|
+
}
|
|
291
|
+
});
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
protected logAnswer(answer: string): void {
|
|
295
|
+
if (this._debugLog) {
|
|
296
|
+
console.log(' - answer: ', answer);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
|
|
301
|
+
|
|
302
|
+
//////////////////////////////////////////////////////////////////////////////////////////
|
|
303
|
+
// LLM CHAT METHODS //
|
|
304
|
+
//////////////////////////////////////////////////////////////////////////////////////////
|
|
305
|
+
|
|
306
|
+
|
|
307
|
+
protected logConversation(
|
|
308
|
+
set: {
|
|
309
|
+
conversation: DyFM_AI_Message[],
|
|
310
|
+
debugLog?: boolean,
|
|
311
|
+
/** this is used to readably replace too long contents to eg '...' in logs */
|
|
312
|
+
replaceThisInLog?: string,
|
|
313
|
+
}
|
|
314
|
+
) {
|
|
315
|
+
if (set.debugLog || this._debugLog) {
|
|
316
|
+
DyFM_Log.info('Conversation log at', DyFM_getLocalStackLocation());
|
|
317
|
+
|
|
318
|
+
set.conversation.forEach(message => {
|
|
319
|
+
console.log(
|
|
320
|
+
` - ${message.role}: ${message.content.replace(set.replaceThisInLog, this.defaultLogReplacer)}`
|
|
321
|
+
);
|
|
322
|
+
});
|
|
323
|
+
}
|
|
324
|
+
}
|
|
81
325
|
}
|
|
@@ -18,7 +18,7 @@ export abstract class DyNTS_AI_Provider_ServiceBase extends DyNTS_SingletonServi
|
|
|
18
18
|
* Initialize the provider with configuration
|
|
19
19
|
* @param config - Provider-specific configuration
|
|
20
20
|
*/
|
|
21
|
-
abstract
|
|
21
|
+
abstract setup(config: DyFM_AI_Config): void;
|
|
22
22
|
|
|
23
23
|
/**
|
|
24
24
|
* Test the connection to the AI provider
|
|
@@ -44,12 +44,12 @@ export abstract class DyNTS_Ass_IO_ControlService extends DyNTS_Bot_IO_ControlSe
|
|
|
44
44
|
});
|
|
45
45
|
|
|
46
46
|
// Get AI response using EXISTING getAnswerInConversation method
|
|
47
|
-
const aiResult: string = await this.aiProvider.
|
|
47
|
+
const aiResult: string = await this.aiProvider.requestSimpleMessageInConversation({
|
|
48
48
|
conversation: aiMessages,
|
|
49
|
-
issuer: issuer,
|
|
50
49
|
settings: {
|
|
51
50
|
systemPrompt: this.mainBot_CS.defaultSystemPrompt,
|
|
52
51
|
},
|
|
52
|
+
issuer: issuer,
|
|
53
53
|
});
|
|
54
54
|
|
|
55
55
|
// Reply via same provider the message came from
|
|
@@ -61,9 +61,9 @@ export abstract class DyNTS_DiAs_Chunk_DataService<
|
|
|
61
61
|
try {
|
|
62
62
|
DyFM_Log.info('🔍 Document message received:', conversation[conversation.length - 1].content);
|
|
63
63
|
|
|
64
|
-
const vectorSearchNeeded: boolean = await this.llmChat_CS.
|
|
64
|
+
const vectorSearchNeeded: boolean = await this.llmChat_CS.requestYesNoInConversation({
|
|
65
65
|
conversation: conversation,
|
|
66
|
-
|
|
66
|
+
message: DyNTS_OAI_LLMDefaultPredefined_Requests.vectorSearch.doWeNeedVectorSearch,
|
|
67
67
|
issuer: this.issuer,
|
|
68
68
|
settings: {
|
|
69
69
|
systemPrompt: DyNTS_OAI_LLMDefaultPredefined_Requests.defaultSystemPrompt,
|
|
@@ -74,12 +74,12 @@ export abstract class DyNTS_DiAs_Chunk_DataService<
|
|
|
74
74
|
if (vectorSearchNeeded) {
|
|
75
75
|
result = await this.vectorSearchAndResolveConversation(conversation, limit, numberOfCandidates);
|
|
76
76
|
} else {
|
|
77
|
-
result = await this.llmChat_CS.
|
|
77
|
+
result = await this.llmChat_CS.requestSimpleMessageInConversation({
|
|
78
78
|
conversation: conversation,
|
|
79
|
-
issuer: this.issuer,
|
|
80
79
|
settings: {
|
|
81
80
|
systemPrompt: DyNTS_OAI_LLMDefaultPredefined_Requests.defaultSystemPrompt,
|
|
82
81
|
},
|
|
82
|
+
issuer: this.issuer,
|
|
83
83
|
});
|
|
84
84
|
}
|
|
85
85
|
|
|
@@ -117,15 +117,15 @@ export abstract class DyNTS_DiAs_Chunk_DataService<
|
|
|
117
117
|
|
|
118
118
|
DyFM_Log.H_success(`✅ Document search results:`, parsedSearchResults);
|
|
119
119
|
|
|
120
|
-
const result: string = await this.llmChat_CS.
|
|
120
|
+
const result: string = await this.llmChat_CS.requestSimpleMessageInConversation({
|
|
121
121
|
conversation: conversation,
|
|
122
|
-
issuer: this.issuer,
|
|
123
122
|
settings: {
|
|
124
123
|
systemPrompt:
|
|
125
124
|
DyNTS_OAI_LLMDefaultPredefined_Requests.defaultSystemPrompt +
|
|
126
125
|
DyNTS_OAI_LLMDefaultPredefined_Requests.vectorSearch.resolveSearchResults +
|
|
127
126
|
parsedSearchResults,
|
|
128
127
|
},
|
|
128
|
+
issuer: this.issuer,
|
|
129
129
|
});
|
|
130
130
|
|
|
131
131
|
return result;
|
|
@@ -146,15 +146,15 @@ export abstract class DyNTS_DiAs_Chunk_DataService<
|
|
|
146
146
|
try {
|
|
147
147
|
const lastMessage: DyFM_AI_Message = conversation[conversation.length - 1];
|
|
148
148
|
|
|
149
|
-
const searchQuestion: string = await this.llmChat_CS.
|
|
149
|
+
const searchQuestion: string = await this.llmChat_CS.requestSimpleMessageInConversation({
|
|
150
150
|
conversation: conversation,
|
|
151
|
-
|
|
152
|
-
issuer: this.issuer,
|
|
151
|
+
message: DyNTS_OAI_LLMDefaultPredefined_Requests.vectorSearch.getSearchQuestion,
|
|
153
152
|
settings: {
|
|
154
153
|
systemPrompt:
|
|
155
154
|
DyNTS_OAI_LLMDefaultPredefined_Requests.defaultSystemPrompt +
|
|
156
155
|
DyNTS_OAI_LLMDefaultPredefined_Requests.vectorSearch.systemPrompt,
|
|
157
156
|
},
|
|
157
|
+
issuer: this.issuer,
|
|
158
158
|
});
|
|
159
159
|
|
|
160
160
|
DyFM_Log.testInfo('🔍 Document search question:', searchQuestion);
|
|
@@ -39,12 +39,12 @@ export abstract class DyNTS_DiAs_IO_ControlService extends DyNTS_DiBo_IO_Control
|
|
|
39
39
|
issuer: issuer,
|
|
40
40
|
});
|
|
41
41
|
|
|
42
|
-
const gptResult: string = await this.llmChat_CS.
|
|
42
|
+
const gptResult: string = await this.llmChat_CS.requestSimpleMessageInConversation({
|
|
43
43
|
conversation: oaiMessages,
|
|
44
|
-
issuer: issuer,
|
|
45
44
|
settings: {
|
|
46
45
|
systemPrompt: this.mainDiscordBot_CS.defaultSystemPrompt,
|
|
47
46
|
},
|
|
47
|
+
issuer: issuer,
|
|
48
48
|
});
|
|
49
49
|
|
|
50
50
|
return await message.reply(gptResult);
|