halbot 1991.2.21 → 1991.2.23
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/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "halbot",
|
|
3
3
|
"description": "Just another `ChatGPT` / `Gemini` / `Mistral (by ollama)` Telegram bob, which is simple design, easy to use, extendable and fun.",
|
|
4
|
-
"version": "1991.2.
|
|
4
|
+
"version": "1991.2.23",
|
|
5
5
|
"private": false,
|
|
6
6
|
"homepage": "https://github.com/Leask/halbot",
|
|
7
7
|
"type": "module",
|
|
@@ -51,7 +51,7 @@
|
|
|
51
51
|
"pgvector": "^0.2.0",
|
|
52
52
|
"telegraf": "^4.16.3",
|
|
53
53
|
"tesseract.js": "^5.1.0",
|
|
54
|
-
"utilitas": "^1997.1.
|
|
54
|
+
"utilitas": "^1997.1.4",
|
|
55
55
|
"youtube-transcript": "^1.2.1"
|
|
56
56
|
}
|
|
57
57
|
}
|
|
@@ -1,19 +1,25 @@
|
|
|
1
1
|
import { alan, bot, uoid, utilitas } from 'utilitas';
|
|
2
2
|
|
|
3
|
-
const EMIJI_FINISH = '☑️';
|
|
3
|
+
const [EMIJI_FINISH, END, NEW, THREAD, CLR] = ['☑️', '❎', '✨', '🧵', '🆑'];
|
|
4
|
+
|
|
5
|
+
const [CREATED, SWITCHED] = [
|
|
6
|
+
`${NEW} Thread created: `, `${EMIJI_FINISH} Thread switched: `
|
|
7
|
+
];
|
|
4
8
|
|
|
5
9
|
// moved to help and configs
|
|
6
10
|
const keyboards = [[
|
|
7
|
-
{ text:
|
|
8
|
-
{ text:
|
|
11
|
+
{ text: `/clear ${CLR}` },
|
|
12
|
+
{ text: `/end ${END}` },
|
|
13
|
+
{ text: `/list ${THREAD}` },
|
|
14
|
+
{ text: `/new ${NEW}` },
|
|
9
15
|
], [
|
|
10
|
-
{ text: '/
|
|
11
|
-
{ text: '/
|
|
12
|
-
{ text: '/
|
|
16
|
+
{ text: '/polish ❇️' },
|
|
17
|
+
{ text: '/translate 🇨🇳' },
|
|
18
|
+
{ text: '/translate 🇺🇸' },
|
|
13
19
|
], [
|
|
14
20
|
{ text: '/help 🛟' },
|
|
15
|
-
{ text: '/
|
|
16
|
-
{ text: '/
|
|
21
|
+
{ text: '/set --tts=🔇' },
|
|
22
|
+
{ text: '/set --tts=🔊' },
|
|
17
23
|
]];
|
|
18
24
|
|
|
19
25
|
const action = async (ctx, next) => {
|
|
@@ -24,10 +30,25 @@ const action = async (ctx, next) => {
|
|
|
24
30
|
const resetSessions = () => ctx.session.sessions = [];
|
|
25
31
|
const resetContext = context => ctx.session.context = context || {};
|
|
26
32
|
const now = Date.now();
|
|
27
|
-
ctx.session.sessionId || resetSession();
|
|
33
|
+
const preSessionId = ctx.session.sessionId || resetSession();
|
|
28
34
|
ctx.session.sessions || resetSessions();
|
|
29
35
|
ctx.session.context || resetContext();
|
|
36
|
+
ctx.carry || (ctx.carry = {});
|
|
37
|
+
ctx.carry.threadInfo || (ctx.carry.threadInfo = []);
|
|
30
38
|
// load functions
|
|
39
|
+
ctx.clear = async context => {
|
|
40
|
+
await alan.resetSession(
|
|
41
|
+
ctx.session.sessionId,
|
|
42
|
+
// { systemPrompt: context?.prompt } // @todo: switch to real system prompt
|
|
43
|
+
);
|
|
44
|
+
resetContext(context);
|
|
45
|
+
const id = findSession(ctx.session.sessionId);
|
|
46
|
+
ctx.cmd.ignored = true;
|
|
47
|
+
ctx.session.sessions?.[id] && (
|
|
48
|
+
ctx.session.sessions[id].context = ctx.session.context
|
|
49
|
+
);
|
|
50
|
+
ctx.hello(context?.prompt);
|
|
51
|
+
};
|
|
31
52
|
const switchSession = async () => {
|
|
32
53
|
let resp;
|
|
33
54
|
for (const session of ctx.session.sessions) {
|
|
@@ -36,6 +57,9 @@ const action = async (ctx, next) => {
|
|
|
36
57
|
ctx.session.context = session.context;
|
|
37
58
|
session.touchedAt = now;
|
|
38
59
|
resp = session;
|
|
60
|
+
preSessionId !== ctx.session.sessionId
|
|
61
|
+
&& ctx.carry.threadInfo.push(SWITCHED
|
|
62
|
+
+ getLabel(findSession(ctx.session.sessionId)));
|
|
39
63
|
break;
|
|
40
64
|
}
|
|
41
65
|
}
|
|
@@ -44,9 +68,12 @@ const action = async (ctx, next) => {
|
|
|
44
68
|
id: resetSession(),
|
|
45
69
|
createdAt: now, touchedAt: now, context: {},
|
|
46
70
|
});
|
|
71
|
+
ctx.carry.threadInfo.push(CREATED
|
|
72
|
+
+ getLabel(findSession(ctx.session.sessionId)));
|
|
47
73
|
await ctx.clear();
|
|
48
74
|
}
|
|
49
|
-
ctx.carry =
|
|
75
|
+
ctx.carry.sessionId = ctx.session.sessionId;
|
|
76
|
+
ctx.carry.threadInfo.length && (ctx.carry.keyboards = keyboards);
|
|
50
77
|
return resp;
|
|
51
78
|
};
|
|
52
79
|
const defauleTitle = i => (ctx.session.sessions[i]?.context?.cmd
|
|
@@ -60,26 +87,13 @@ const action = async (ctx, next) => {
|
|
|
60
87
|
}
|
|
61
88
|
}
|
|
62
89
|
};
|
|
63
|
-
ctx.clear = async context => {
|
|
64
|
-
await alan.resetSession(
|
|
65
|
-
ctx.session.sessionId,
|
|
66
|
-
// { systemPrompt: context?.prompt } // @todo: switch to real system prompt
|
|
67
|
-
);
|
|
68
|
-
resetContext(context);
|
|
69
|
-
const id = findSession(ctx.session.sessionId);
|
|
70
|
-
ctx.cmd.ignored = true;
|
|
71
|
-
ctx.session.sessions?.[id] && (
|
|
72
|
-
ctx.session.sessions[id].context = ctx.session.context
|
|
73
|
-
);
|
|
74
|
-
ctx.hello(context?.prompt);
|
|
75
|
-
};
|
|
76
90
|
const ok = async (message, options) => await ctx.ok(message, {
|
|
77
|
-
...options || {},
|
|
91
|
+
...options || {},
|
|
92
|
+
...options?.buttons ? {} : (options?.keyboards || { keyboards }),
|
|
78
93
|
});
|
|
79
|
-
// handle commands
|
|
80
94
|
const sendList = async (names, lastMsgId) => {
|
|
81
95
|
lastMsgId = lastMsgId || ctx.update?.callback_query?.message?.message_id;
|
|
82
|
-
const message =
|
|
96
|
+
const message = `{THREAD} Thread${ctx.session.sessions.length > 0 ? 's' : ''}:`;
|
|
83
97
|
const buttons = ctx.session.sessions.map((x, i) => {
|
|
84
98
|
names?.[x.id]
|
|
85
99
|
&& (ctx.session.sessions[i].label = names[x.id])
|
|
@@ -92,14 +106,26 @@ const action = async (ctx, next) => {
|
|
|
92
106
|
});
|
|
93
107
|
return await ok(message, { lastMessageId: lastMsgId, buttons });
|
|
94
108
|
};
|
|
95
|
-
const switched = async preTitle => await ok(
|
|
96
|
-
`${
|
|
97
|
-
|
|
98
|
-
|
|
109
|
+
const switched = async (preTitle, newThread) => await ok(`${preTitle
|
|
110
|
+
? `${END} Thread ended: \`${preTitle}\`\n\n` : ''}`
|
|
111
|
+
+ (newThread ? CREATED : SWITCHED)
|
|
112
|
+
+ getLabel(findSession(ctx.session.sessionId)), { pageBreak: true });
|
|
113
|
+
// handle commands
|
|
99
114
|
switch (ctx.cmd?.cmd) {
|
|
100
|
-
case '
|
|
101
|
-
|
|
102
|
-
case '
|
|
115
|
+
case 'clearkb':
|
|
116
|
+
return await ok(EMIJI_FINISH, { keyboards: [] });
|
|
117
|
+
case 'clear':
|
|
118
|
+
ctx.carry.threadInfo.push(`${CLR} Thread cleared: `
|
|
119
|
+
+ getLabel(findSession(ctx.session.sessionId)));
|
|
120
|
+
await ctx.clear();
|
|
121
|
+
break;
|
|
122
|
+
case 'clearall':
|
|
123
|
+
ctx.carry.threadInfo.push(`🔄 All threads have been cleared.`);
|
|
124
|
+
resetSessions();
|
|
125
|
+
break;
|
|
126
|
+
case 'new':
|
|
127
|
+
resetSession();
|
|
128
|
+
break;
|
|
103
129
|
case 'list':
|
|
104
130
|
const resp = await sendList();
|
|
105
131
|
utilitas.ignoreErrFunc(async () => {
|
|
@@ -119,16 +145,18 @@ const action = async (ctx, next) => {
|
|
|
119
145
|
let preTitle = '';
|
|
120
146
|
ctx.session.sessions?.[id] && (preTitle = getLabel(id))
|
|
121
147
|
&& (ctx.session.sessions.splice(id, 1));
|
|
148
|
+
const newThread = ctx.session.sessions.length === 0
|
|
122
149
|
const sorted = ctx.session.sessions.slice().sort(
|
|
123
150
|
(x, y) => y.touchedAt - x.touchedAt
|
|
124
151
|
);
|
|
125
152
|
ctx.session.sessionId = sorted?.[0]?.id;
|
|
126
153
|
await switchSession();
|
|
127
|
-
return await switched(preTitle);
|
|
154
|
+
return await switched(preTitle, newThread);
|
|
128
155
|
case 'switch':
|
|
129
156
|
ctx.session.sessionId = utilitas.trim(ctx.cmd.args);
|
|
130
157
|
await switchSession();
|
|
131
|
-
|
|
158
|
+
await sendList();
|
|
159
|
+
return await switched();
|
|
132
160
|
case 'factory':
|
|
133
161
|
case 'reset':
|
|
134
162
|
await alan.resetSession(ctx.session.sessionId);
|
|
@@ -139,17 +167,17 @@ const action = async (ctx, next) => {
|
|
|
139
167
|
};
|
|
140
168
|
|
|
141
169
|
export const { name, run, priority, func, help, cmds, cmdx } = {
|
|
142
|
-
name: '
|
|
170
|
+
name: 'Thread',
|
|
143
171
|
run: true,
|
|
144
172
|
priority: -8845,
|
|
145
173
|
func: action,
|
|
146
|
-
help: '',
|
|
174
|
+
help: 'Thread management.',
|
|
147
175
|
cmdx: {
|
|
148
|
-
new: '
|
|
149
|
-
end: '
|
|
150
|
-
switch: 'Switch to a
|
|
151
|
-
clear: 'Clear current
|
|
152
|
-
clearall: 'Clear all
|
|
153
|
-
list: 'List all
|
|
176
|
+
new: 'Create a new thread.',
|
|
177
|
+
end: 'End current thread.',
|
|
178
|
+
switch: 'Switch to a thread. Usage: /switch `THREAD_ID`.',
|
|
179
|
+
clear: 'Clear current thread.',
|
|
180
|
+
clearall: 'Clear all threads.',
|
|
181
|
+
list: 'List all threads.',
|
|
154
182
|
},
|
|
155
183
|
};
|
package/skills/70_chat.mjs
CHANGED
|
@@ -13,7 +13,9 @@ const action = async (ctx, next) => {
|
|
|
13
13
|
let [lastMsg, lastSent] = [null, 0];
|
|
14
14
|
const packMsg = options => {
|
|
15
15
|
const said = !options?.tts && ctx.result ? ctx.result : '';
|
|
16
|
-
const packed = [
|
|
16
|
+
const packed = [
|
|
17
|
+
...ctx.carry?.threadInfo, ...said ? [joinL2([YOU, said])] : [],
|
|
18
|
+
];
|
|
17
19
|
const source = options?.tts ? tts : msgs;
|
|
18
20
|
const pure = [];
|
|
19
21
|
ctx.selectedAi.map(n => {
|
|
@@ -36,9 +38,12 @@ const action = async (ctx, next) => {
|
|
|
36
38
|
options?.final && cmd && (extra.buttons = [{
|
|
37
39
|
label: `❎ End context: \`${cmd}\``, text: '/clear',
|
|
38
40
|
}]);
|
|
39
|
-
return await ctx.ok(curMsg, {
|
|
41
|
+
return await ctx.ok(curMsg, {
|
|
42
|
+
...ctx.carry.keyboards ? { keyboards: ctx.carry.keyboards } : {},
|
|
43
|
+
md: true, ...extra, ...options || {},
|
|
44
|
+
});
|
|
40
45
|
};
|
|
41
|
-
await ok(onProgress);
|
|
46
|
+
ctx.carry.threadInfo.length || await ok(onProgress);
|
|
42
47
|
for (let n of ctx.selectedAi) {
|
|
43
48
|
pms.push((async () => {
|
|
44
49
|
try {
|
|
@@ -46,7 +51,7 @@ const action = async (ctx, next) => {
|
|
|
46
51
|
engine: ctx._.ai[n].engine, ...ctx.carry,
|
|
47
52
|
stream: async r => {
|
|
48
53
|
msgs[n] = r[0].text;
|
|
49
|
-
await ok(onProgress);
|
|
54
|
+
ctx.carry.threadInfo.length || await ok(onProgress);
|
|
50
55
|
},
|
|
51
56
|
});
|
|
52
57
|
msgs[n] = ctx.session.config?.render === true
|