node-red-contrib-ai-agent 0.5.9 → 0.5.10

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.
@@ -69,10 +69,11 @@ class SimpleFileStorage {
69
69
  this.filePath = options.filePath;
70
70
  this.backupEnabled = options.backupEnabled !== false;
71
71
  this.backupCount = options.backupCount || 3;
72
+ this._writeQueue = Promise.resolve();
72
73
  }
73
74
 
74
75
  async save(data) {
75
- try {
76
+ this._writeQueue = this._writeQueue.then(async () => {
76
77
  const dir = path.dirname(this.filePath);
77
78
  if (!fs.existsSync(dir)) {
78
79
  fs.mkdirSync(dir, { recursive: true });
@@ -81,15 +82,27 @@ class SimpleFileStorage {
81
82
  data.metadata = data.metadata || {};
82
83
  data.metadata.lastUpdated = new Date().toISOString();
83
84
 
84
- await fs.promises.writeFile(
85
- this.filePath,
86
- JSON.stringify(data, null, 2)
87
- );
85
+ const tmpPath = `${this.filePath}.tmp`;
86
+ await fs.promises.writeFile(tmpPath, JSON.stringify(data, null, 2));
87
+
88
+ try {
89
+ await fs.promises.rename(tmpPath, this.filePath);
90
+ } catch (err) {
91
+ try {
92
+ await fs.promises.unlink(this.filePath);
93
+ } catch (e) {
94
+ // ignore
95
+ }
96
+ await fs.promises.rename(tmpPath, this.filePath);
97
+ }
88
98
 
89
99
  if (this.backupEnabled) {
90
100
  await this.createBackup();
91
101
  }
102
+ });
92
103
 
104
+ try {
105
+ await this._writeQueue;
93
106
  return true;
94
107
  } catch (error) {
95
108
  return false;
@@ -427,7 +440,7 @@ module.exports = function (RED) {
427
440
  // Use send and done for Node-RED 1.0+ compatibility
428
441
  send = send || function () { node.send.apply(node, arguments) };
429
442
 
430
- try {
443
+ node._inputQueue = (node._inputQueue || Promise.resolve()).then(async () => {
431
444
  msg.aimemory = msg.aimemory || {};
432
445
 
433
446
  if (msg.command) {
@@ -456,14 +469,16 @@ module.exports = function (RED) {
456
469
  shape: "dot",
457
470
  text: `${node.memoryManager.conversations.length} convs, ${node.memoryManager.longTerm.vectors.length} long-term`
458
471
  });
459
-
460
- if (done) done();
461
- } catch (err) {
462
-
463
- node.error("Error in memory node: " + err.message, msg);
464
- node.status({ fill: "red", shape: "ring", text: "Error" });
465
- if (done) done(err);
466
- }
472
+ }).then(
473
+ () => {
474
+ if (done) done();
475
+ },
476
+ (err) => {
477
+ node.error("Error in memory node: " + err.message, msg);
478
+ node.status({ fill: "red", shape: "ring", text: "Error" });
479
+ if (done) done(err);
480
+ }
481
+ );
467
482
  });
468
483
 
469
484
  async function processCommand(node, msg) {
@@ -157,7 +157,9 @@ Return a JSON object with a "tasks" array. Each task should have:
157
157
  }`;
158
158
 
159
159
  try {
160
+ node.warn("Prompt: " + prompt);
160
161
  const response = await callAI(msg.aiagent, prompt, "You are an AI Orchestrator that creates non-linear plans with dependencies.");
162
+ node.warn("Response: " + response);
161
163
  const planData = JSON.parse(extractJson(response));
162
164
  msg.orchestration.plan = planData;
163
165
  msg.orchestration.status = 'executing';
@@ -218,7 +218,9 @@ module.exports = function (RED) {
218
218
 
219
219
  const inputText = typeof taskInput === 'string' ? taskInput : JSON.stringify(taskInput);
220
220
  const { messages, userMessage } = preparePrompt(node, msg, inputText);
221
+ node.warn("Messages: " + JSON.stringify(messages));
221
222
  const response = await callAI(node, msg.aiagent, messages);
223
+ node.warn("Response: " + response);
222
224
 
223
225
  if (msg.aimemory && userMessage) {
224
226
  updateContext(msg, userMessage, response);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "node-red-contrib-ai-agent",
3
- "version": "0.5.9",
3
+ "version": "0.5.10",
4
4
  "description": "AI Agent for Node-RED",
5
5
  "repository": {
6
6
  "type": "git",