@alfe.ai/gateway 0.0.34 → 0.0.36

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 (2) hide show
  1. package/dist/health.js +72 -30
  2. package/package.json +2 -2
package/dist/health.js CHANGED
@@ -82,6 +82,7 @@ const ID_PREFIXES = {
82
82
  memory: "mem",
83
83
  knowledgeTriple: "kgt",
84
84
  accessCode: "acc",
85
+ pendingInject: "pij",
85
86
  run: "run",
86
87
  request: "req",
87
88
  connection: "conn",
@@ -515,23 +516,8 @@ var IntegrationsService = class {
515
516
  getMobileNumber(agentId) {
516
517
  return this.client.request(`/mobile/numbers?agentId=${encodeURIComponent(agentId)}`);
517
518
  }
518
- recallJoinMeeting(agentId, meetingUrl, botName) {
519
- if (this.voiceClient) return this.voiceClient.request("/api/join", {
520
- method: "POST",
521
- body: JSON.stringify({
522
- agentId,
523
- meetingUrl,
524
- botName
525
- })
526
- });
527
- return this.client.request("/integrations/recall/join", {
528
- method: "POST",
529
- body: JSON.stringify({
530
- agentId,
531
- meetingUrl,
532
- botName
533
- })
534
- });
519
+ disconnectGoogle(agentId) {
520
+ return this.client.request(`/google/agents/${encodeURIComponent(agentId)}/account`, { method: "DELETE" });
535
521
  }
536
522
  listSlackChannels(agentId) {
537
523
  return this.client.request(`/slack/agents/${encodeURIComponent(agentId)}/channels`);
@@ -3250,6 +3236,7 @@ enumValues({
3250
3236
  object({ gracePeriodDays: number().int().positive().optional() });
3251
3237
  enumValues({
3252
3238
  Free: "free",
3239
+ Personal: "personal",
3253
3240
  Tier1: "tier_1",
3254
3241
  Tier2: "tier_2"
3255
3242
  });
@@ -3321,7 +3308,8 @@ enumValues({
3321
3308
  AdminGift: "admin_gift",
3322
3309
  ReferralCredit: "referral_credit",
3323
3310
  PromoCredit: "promo_credit",
3324
- Refund: "refund"
3311
+ Refund: "refund",
3312
+ WelcomeCredit: "welcome_credit"
3325
3313
  });
3326
3314
  enumValues({
3327
3315
  Pending: "pending",
@@ -4009,6 +3997,33 @@ var ReconciliationEngine = class {
4009
3997
  });
4010
3998
  return;
4011
3999
  }
4000
+ if (!await this.manager.isInstallIntact(id)) {
4001
+ log$2.info(`Auto-reinstalling ${id} — install directory is corrupted or missing`);
4002
+ try {
4003
+ if ((await this.manager.reinstall(id, desired.version, desired.config)).configApplied) report.configApplied = true;
4004
+ report.installed.push(id);
4005
+ report.activated.push(id);
4006
+ report.results.push({
4007
+ integrationId: id,
4008
+ action: "installed",
4009
+ actualStatus: "active"
4010
+ });
4011
+ } catch (reinstallErr) {
4012
+ const reinstallMsg = reinstallErr instanceof Error ? reinstallErr.message : String(reinstallErr);
4013
+ log$2.error({ err: reinstallErr }, `Auto-reinstall failed for ${id}`);
4014
+ report.errors.push({
4015
+ integrationId: id,
4016
+ error: reinstallMsg
4017
+ });
4018
+ report.results.push({
4019
+ integrationId: id,
4020
+ action: "error",
4021
+ actualStatus: "error",
4022
+ errorMessage: reinstallMsg
4023
+ });
4024
+ }
4025
+ return;
4026
+ }
4012
4027
  log$2.warn(`Integration ${id} is in error state — waiting for reinstall request`);
4013
4028
  report.errors.push({
4014
4029
  integrationId: id,
@@ -4126,6 +4141,8 @@ var CloudClient = class {
4126
4141
  onRuntimeRestartNeeded = null;
4127
4142
  onReconciliationComplete = null;
4128
4143
  reconciliationEngine = null;
4144
+ reconciling = false;
4145
+ pendingDesiredState = null;
4129
4146
  constructor(config) {
4130
4147
  this.config = config;
4131
4148
  }
@@ -4189,6 +4206,8 @@ var CloudClient = class {
4189
4206
  this.ws = null;
4190
4207
  }
4191
4208
  this.registered = false;
4209
+ this.reconciling = false;
4210
+ this.pendingDesiredState = null;
4192
4211
  logger$1.debug("Cloud client stopped");
4193
4212
  }
4194
4213
  /**
@@ -4348,24 +4367,47 @@ var CloudClient = class {
4348
4367
  logger$1.warn("Cloud: DESIRED_STATE received but no integration manager set — skipping reconciliation");
4349
4368
  return;
4350
4369
  }
4370
+ if (this.reconciling) {
4371
+ logger$1.info("Cloud: reconciliation in progress — queuing latest desired state");
4372
+ this.pendingDesiredState = msg;
4373
+ return;
4374
+ }
4375
+ this.reconciling = true;
4351
4376
  try {
4352
- const report = await this.reconciliationEngine.reconcile(msg.integrations);
4353
- logger$1.info({
4354
- installed: report.installed.length,
4355
- activated: report.activated.length,
4356
- deactivated: report.deactivated.length,
4357
- uninstalled: report.uninstalled.length,
4358
- errors: report.errors.length
4359
- }, "Cloud: reconciliation complete");
4360
- const reportMsg = createReconciliationReport(report.results);
4361
- this.send(reportMsg);
4362
- if ((report.installed.length > 0 || report.uninstalled.length > 0 || report.configApplied) && this.onRuntimeRestartNeeded) this.onRuntimeRestartNeeded();
4363
- this.onReconciliationComplete?.();
4377
+ await this.runReconciliation(msg);
4364
4378
  } catch (err) {
4365
4379
  const message = err instanceof Error ? err.message : String(err);
4366
4380
  logger$1.error({ err: message }, "Cloud: reconciliation failed");
4381
+ } finally {
4382
+ while (this.pendingDesiredState) {
4383
+ const next = this.pendingDesiredState;
4384
+ this.pendingDesiredState = null;
4385
+ logger$1.info({ count: next.integrations.length }, "Cloud: processing queued DESIRED_STATE");
4386
+ try {
4387
+ await this.runReconciliation(next);
4388
+ } catch (err) {
4389
+ const message = err instanceof Error ? err.message : String(err);
4390
+ logger$1.error({ err: message }, "Cloud: queued reconciliation failed");
4391
+ }
4392
+ }
4393
+ this.reconciling = false;
4367
4394
  }
4368
4395
  }
4396
+ async runReconciliation(msg) {
4397
+ if (!this.reconciliationEngine) return;
4398
+ const report = await this.reconciliationEngine.reconcile(msg.integrations);
4399
+ logger$1.info({
4400
+ installed: report.installed.length,
4401
+ activated: report.activated.length,
4402
+ deactivated: report.deactivated.length,
4403
+ uninstalled: report.uninstalled.length,
4404
+ errors: report.errors.length
4405
+ }, "Cloud: reconciliation complete");
4406
+ const reportMsg = createReconciliationReport(report.results);
4407
+ this.send(reportMsg);
4408
+ if ((report.installed.length > 0 || report.uninstalled.length > 0 || report.configApplied) && this.onRuntimeRestartNeeded) this.onRuntimeRestartNeeded();
4409
+ this.onReconciliationComplete?.();
4410
+ }
4369
4411
  send(msg) {
4370
4412
  if (this.ws?.readyState === WebSocket.OPEN) this.ws.send(JSON.stringify(msg));
4371
4413
  else logger$1.debug({ readyState: this.ws?.readyState }, "Cloud: send skipped — WebSocket not open");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@alfe.ai/gateway",
3
- "version": "0.0.34",
3
+ "version": "0.0.36",
4
4
  "description": "Alfe local gateway daemon — persistent control plane for agent integrations",
5
5
  "type": "module",
6
6
  "bin": {
@@ -25,7 +25,7 @@
25
25
  "@alfe.ai/ai-proxy-local": "^0.0.7",
26
26
  "@alfe.ai/config": "^0.0.7",
27
27
  "@alfe.ai/integration-manifest": "^0.0.9",
28
- "@alfe.ai/integrations": "^0.0.22"
28
+ "@alfe.ai/integrations": "^0.0.24"
29
29
  },
30
30
  "license": "UNLICENSED",
31
31
  "scripts": {