@fideliosai/server 0.0.11 → 0.0.12

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.
Files changed (88) hide show
  1. package/dist/index.d.ts.map +1 -1
  2. package/dist/index.js +36 -12
  3. package/dist/index.js.map +1 -1
  4. package/dist/routes/agents.d.ts.map +1 -1
  5. package/dist/routes/agents.js +1 -0
  6. package/dist/routes/agents.js.map +1 -1
  7. package/dist/services/heartbeat.d.ts +5 -0
  8. package/dist/services/heartbeat.d.ts.map +1 -1
  9. package/dist/services/heartbeat.js +83 -18
  10. package/dist/services/heartbeat.js.map +1 -1
  11. package/dist/services/routines.d.ts.map +1 -1
  12. package/dist/services/routines.js +15 -1
  13. package/dist/services/routines.js.map +1 -1
  14. package/package.json +13 -13
  15. package/ui-dist/assets/{_basePickBy-aCZUIqgz.js → _basePickBy-Bz1lMRr1.js} +1 -1
  16. package/ui-dist/assets/{_baseUniq-BLy-h0im.js → _baseUniq-Cz0DIzBh.js} +1 -1
  17. package/ui-dist/assets/{arc-DORcpZ2v.js → arc-B03KhCd2.js} +1 -1
  18. package/ui-dist/assets/{architectureDiagram-VXUJARFQ-CrC43GAv.js → architectureDiagram-VXUJARFQ-Bd-fd33T.js} +1 -1
  19. package/ui-dist/assets/{blockDiagram-VD42YOAC-xTdotV4a.js → blockDiagram-VD42YOAC-CXaFl4cP.js} +1 -1
  20. package/ui-dist/assets/{c4Diagram-YG6GDRKO-Dz1ltwa_.js → c4Diagram-YG6GDRKO-DaDthSB7.js} +1 -1
  21. package/ui-dist/assets/channel-DyOjp3LQ.js +1 -0
  22. package/ui-dist/assets/{chunk-4BX2VUAB-0yJ60N67.js → chunk-4BX2VUAB-CJnPL87r.js} +1 -1
  23. package/ui-dist/assets/{chunk-55IACEB6-CaykP-lI.js → chunk-55IACEB6-CJNMJX2n.js} +1 -1
  24. package/ui-dist/assets/{chunk-B4BG7PRW-KHME69me.js → chunk-B4BG7PRW-DIkK9Mlj.js} +1 -1
  25. package/ui-dist/assets/{chunk-DI55MBZ5-B0usDtdN.js → chunk-DI55MBZ5-DSmF2iXg.js} +1 -1
  26. package/ui-dist/assets/{chunk-FMBD7UC4-DzvV4HxO.js → chunk-FMBD7UC4-gfze-lvJ.js} +1 -1
  27. package/ui-dist/assets/{chunk-QN33PNHL-lQSWl0lp.js → chunk-QN33PNHL-Ddo3zVqT.js} +1 -1
  28. package/ui-dist/assets/{chunk-QZHKN3VN-CNSl5CP7.js → chunk-QZHKN3VN-BPSHvZyX.js} +1 -1
  29. package/ui-dist/assets/{chunk-TZMSLE5B-DGMwf-PG.js → chunk-TZMSLE5B-C7wuUAs7.js} +1 -1
  30. package/ui-dist/assets/classDiagram-2ON5EDUG-BtJMQosd.js +1 -0
  31. package/ui-dist/assets/classDiagram-v2-WZHVMYZB-BtJMQosd.js +1 -0
  32. package/ui-dist/assets/clone-CXFUP-5d.js +1 -0
  33. package/ui-dist/assets/{cose-bilkent-S5V4N54A-DHdl31U9.js → cose-bilkent-S5V4N54A-io2ht7Tg.js} +1 -1
  34. package/ui-dist/assets/{dagre-6UL2VRFP-qya_P88Y.js → dagre-6UL2VRFP-CFH5DFm7.js} +1 -1
  35. package/ui-dist/assets/{diagram-PSM6KHXK-r6VT3OaH.js → diagram-PSM6KHXK-CPQXpnTx.js} +1 -1
  36. package/ui-dist/assets/{diagram-QEK2KX5R-B_q3SrYe.js → diagram-QEK2KX5R-BbyOPiaB.js} +1 -1
  37. package/ui-dist/assets/{diagram-S2PKOQOG-fUd6aDqY.js → diagram-S2PKOQOG-D6BCeM_j.js} +1 -1
  38. package/ui-dist/assets/{erDiagram-Q2GNP2WA-C4GVHjeF.js → erDiagram-Q2GNP2WA-C69wMd1X.js} +1 -1
  39. package/ui-dist/assets/{flowDiagram-NV44I4VS-NJOvXcsO.js → flowDiagram-NV44I4VS-CKJK9Bqb.js} +1 -1
  40. package/ui-dist/assets/{ganttDiagram-JELNMOA3-CR6i8bw3.js → ganttDiagram-JELNMOA3-CPfA5Aye.js} +1 -1
  41. package/ui-dist/assets/{gitGraphDiagram-V2S2FVAM-KuUBqBCF.js → gitGraphDiagram-V2S2FVAM-DZaZg_GO.js} +1 -1
  42. package/ui-dist/assets/{graph-C2ndFxK0.js → graph-DhWILner.js} +1 -1
  43. package/ui-dist/assets/{index-C0zpXTd4.js → index-0wF5nWs7.js} +1 -1
  44. package/ui-dist/assets/{index-2E9SUYYV.js → index-BA22JOVS.js} +1 -1
  45. package/ui-dist/assets/{index-BCxeL4sC.js → index-BYLf-CL8.js} +1 -1
  46. package/ui-dist/assets/{index-BXJ3uZW7.js → index-BYNiNvTL.js} +1 -1
  47. package/ui-dist/assets/{index-BX559d7s.js → index-BpI5gD12.js} +1 -1
  48. package/ui-dist/assets/{index-iwCaKqyH.js → index-Bw34OrlI.js} +1 -1
  49. package/ui-dist/assets/{index-BpmpzDnz.js → index-C0eJUuhF.js} +1 -1
  50. package/ui-dist/assets/{index-DG8bzLmY.js → index-CDX_vTiv.js} +1 -1
  51. package/ui-dist/assets/{index-B7IYeGcu.js → index-CE0NQXcf.js} +1 -1
  52. package/ui-dist/assets/{index-8u8n9Pq4.js → index-CHuh0SWm.js} +1 -1
  53. package/ui-dist/assets/{index-dlwMuMNB.js → index-CPbbQZoC.js} +1 -1
  54. package/ui-dist/assets/{index-COKsPUYc.js → index-ChbF-4_t.js} +1 -1
  55. package/ui-dist/assets/{index-B0NynVYx.js → index-CoA6TNOP.js} +1 -1
  56. package/ui-dist/assets/{index-DRYxIzsk.js → index-D2T0iIrx.js} +1 -1
  57. package/ui-dist/assets/{index-BgKIv3L-.js → index-DErU01-2.js} +1 -1
  58. package/ui-dist/assets/{index-CbtLpvDh.js → index-DM_ccx3O.js} +1 -1
  59. package/ui-dist/assets/{index-vwVAOsXL.js → index-DOD72BH5.js} +1 -1
  60. package/ui-dist/assets/{index-Chz5Zuq6.js → index-DnxtFtFx.js} +1 -1
  61. package/ui-dist/assets/{index-BY05NZdH.js → index-IWMCpuKI.js} +1 -1
  62. package/ui-dist/assets/{index-cDG_QEmf.js → index-T3Zr4GMI.js} +1 -1
  63. package/ui-dist/assets/{index-CiAa-OcP.js → index-lCZF_3wT.js} +1 -1
  64. package/ui-dist/assets/{index-C_pLB968.js → index-samEGEZm.js} +1 -1
  65. package/ui-dist/assets/{index-CZ5YNJWm.js → index-ypuEcx6t.js} +107 -107
  66. package/ui-dist/assets/{infoDiagram-HS3SLOUP-DEFCtERi.js → infoDiagram-HS3SLOUP-LnZP2Iev.js} +1 -1
  67. package/ui-dist/assets/{journeyDiagram-XKPGCS4Q-R88Ohnwu.js → journeyDiagram-XKPGCS4Q-TeWCkroV.js} +1 -1
  68. package/ui-dist/assets/{kanban-definition-3W4ZIXB7-DNRXkJwN.js → kanban-definition-3W4ZIXB7-BnVAyHyB.js} +1 -1
  69. package/ui-dist/assets/{layout-DoH9I_tz.js → layout-B6TLG_zF.js} +1 -1
  70. package/ui-dist/assets/{linear-D4V-ctT5.js → linear-Dyb-7GvO.js} +1 -1
  71. package/ui-dist/assets/{mermaid.core-D9TAWwGC.js → mermaid.core-CpCDuAY2.js} +4 -4
  72. package/ui-dist/assets/{mindmap-definition-VGOIOE7T-B3z_zJUb.js → mindmap-definition-VGOIOE7T-YN4fDnoi.js} +1 -1
  73. package/ui-dist/assets/{pieDiagram-ADFJNKIX-QMtcHwNj.js → pieDiagram-ADFJNKIX-Jt-577aV.js} +1 -1
  74. package/ui-dist/assets/{quadrantDiagram-AYHSOK5B-CLELWbCb.js → quadrantDiagram-AYHSOK5B-CGgFva_d.js} +1 -1
  75. package/ui-dist/assets/{requirementDiagram-UZGBJVZJ-CPKqi-aD.js → requirementDiagram-UZGBJVZJ-DdBYxuTR.js} +1 -1
  76. package/ui-dist/assets/{sankeyDiagram-TZEHDZUN-Dd8dy8DO.js → sankeyDiagram-TZEHDZUN-CykYs1PD.js} +1 -1
  77. package/ui-dist/assets/{sequenceDiagram-WL72ISMW-DgwQ1CPY.js → sequenceDiagram-WL72ISMW-CDK1H21a.js} +1 -1
  78. package/ui-dist/assets/{stateDiagram-FKZM4ZOC-DeI2cgrU.js → stateDiagram-FKZM4ZOC-CUqmB-ze.js} +1 -1
  79. package/ui-dist/assets/stateDiagram-v2-4FDKWEC3-ST-nIdhL.js +1 -0
  80. package/ui-dist/assets/{timeline-definition-IT6M3QCI-CMPp7ApP.js → timeline-definition-IT6M3QCI-CM3R1w9U.js} +1 -1
  81. package/ui-dist/assets/{treemap-GDKQZRPO-C1Fv7Xlx.js → treemap-GDKQZRPO-Ddo-4aIO.js} +1 -1
  82. package/ui-dist/assets/{xychartDiagram-PRI3JC2R-Dr7tKPcx.js → xychartDiagram-PRI3JC2R-BBxPoZv5.js} +1 -1
  83. package/ui-dist/index.html +1 -1
  84. package/ui-dist/assets/channel-N7GASpcu.js +0 -1
  85. package/ui-dist/assets/classDiagram-2ON5EDUG-875mZmmv.js +0 -1
  86. package/ui-dist/assets/classDiagram-v2-WZHVMYZB-875mZmmv.js +0 -1
  87. package/ui-dist/assets/clone-CKZ8Y0-n.js +0 -1
  88. package/ui-dist/assets/stateDiagram-v2-4FDKWEC3-DGSG2WeT.js +0 -1
@@ -1364,25 +1364,21 @@ export function heartbeatService(db) {
1364
1364
  }
1365
1365
  const tracksLocalChild = isTrackedLocalChildProcessAdapter(adapterType);
1366
1366
  if (tracksLocalChild && run.processPid && isProcessAlive(run.processPid)) {
1367
- if (run.errorCode !== DETACHED_PROCESS_ERROR_CODE) {
1368
- const detachedMessage = `Lost in-memory process handle, but child pid ${run.processPid} is still alive`;
1369
- const detachedRun = await setRunStatus(run.id, "running", {
1370
- error: detachedMessage,
1371
- errorCode: DETACHED_PROCESS_ERROR_CODE,
1372
- });
1373
- if (detachedRun) {
1374
- await appendRunEvent(detachedRun, await nextRunEventSeq(detachedRun.id), {
1375
- eventType: "lifecycle",
1376
- stream: "system",
1377
- level: "warn",
1378
- message: detachedMessage,
1379
- payload: {
1380
- processPid: run.processPid,
1381
- },
1382
- });
1383
- }
1367
+ // Kill the orphaned process instead of letting it hang forever
1368
+ const detachedMessage = `Lost in-memory process handle, but child pid ${run.processPid} is still alive — killing and marking failed`;
1369
+ logger.info({ runId: run.id, pid: run.processPid }, detachedMessage);
1370
+ try {
1371
+ process.kill(run.processPid, "SIGTERM");
1384
1372
  }
1385
- continue;
1373
+ catch { }
1374
+ setTimeout(() => {
1375
+ try {
1376
+ if (isProcessAlive(run.processPid))
1377
+ process.kill(run.processPid, "SIGKILL");
1378
+ }
1379
+ catch { }
1380
+ }, 5000);
1381
+ // Fall through to the same fail+retry logic below (don't continue)
1386
1382
  }
1387
1383
  const shouldRetry = tracksLocalChild && !!run.processPid && (run.processLossRetryCount ?? 0) < 1;
1388
1384
  const baseMessage = run.processPid
@@ -2937,6 +2933,21 @@ export function heartbeatService(db) {
2937
2933
  }
2938
2934
  }, graceMs);
2939
2935
  }
2936
+ else if (run.processPid && isProcessAlive(run.processPid)) {
2937
+ // Fallback: kill by PID when in-memory handle is lost (e.g. after server restart)
2938
+ logger.info({ runId, pid: run.processPid }, "Killing detached process by PID (no in-memory handle)");
2939
+ try {
2940
+ process.kill(run.processPid, "SIGTERM");
2941
+ }
2942
+ catch { }
2943
+ setTimeout(() => {
2944
+ try {
2945
+ if (isProcessAlive(run.processPid))
2946
+ process.kill(run.processPid, "SIGKILL");
2947
+ }
2948
+ catch { }
2949
+ }, 5000);
2950
+ }
2940
2951
  const cancelled = await setRunStatus(run.id, "cancelled", {
2941
2952
  finishedAt: new Date(),
2942
2953
  error: reason,
@@ -3159,6 +3170,60 @@ export function heartbeatService(db) {
3159
3170
  .limit(1);
3160
3171
  return run ?? null;
3161
3172
  },
3173
+ /**
3174
+ * On server startup, kill any orphaned processes from a previous server lifetime
3175
+ * and mark their runs as failed. This prevents "process_detached" hangs.
3176
+ */
3177
+ reconcileOrphanedRunsOnStartup: async () => {
3178
+ const staleRuns = await db
3179
+ .select({
3180
+ id: heartbeatRuns.id,
3181
+ agentId: heartbeatRuns.agentId,
3182
+ processPid: heartbeatRuns.processPid,
3183
+ wakeupRequestId: heartbeatRuns.wakeupRequestId,
3184
+ processLossRetryCount: heartbeatRuns.processLossRetryCount,
3185
+ })
3186
+ .from(heartbeatRuns)
3187
+ .innerJoin(agents, eq(heartbeatRuns.agentId, agents.id))
3188
+ .where(eq(heartbeatRuns.status, "running"));
3189
+ if (staleRuns.length === 0)
3190
+ return;
3191
+ const now = new Date();
3192
+ logger.info({ count: staleRuns.length }, "Reconciling stale running heartbeat runs from previous server lifetime");
3193
+ for (const run of staleRuns) {
3194
+ // Kill orphaned process if still alive
3195
+ if (run.processPid && isProcessAlive(run.processPid)) {
3196
+ logger.info({ runId: run.id, pid: run.processPid }, "Killing orphaned process from previous server lifetime");
3197
+ try {
3198
+ process.kill(run.processPid, "SIGTERM");
3199
+ }
3200
+ catch { }
3201
+ // SIGKILL will follow from reapOrphanedRuns if needed
3202
+ }
3203
+ const message = run.processPid
3204
+ ? `Orphaned run from previous server lifetime — pid ${run.processPid} killed`
3205
+ : "Stale running run from previous server lifetime";
3206
+ await setRunStatus(run.id, "failed", {
3207
+ error: message,
3208
+ errorCode: "process_lost",
3209
+ finishedAt: now,
3210
+ });
3211
+ await setWakeupStatus(run.wakeupRequestId, "failed", {
3212
+ finishedAt: now,
3213
+ error: message,
3214
+ });
3215
+ // Queue retry if under limit
3216
+ if ((run.processLossRetryCount ?? 0) < 1) {
3217
+ const agent = await getAgent(run.agentId);
3218
+ const fullRun = await getRun(run.id);
3219
+ if (agent && fullRun) {
3220
+ await enqueueProcessLossRetry(fullRun, agent, now);
3221
+ }
3222
+ }
3223
+ await finalizeAgentStatus(run.agentId, "failed");
3224
+ }
3225
+ logger.info({ reconciled: staleRuns.length }, "Startup reconciliation complete");
3226
+ },
3162
3227
  };
3163
3228
  }
3164
3229
  //# sourceMappingURL=heartbeat.js.map