@j-o-r/hello-dave 0.0.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/LICENSE +73 -0
- package/README.md +207 -0
- package/bin/hdAsk.js +103 -0
- package/bin/hdClear.js +13 -0
- package/bin/hdCode.js +110 -0
- package/bin/hdConnect.js +230 -0
- package/bin/hdInspect.js +28 -0
- package/bin/hdNpm.js +114 -0
- package/bin/hdPrompt.js +108 -0
- package/examples/claude-test.js +89 -0
- package/examples/claude.js +143 -0
- package/examples/gpt.js +127 -0
- package/examples/gpt_code.js +125 -0
- package/examples/gpt_note_keeping.js +117 -0
- package/examples/grok.js +119 -0
- package/examples/grok_code.js +114 -0
- package/examples/grok_note_keeping.js +111 -0
- package/lib/API/anthropic.com/text.js +402 -0
- package/lib/API/brave.com/search.js +239 -0
- package/lib/API/openai.com/README.md +1 -0
- package/lib/API/openai.com/reponses/MESSAGES.md +69 -0
- package/lib/API/openai.com/reponses/text.js +416 -0
- package/lib/API/x.ai/text.js +415 -0
- package/lib/AgentClient.js +197 -0
- package/lib/AgentManager.js +144 -0
- package/lib/AgentServer.js +336 -0
- package/lib/Cli.js +256 -0
- package/lib/Prompt.js +728 -0
- package/lib/Session.js +231 -0
- package/lib/ToolSet.js +186 -0
- package/lib/fafs.js +93 -0
- package/lib/genericToolset.js +170 -0
- package/lib/index.js +34 -0
- package/lib/promptHelpers.js +132 -0
- package/lib/testToolset.js +42 -0
- package/module.md +189 -0
- package/package.json +49 -0
- package/types/API/anthropic.com/text.d.ts +207 -0
- package/types/API/brave.com/search.d.ts +156 -0
- package/types/API/openai.com/reponses/text.d.ts +225 -0
- package/types/API/x.ai/text.d.ts +286 -0
- package/types/AgentClient.d.ts +70 -0
- package/types/AgentManager.d.ts +112 -0
- package/types/AgentServer.d.ts +38 -0
- package/types/Cli.d.ts +52 -0
- package/types/Prompt.d.ts +298 -0
- package/types/Session.d.ts +31 -0
- package/types/ToolSet.d.ts +95 -0
- package/types/fafs.d.ts +47 -0
- package/types/genericToolset.d.ts +3 -0
- package/types/index.d.ts +23 -0
- package/types/promptHelpers.d.ts +1 -0
- package/types/testToolset.d.ts +3 -0
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
import { Prompt, Cli, AgentClient, AgentServer, API, ToolSet, Session, env } from './index.js';
|
|
2
|
+
import toolsPool from './genericToolset.js'
|
|
3
|
+
/**
|
|
4
|
+
* @typedef {import('./API/x.ai/text.js').XOptions} XOptions
|
|
5
|
+
* @typedef {import('./API/openai.com/reponses/text.js').OAOptions} OAOptions
|
|
6
|
+
* @typedef {import('./API/anthropic.com/text.js').ANTHOptions} ANTHOptions
|
|
7
|
+
*/
|
|
8
|
+
/**
|
|
9
|
+
* @typedef {Object} Setup
|
|
10
|
+
* @property {string} prompt - Initial system prompt
|
|
11
|
+
* @property {OAOptions|XOptions|ANTHOptions} options - Model options
|
|
12
|
+
* @property {'gpt'|'grok'|'claude'} api - AI endpoint to use
|
|
13
|
+
* @property {number} [contextWindow] - The size in tokens for the context/session
|
|
14
|
+
* @property {'auto'|'required'|void} [toolsetMode] -
|
|
15
|
+
* @property {boolean} [debug] - verbose output
|
|
16
|
+
*/
|
|
17
|
+
/**
|
|
18
|
+
* @typedef {Object} Options
|
|
19
|
+
* @property {string} name - Agent name
|
|
20
|
+
* @property {string} [cachePath] - path to session/record storage
|
|
21
|
+
*/
|
|
22
|
+
class AgentManager {
|
|
23
|
+
/** @type {Prompt} */
|
|
24
|
+
#prompt;
|
|
25
|
+
/** @type {Session} */
|
|
26
|
+
#sessionStorage;
|
|
27
|
+
#name = 'agent';
|
|
28
|
+
#cachePath = '.cache/hello-dave';
|
|
29
|
+
#debug = false;
|
|
30
|
+
/**
|
|
31
|
+
* @param {Options} options
|
|
32
|
+
*/
|
|
33
|
+
constructor(options) {
|
|
34
|
+
this.#name = options.name || this.#name;
|
|
35
|
+
this.#cachePath = options.cachePath || this.#cachePath;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* @param {Setup} setup
|
|
40
|
+
*/
|
|
41
|
+
setup(setup) {
|
|
42
|
+
const {
|
|
43
|
+
prompt,
|
|
44
|
+
api = 'gpt',
|
|
45
|
+
contextWindow = 300000,
|
|
46
|
+
options = null,
|
|
47
|
+
toolsetMode = null,
|
|
48
|
+
debug = false
|
|
49
|
+
} = setup;
|
|
50
|
+
let toolset;
|
|
51
|
+
if (toolsetMode) {
|
|
52
|
+
toolset = new ToolSet(toolsetMode);
|
|
53
|
+
}
|
|
54
|
+
if (debug) {
|
|
55
|
+
this.#debug = true;
|
|
56
|
+
}
|
|
57
|
+
this.#prompt = new Prompt(contextWindow);
|
|
58
|
+
this.#sessionStorage = new Session(this.#name, this.#prompt, this.#cachePath);
|
|
59
|
+
this.#prompt.add('system', prompt, true);
|
|
60
|
+
this.#prompt.setAdaptor(API.text[api], toolset, options);
|
|
61
|
+
return this; // For chaining
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
/**
|
|
65
|
+
* Start a CLI for local usage
|
|
66
|
+
* @param {string} description - introduction message for the CLI user
|
|
67
|
+
*/
|
|
68
|
+
startCli(description) {
|
|
69
|
+
if (!this.#prompt) throw new Error('Run setup first');
|
|
70
|
+
const cli = new Cli({ prompt: this.#prompt, session: this.#sessionStorage, description });
|
|
71
|
+
setTimeout(() => {
|
|
72
|
+
// This resolves issues with log output after the console has been started
|
|
73
|
+
cli.start();
|
|
74
|
+
}, 1000);
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
/**
|
|
78
|
+
* Attach a session to an AgentServer
|
|
79
|
+
* DO NOT ATTACH TO SELF, however, when in server mode
|
|
80
|
+
* An AgentServer can attach as client to another server
|
|
81
|
+
* @param {string} name - function_call name
|
|
82
|
+
* @param {string} description - function_call description
|
|
83
|
+
* @param {string} [url='ws://127.0.0.1:8000/ws'] - ws URL
|
|
84
|
+
*/
|
|
85
|
+
attach(name, description, url = 'ws://127.0.0.1:8000/ws') {
|
|
86
|
+
if (!this.#prompt) throw new Error('Run setup first');
|
|
87
|
+
return new AgentClient({ prompt: this.#prompt, name, description, url });
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Start the Agent in server mode.
|
|
92
|
+
* A server is always started on localhost
|
|
93
|
+
* Clients can attach now and are accesible as via function_calls (toolset)
|
|
94
|
+
* @param {string} name - function_call name
|
|
95
|
+
* @param {string} description - function_call description
|
|
96
|
+
* @param {number} [port=8000] - Start the dynamic toolset server on this port
|
|
97
|
+
*/
|
|
98
|
+
enableServer(name, description = '', port = 8000) {
|
|
99
|
+
if (!this.#prompt) throw new Error('Run setup first');
|
|
100
|
+
if (!this.#prompt.toolset) throw new Error('No toolset defined');
|
|
101
|
+
const server = new AgentServer({
|
|
102
|
+
port,
|
|
103
|
+
name,
|
|
104
|
+
description,
|
|
105
|
+
prompt: this.#prompt,
|
|
106
|
+
session: this.#sessionStorage,
|
|
107
|
+
debug: this.#debug
|
|
108
|
+
|
|
109
|
+
});
|
|
110
|
+
// trigger reset on all Agents
|
|
111
|
+
this.#prompt.on('reset', () => {
|
|
112
|
+
// Generate new context for all Agents
|
|
113
|
+
server.resetAll();
|
|
114
|
+
})
|
|
115
|
+
}
|
|
116
|
+
/**
|
|
117
|
+
* Direct call to the prompt
|
|
118
|
+
* @param {string} input
|
|
119
|
+
* @returns {Promise<string>}
|
|
120
|
+
*/
|
|
121
|
+
async directCall(input) {
|
|
122
|
+
const res = await this.#prompt.call(input);
|
|
123
|
+
return res;
|
|
124
|
+
}
|
|
125
|
+
/** @returns {Prompt} */
|
|
126
|
+
getPrompt() { return this.#prompt; }
|
|
127
|
+
/** @returns {ToolSet|void} */
|
|
128
|
+
getToolset() { return this.#prompt.toolset; }
|
|
129
|
+
/** @returns {Promise<import('./fafs.js').EnvironmentInfo>} */
|
|
130
|
+
async environment() {
|
|
131
|
+
return env();
|
|
132
|
+
}
|
|
133
|
+
/**
|
|
134
|
+
* @param {string} name - the toolname
|
|
135
|
+
*/
|
|
136
|
+
addGenericToolcall(name) {
|
|
137
|
+
if (!this.#prompt.toolset) throw new Error('No ToolSet defined')
|
|
138
|
+
let tool = toolsPool.get(name);
|
|
139
|
+
if (!tool) throw new Error('Tool not defined')
|
|
140
|
+
this.#prompt.toolset.add(name, tool.description, tool.parameters, tool.method);
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
export default AgentManager;
|
|
@@ -0,0 +1,336 @@
|
|
|
1
|
+
import { WebSocketServer, server } from '@j-o-r/apiserver';
|
|
2
|
+
|
|
3
|
+
const TIMEOUT = 30000;
|
|
4
|
+
const MAX_INTERVALS = 20; // 10 minutes (30 sec * 20)
|
|
5
|
+
|
|
6
|
+
let ws;
|
|
7
|
+
/**
|
|
8
|
+
@typedef {import('../node_modules/@j-o-r/apiserver/types/ClientWrapper.d.ts').ClientWrapper} Client
|
|
9
|
+
@typedef {import('./Prompt.js').default} Prompt
|
|
10
|
+
@typedef {import('./ToolSet.js').default} ToolSet
|
|
11
|
+
@typedef {import('./Session.js').default} Session
|
|
12
|
+
*/
|
|
13
|
+
/**
|
|
14
|
+
* @type {string|object} messageContent
|
|
15
|
+
*/
|
|
16
|
+
/**
|
|
17
|
+
* @type {Object} message
|
|
18
|
+
* @property {string} action
|
|
19
|
+
* @property {messageContent} content
|
|
20
|
+
*/
|
|
21
|
+
/**
|
|
22
|
+
* @typedef {(conn: import('@j-o-r/apiserver/types/WebSocketServer.js').WebSocketConnection) => Promise<boolean>} AuthFunction
|
|
23
|
+
*/
|
|
24
|
+
/**
|
|
25
|
+
* @typedef {Object} AgentServerOptions
|
|
26
|
+
* @property {string} name
|
|
27
|
+
* @property {string} description
|
|
28
|
+
* @property {Prompt} prompt
|
|
29
|
+
* @property {Session} session
|
|
30
|
+
* @property {AuthFunction} [auth]
|
|
31
|
+
* @property {number} [port] - default 8000
|
|
32
|
+
* @property {boolean} [debug = false]
|
|
33
|
+
*/
|
|
34
|
+
|
|
35
|
+
const ACTIONS = [
|
|
36
|
+
// Agent / Toolset function calls
|
|
37
|
+
'agent_introduction', // Describe your task, your purpose and usage. This is a reaction on a 'introduce' requests
|
|
38
|
+
'agent_error', // Message error
|
|
39
|
+
'agent_query', // doing a query
|
|
40
|
+
'agent_response', // Doing an response on a query
|
|
41
|
+
// Regular user interaction
|
|
42
|
+
'user_introduction', // Websocket client connection on open
|
|
43
|
+
'user_request', // A client user request
|
|
44
|
+
'server_response', // A reponse to a user request
|
|
45
|
+
'user_reset', // User requests a new session
|
|
46
|
+
'user_sessionlist', // Request a list of sessions
|
|
47
|
+
'user_loadsession', // Request to load a session
|
|
48
|
+
'user_info', // User request server info
|
|
49
|
+
];
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
// WS clients
|
|
55
|
+
const clients = new Map();
|
|
56
|
+
// Pending messages
|
|
57
|
+
const pendingResponses = new Map(); // key: `${conn_id}:${msg_id}`, value: {resolve, reject}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* Delete a client from the toolset
|
|
61
|
+
* @param {ToolSet|void} toolset
|
|
62
|
+
* @param {string} conn_id - Connection id
|
|
63
|
+
*/
|
|
64
|
+
const deleteClient = (toolset, conn_id) => {
|
|
65
|
+
if (!toolset) return;
|
|
66
|
+
const name = clients.get(conn_id);
|
|
67
|
+
if (name) {
|
|
68
|
+
clients.delete(conn_id);
|
|
69
|
+
if (toolset.has(name)) {
|
|
70
|
+
toolset.delete(name);
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* @param {ToolSet|void} toolset
|
|
76
|
+
* @param {string} conn_id - Connection id
|
|
77
|
+
* @param {string} name - logical name / task
|
|
78
|
+
* @param {string} description of the logical name
|
|
79
|
+
*/
|
|
80
|
+
const addClient = (toolset, conn_id, name, description) => {
|
|
81
|
+
if (!toolset) return;
|
|
82
|
+
toolset.add(
|
|
83
|
+
name,
|
|
84
|
+
description,
|
|
85
|
+
{
|
|
86
|
+
type: 'object',
|
|
87
|
+
properties: {
|
|
88
|
+
query: {
|
|
89
|
+
type: 'string',
|
|
90
|
+
description: `Command, question or query for this particulair expert well formed in natural language`
|
|
91
|
+
}
|
|
92
|
+
},
|
|
93
|
+
required: ['query']
|
|
94
|
+
},
|
|
95
|
+
// @ts-ignore
|
|
96
|
+
(params) => {
|
|
97
|
+
return new Promise((resolve, reject) => {
|
|
98
|
+
const msg_id = Date.now().toString();
|
|
99
|
+
const key = `${conn_id}:${msg_id}`;
|
|
100
|
+
clients.set(conn_id, name);
|
|
101
|
+
|
|
102
|
+
// Start timeout/interval and keep its handle so we can clear it on response
|
|
103
|
+
let intervals = 0;
|
|
104
|
+
const timer = setInterval(() => {
|
|
105
|
+
intervals++;
|
|
106
|
+
if (intervals >= MAX_INTERVALS) {
|
|
107
|
+
clearInterval(timer);
|
|
108
|
+
if (pendingResponses.has(key)) {
|
|
109
|
+
reject('Timeout after max intervals');
|
|
110
|
+
pendingResponses.delete(key);
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
}, TIMEOUT);
|
|
114
|
+
|
|
115
|
+
// Store handlers and timer so onMessage can resolve/reject and clear the timer
|
|
116
|
+
pendingResponses.set(key, { resolve, reject, timer });
|
|
117
|
+
|
|
118
|
+
ws.sendToConnection(conn_id, JSON.stringify({
|
|
119
|
+
action: 'agent_query',
|
|
120
|
+
id: msg_id,
|
|
121
|
+
content: params.query
|
|
122
|
+
}));
|
|
123
|
+
}).then(response => (response));
|
|
124
|
+
})
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
// Provide a toolset based on websocket calls
|
|
128
|
+
class AgentServer {
|
|
129
|
+
#debug = false;
|
|
130
|
+
#port = 8000;
|
|
131
|
+
#name = '';
|
|
132
|
+
#description = '';
|
|
133
|
+
/** @type {Prompt} */
|
|
134
|
+
#prompt
|
|
135
|
+
/** @type {Session} */
|
|
136
|
+
#session
|
|
137
|
+
/** @type {AuthFunction} */
|
|
138
|
+
#auth = async (conn) => {
|
|
139
|
+
return true;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* @param {AgentServerOptions} options
|
|
143
|
+
*/
|
|
144
|
+
constructor(options) {
|
|
145
|
+
if (options.port) {
|
|
146
|
+
if (options.port < 1024) {
|
|
147
|
+
throw new Error('Port must be higher then 1024');
|
|
148
|
+
}
|
|
149
|
+
this.#port = options.port;
|
|
150
|
+
}
|
|
151
|
+
if (options.auth) {
|
|
152
|
+
this.#auth = options.auth;
|
|
153
|
+
}
|
|
154
|
+
this.#name = options.name;
|
|
155
|
+
this.#description = options.description;
|
|
156
|
+
this.#session = options.session;
|
|
157
|
+
this.#prompt = options.prompt;
|
|
158
|
+
const events = Object.keys(this.#prompt.EVENTS);
|
|
159
|
+
events.forEach((evt) => {
|
|
160
|
+
this.#prompt.on(evt, (_msg) => {
|
|
161
|
+
console.log(evt);
|
|
162
|
+
});
|
|
163
|
+
});
|
|
164
|
+
this.#debug = options.debug;
|
|
165
|
+
// start
|
|
166
|
+
(async () => {
|
|
167
|
+
await this._start();
|
|
168
|
+
})();
|
|
169
|
+
}
|
|
170
|
+
/**
|
|
171
|
+
* @private
|
|
172
|
+
* Returns a Dynamic Toolset
|
|
173
|
+
* With registered WS clients as toolcalls
|
|
174
|
+
* A deamon start on local host 127.0.0.1, always
|
|
175
|
+
* @returns {Promise<void>}
|
|
176
|
+
*/
|
|
177
|
+
async _start() {
|
|
178
|
+
const name = this.#name;
|
|
179
|
+
const description = this.#description;
|
|
180
|
+
const port = this.#port;
|
|
181
|
+
const DEBUG = this.#debug;
|
|
182
|
+
const API = {
|
|
183
|
+
/**
|
|
184
|
+
* @param {Client} client
|
|
185
|
+
*/
|
|
186
|
+
index: async (client) => {
|
|
187
|
+
await client.serve(200, { name, description });
|
|
188
|
+
}
|
|
189
|
+
};
|
|
190
|
+
ws = new WebSocketServer({
|
|
191
|
+
verbose: this.#debug,
|
|
192
|
+
onMessage: async (conn, msg) => {
|
|
193
|
+
if (!msg.action || !ACTIONS.includes(msg.action)) {
|
|
194
|
+
console.log('Unkown action: ' + msg.action);
|
|
195
|
+
deleteClient(this.#prompt.toolset, conn.id)
|
|
196
|
+
ws.closeConnection(conn.id);
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
if (msg.action === 'agent_introduction') {
|
|
200
|
+
// Register Toolset Agent
|
|
201
|
+
// CLient is added as a Toolset function call
|
|
202
|
+
const name = msg.name;
|
|
203
|
+
const content = (typeof msg.content === 'string') ? msg.content : JSON.stringify(msg.content);
|
|
204
|
+
if (!content) {
|
|
205
|
+
deleteClient(this.#prompt.toolset, conn.id)
|
|
206
|
+
ws.closeConnection(conn.id);
|
|
207
|
+
return;
|
|
208
|
+
}
|
|
209
|
+
addClient(this.#prompt.toolset, conn.id, name, content);
|
|
210
|
+
return;
|
|
211
|
+
}
|
|
212
|
+
if (msg.action === 'agent_response') {
|
|
213
|
+
const key = `${conn.id}:${msg.id}`; // Assume client includes original 'id' in response
|
|
214
|
+
const pending = pendingResponses.get(key);
|
|
215
|
+
if (pending) {
|
|
216
|
+
try { clearInterval(pending.timer); } catch {}
|
|
217
|
+
pending.resolve(msg.content);
|
|
218
|
+
pendingResponses.delete(key);
|
|
219
|
+
}
|
|
220
|
+
return;
|
|
221
|
+
}
|
|
222
|
+
if (msg.action === 'agent_error') {
|
|
223
|
+
const key = `${conn.id}:${msg.id}`; // Assume client includes original 'id' in response
|
|
224
|
+
const pending = pendingResponses.get(key);
|
|
225
|
+
if (pending) {
|
|
226
|
+
try { clearInterval(pending.timer); } catch {}
|
|
227
|
+
pending.reject(msg.content);
|
|
228
|
+
pendingResponses.delete(key);
|
|
229
|
+
}
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
// -------- USER INTERACTION --------------------------------------------------------
|
|
233
|
+
// CLI / WS interaction to MAIN
|
|
234
|
+
if (msg.action === 'user_request') {
|
|
235
|
+
const action = `user_reponse`;
|
|
236
|
+
const id = msg.id;
|
|
237
|
+
if (!msg.content || msg.content.trim() === '') {
|
|
238
|
+
// Empty message, empty reponse
|
|
239
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
240
|
+
action: 'user_response',
|
|
241
|
+
id,
|
|
242
|
+
content: ''
|
|
243
|
+
}));
|
|
244
|
+
return;
|
|
245
|
+
}
|
|
246
|
+
// Bind to THIS prompt
|
|
247
|
+
console.log(`user_request:>>\n${msg.content}\n`);
|
|
248
|
+
const content = await this.#prompt.call(msg.content);
|
|
249
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
250
|
+
action: 'server_response',
|
|
251
|
+
id,
|
|
252
|
+
content
|
|
253
|
+
}));
|
|
254
|
+
console.log(`server_reponse:>>\n${content}\n`);
|
|
255
|
+
}
|
|
256
|
+
if (msg.action === 'user_reset') {
|
|
257
|
+
const id = msg.id;
|
|
258
|
+
this.#prompt.reset();
|
|
259
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
260
|
+
action: 'server_reset',
|
|
261
|
+
id,
|
|
262
|
+
content: 'ok'
|
|
263
|
+
}));
|
|
264
|
+
}
|
|
265
|
+
if (msg.action === 'user_sessionlist') {
|
|
266
|
+
const id = msg.id;
|
|
267
|
+
const sess = this.#session.sessionList().reverse();
|
|
268
|
+
sess.push('NONE');
|
|
269
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
270
|
+
action: 'server_sessionlist',
|
|
271
|
+
id,
|
|
272
|
+
content: sess
|
|
273
|
+
}));
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
if (msg.action === 'user_loadsession') {
|
|
277
|
+
const id = msg.id;
|
|
278
|
+
const selected = msg.content;
|
|
279
|
+
const messages = [];
|
|
280
|
+
const list = this.#session.set(selected);
|
|
281
|
+
list.forEach((msg) => {
|
|
282
|
+
if (!msg.sticky) {
|
|
283
|
+
if (['user', 'assistant', 'reasoning', 'log'].includes(msg.role)) {
|
|
284
|
+
if (msg.role === 'assistant' && msg.content[0].type === 'function_request') {
|
|
285
|
+
|
|
286
|
+
} else {
|
|
287
|
+
const content = this.#prompt.contentToString(msg.content);
|
|
288
|
+
messages.push({ role: msg.role, content });
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
});
|
|
293
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
294
|
+
action: 'server_sessionloaded',
|
|
295
|
+
id,
|
|
296
|
+
content: messages
|
|
297
|
+
}));
|
|
298
|
+
}
|
|
299
|
+
if (msg.action === 'user_info') {
|
|
300
|
+
const id = msg.id;
|
|
301
|
+
const sessionInfo = this.#session.info();
|
|
302
|
+
const promptInfo = this.#prompt.info();
|
|
303
|
+
const info = `\nSESSION\n${sessionInfo}\nPROMPT\n${promptInfo}\nSERVER\nName: ${this.#name}\nDescription: ${this.#description}`;
|
|
304
|
+
ws.sendToConnection(conn.id, JSON.stringify({
|
|
305
|
+
action: 'server_info',
|
|
306
|
+
id,
|
|
307
|
+
content: info
|
|
308
|
+
}));
|
|
309
|
+
}
|
|
310
|
+
},
|
|
311
|
+
onConnection: async (conn) => {
|
|
312
|
+
return this.#auth(conn);
|
|
313
|
+
},
|
|
314
|
+
onClose: async (conn, reason) => {
|
|
315
|
+
deleteClient(this.#prompt.toolset, conn.id);
|
|
316
|
+
|
|
317
|
+
},
|
|
318
|
+
onError: async (conn, error) => {
|
|
319
|
+
// console.error(error);
|
|
320
|
+
deleteClient(this.#prompt.toolset, conn.id);
|
|
321
|
+
ws.closeConnection(conn.id);
|
|
322
|
+
}
|
|
323
|
+
});
|
|
324
|
+
await server.create('v1', { port, host: '127.0.0.1', ws, strict: DEBUG, verbose: DEBUG }, API);
|
|
325
|
+
console.log(`ws running on port: ${port}`);
|
|
326
|
+
}
|
|
327
|
+
/**
|
|
328
|
+
* Send a reset messages to all clients
|
|
329
|
+
* reset will start a new session
|
|
330
|
+
*/
|
|
331
|
+
resetAll() {
|
|
332
|
+
ws.broadcast({ action: 'reset' });
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
export default AgentServer;
|