@tiledesk/tiledesk-server 2.19.2 → 2.19.4
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/CHANGELOG.md +7 -0
- package/models/kb_setting.js +101 -1
- package/package.json +2 -2
- package/routes/kb.js +7 -0
- package/routes/llm.js +1 -0
- package/routes/webhook.js +1 -1
- package/services/aiManager.js +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,13 @@
|
|
|
5
5
|
🚀 IN PRODUCTION 🚀
|
|
6
6
|
(https://www.npmjs.com/package/@tiledesk/tiledesk-server/v/2.3.77)
|
|
7
7
|
|
|
8
|
+
# 2.19.4
|
|
9
|
+
- Added missing id_project in data sent for qa and single scrape
|
|
10
|
+
|
|
11
|
+
# 2.19.3
|
|
12
|
+
- Fixed bug on AiPrompt action with vllm models
|
|
13
|
+
- Updated tybot-connector to 2.1.2
|
|
14
|
+
|
|
8
15
|
# 2.19.2
|
|
9
16
|
- Improved vLLM integration in order to support multiple servers
|
|
10
17
|
- Added custom_regex option for .txt and .md file uploaded in a Knowledge Base
|
package/models/kb_setting.js
CHANGED
|
@@ -20,6 +20,67 @@ let expireAnsweredAfterSeconds = ttlSecondsFromEnv(
|
|
|
20
20
|
DEFAULT_ANSWERED_TTL_SEC
|
|
21
21
|
);
|
|
22
22
|
|
|
23
|
+
const EMPTY_EMBEDDING_API_KEY = '';
|
|
24
|
+
|
|
25
|
+
function logEmbeddingApiKeyWriteAttempt(source, attemptedValue, meta = {}) {
|
|
26
|
+
if (attemptedValue === EMPTY_EMBEDDING_API_KEY || attemptedValue == null) {
|
|
27
|
+
return;
|
|
28
|
+
}
|
|
29
|
+
winston.warn('[Namespace.embedding.api_key] non-empty value blocked on ' + source, {
|
|
30
|
+
...meta,
|
|
31
|
+
attemptedValue,
|
|
32
|
+
stack: new Error().stack
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
function sanitizeEmbeddingApiKeyObject(embedding, source, meta = {}) {
|
|
37
|
+
if (!embedding || typeof embedding !== 'object') {
|
|
38
|
+
return false;
|
|
39
|
+
}
|
|
40
|
+
if (!Object.prototype.hasOwnProperty.call(embedding, 'api_key')) {
|
|
41
|
+
return false;
|
|
42
|
+
}
|
|
43
|
+
if (embedding.api_key === EMPTY_EMBEDDING_API_KEY || embedding.api_key == null) {
|
|
44
|
+
embedding.api_key = EMPTY_EMBEDDING_API_KEY;
|
|
45
|
+
return false;
|
|
46
|
+
}
|
|
47
|
+
logEmbeddingApiKeyWriteAttempt(source, embedding.api_key, meta);
|
|
48
|
+
embedding.api_key = EMPTY_EMBEDDING_API_KEY;
|
|
49
|
+
return true;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
function sanitizeEmbeddingApiKeyUpdate(update, source, meta = {}) {
|
|
53
|
+
if (!update || typeof update !== 'object') {
|
|
54
|
+
return false;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
let changed = false;
|
|
58
|
+
|
|
59
|
+
const sanitizeContainer = (container) => {
|
|
60
|
+
if (!container || typeof container !== 'object') {
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
63
|
+
if (sanitizeEmbeddingApiKeyObject(container.embedding, source, meta)) {
|
|
64
|
+
changed = true;
|
|
65
|
+
}
|
|
66
|
+
if (Object.prototype.hasOwnProperty.call(container, 'embedding.api_key')
|
|
67
|
+
&& container['embedding.api_key'] !== EMPTY_EMBEDDING_API_KEY) {
|
|
68
|
+
logEmbeddingApiKeyWriteAttempt(source, container['embedding.api_key'], meta);
|
|
69
|
+
container['embedding.api_key'] = EMPTY_EMBEDDING_API_KEY;
|
|
70
|
+
changed = true;
|
|
71
|
+
}
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
sanitizeContainer(update);
|
|
75
|
+
['$set', '$setOnInsert'].forEach((key) => {
|
|
76
|
+
if (update[key]) {
|
|
77
|
+
sanitizeContainer(update[key]);
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
|
|
81
|
+
return changed;
|
|
82
|
+
}
|
|
83
|
+
|
|
23
84
|
|
|
24
85
|
const EngineSchema = new Schema({
|
|
25
86
|
name: {
|
|
@@ -77,7 +138,12 @@ const EmbeddingSchema = new Schema({
|
|
|
77
138
|
},
|
|
78
139
|
api_key: {
|
|
79
140
|
type: String,
|
|
80
|
-
required: false
|
|
141
|
+
required: false,
|
|
142
|
+
default: EMPTY_EMBEDDING_API_KEY,
|
|
143
|
+
set: function (value) {
|
|
144
|
+
logEmbeddingApiKeyWriteAttempt('embedding.api_key setter', value);
|
|
145
|
+
return EMPTY_EMBEDDING_API_KEY;
|
|
146
|
+
}
|
|
81
147
|
}
|
|
82
148
|
}, {
|
|
83
149
|
_id: false // This is schema is always used as an embedded object inside NamespaceSchema
|
|
@@ -120,6 +186,40 @@ const NamespaceSchema = new Schema({
|
|
|
120
186
|
timestamps: true
|
|
121
187
|
})
|
|
122
188
|
|
|
189
|
+
NamespaceSchema.pre('save', function (next) {
|
|
190
|
+
if (this.isModified('embedding.api_key')) {
|
|
191
|
+
const attemptedValue = this.get('embedding.api_key');
|
|
192
|
+
logEmbeddingApiKeyWriteAttempt('save', attemptedValue, {
|
|
193
|
+
namespaceId: this.id,
|
|
194
|
+
id_project: this.id_project
|
|
195
|
+
});
|
|
196
|
+
this.set('embedding.api_key', EMPTY_EMBEDDING_API_KEY);
|
|
197
|
+
}
|
|
198
|
+
next();
|
|
199
|
+
});
|
|
200
|
+
|
|
201
|
+
['updateOne', 'updateMany', 'findOneAndUpdate'].forEach((hook) => {
|
|
202
|
+
NamespaceSchema.pre(hook, function (next) {
|
|
203
|
+
const update = this.getUpdate();
|
|
204
|
+
if (sanitizeEmbeddingApiKeyUpdate(update, hook, { query: this.getQuery() })) {
|
|
205
|
+
this.setUpdate(update);
|
|
206
|
+
}
|
|
207
|
+
next();
|
|
208
|
+
});
|
|
209
|
+
});
|
|
210
|
+
|
|
211
|
+
NamespaceSchema.pre('insertMany', function (next, docs) {
|
|
212
|
+
if (Array.isArray(docs)) {
|
|
213
|
+
docs.forEach((doc) => {
|
|
214
|
+
sanitizeEmbeddingApiKeyObject(doc.embedding, 'insertMany', {
|
|
215
|
+
namespaceId: doc.id,
|
|
216
|
+
id_project: doc.id_project
|
|
217
|
+
});
|
|
218
|
+
});
|
|
219
|
+
}
|
|
220
|
+
next();
|
|
221
|
+
});
|
|
222
|
+
|
|
123
223
|
var KBSchema = new Schema({
|
|
124
224
|
id_project: {
|
|
125
225
|
type: String,
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tiledesk/tiledesk-server",
|
|
3
3
|
"description": "The Tiledesk server module",
|
|
4
|
-
"version": "2.19.
|
|
4
|
+
"version": "2.19.4",
|
|
5
5
|
"scripts": {
|
|
6
6
|
"start": "node ./bin/www",
|
|
7
7
|
"pretest": "mongodb-runner start",
|
|
@@ -49,7 +49,7 @@
|
|
|
49
49
|
"@tiledesk/tiledesk-rasa-connector": "^1.0.10",
|
|
50
50
|
"@tiledesk/tiledesk-sms-connector": "^0.1.13",
|
|
51
51
|
"@tiledesk/tiledesk-telegram-connector": "^0.1.14",
|
|
52
|
-
"@tiledesk/tiledesk-tybot-connector": "^2.1.
|
|
52
|
+
"@tiledesk/tiledesk-tybot-connector": "^2.1.2",
|
|
53
53
|
"@tiledesk/tiledesk-voice-twilio-connector": "^0.3.2",
|
|
54
54
|
"@tiledesk/tiledesk-vxml-connector": "^0.1.91",
|
|
55
55
|
"@tiledesk/tiledesk-whatsapp-connector": "1.0.26",
|
package/routes/kb.js
CHANGED
|
@@ -276,6 +276,8 @@ router.post('/scrape/single', async (req, res) => {
|
|
|
276
276
|
|
|
277
277
|
winston.verbose("/scrape/single json: ", json);
|
|
278
278
|
|
|
279
|
+
json.id_project = project_id;
|
|
280
|
+
|
|
279
281
|
if (process.env.NODE_ENV === "test") {
|
|
280
282
|
res.status(200).send({ success: true, message: "Skip indexing in test environment", data: json })
|
|
281
283
|
}
|
|
@@ -362,6 +364,7 @@ router.post('/qa', async (req, res) => {
|
|
|
362
364
|
let id_project = req.projectid;
|
|
363
365
|
let publicKey = false;
|
|
364
366
|
let data = req.body;
|
|
367
|
+
data.id_project = id_project;
|
|
365
368
|
|
|
366
369
|
let namespace;
|
|
367
370
|
try {
|
|
@@ -601,10 +604,14 @@ router.post('/qa', async (req, res) => {
|
|
|
601
604
|
return;
|
|
602
605
|
}
|
|
603
606
|
|
|
607
|
+
let duration = Date.now();
|
|
608
|
+
|
|
604
609
|
aiService.askNamespace(data).then((resp) => {
|
|
605
610
|
winston.debug("qa resp: ", resp.data);
|
|
606
611
|
let answer = resp.data;
|
|
607
612
|
|
|
613
|
+
answer.duration = (Date.now() - duration) / 1000;
|
|
614
|
+
|
|
608
615
|
if (publicKey === true) {
|
|
609
616
|
let modelKey;
|
|
610
617
|
if (typeof data.model === 'string') {
|
package/routes/llm.js
CHANGED
package/routes/webhook.js
CHANGED
|
@@ -199,7 +199,7 @@ router.post('/kb/reindex', async (req, res) => {
|
|
|
199
199
|
json.engine = namespace.engine || (namespace.hybrid ? default_engine_hybrid : default_engine);
|
|
200
200
|
json.hybrid = namespace.hybrid;
|
|
201
201
|
|
|
202
|
-
let embedding = namespace.embedding || default_embedding;
|
|
202
|
+
let embedding = namespace.embedding || Object.assign({}, default_embedding);
|
|
203
203
|
embedding.api_key = process.env.EMBEDDING_API_KEY || process.env.GPTKEY;
|
|
204
204
|
json.embedding = embedding;
|
|
205
205
|
|
package/services/aiManager.js
CHANGED
|
@@ -94,7 +94,7 @@ class AiManager {
|
|
|
94
94
|
this.saveBulk(operations, kbs, namespace.id_project, namespace.id).then( async (result) => {
|
|
95
95
|
let hybrid = namespace.hybrid;
|
|
96
96
|
let engine = namespace.engine || default_engine;
|
|
97
|
-
let embedding = namespace.embedding || default_embedding;
|
|
97
|
+
let embedding = namespace.embedding || Object.assign({}, default_embedding);
|
|
98
98
|
embedding.api_key = process.env.EMBEDDING_API_KEY || process.env.GPTKEY;
|
|
99
99
|
|
|
100
100
|
let situated_context;
|