agentlife 2.3.0 → 2.4.1

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/index.js +36 -25
  2. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -2710,13 +2710,22 @@ function runStartupPurge(state) {
2710
2710
  console.log("[agentlife] surfaces DB: %d persisted%s%s", state.surfaceDb.size, purged > 0 ? ` (purged ${purged} past grace period)` : "", backfilled > 0 ? ` (backfilled ${backfilled} agent mappings from history)` : "");
2711
2711
  }
2712
2712
 
2713
- // render-widgets.ts
2714
- var PROVISIONED_IDS = new Set(PROVISIONED_AGENTS.filter((a) => !a.existingAgent).map((a) => a.id));
2715
- function listSpecialistIds(runtime) {
2713
+ // onboarding.ts
2714
+ var PROVISIONED_IDS = new Set(PROVISIONED_AGENTS.map((a) => a.id));
2715
+ function userAgentIds(runtime) {
2716
2716
  const cfg = runtime.config.loadConfig();
2717
2717
  const list = cfg?.agents?.list ?? [];
2718
2718
  return list.map((a) => a?.id).filter((id) => !!id && !PROVISIONED_IDS.has(id));
2719
2719
  }
2720
+ function isOnboarding(_state, runtime) {
2721
+ return userAgentIds(runtime).length === 0;
2722
+ }
2723
+ function snapshotOnboarding(state, runtime) {
2724
+ const count = userAgentIds(runtime).length;
2725
+ return { isActive: count === 0, userAgentCount: count };
2726
+ }
2727
+
2728
+ // render-widgets.ts
2720
2729
  function recentActivityCount(state, agentId, sinceMs) {
2721
2730
  if (!state.historyDb)
2722
2731
  return 0;
@@ -2770,7 +2779,7 @@ function agentEmoji(runtime, agentId) {
2770
2779
  return found?.identity?.emoji ?? "\uD83C\uDFAF";
2771
2780
  }
2772
2781
  function renderAgentWidget(state, runtime, agentId, log) {
2773
- if (PROVISIONED_IDS.has(agentId))
2782
+ if (!userAgentIds(runtime).includes(agentId))
2774
2783
  return;
2775
2784
  const entry = state.agentRegistry.get(agentId);
2776
2785
  if (!entry) {
@@ -2790,13 +2799,12 @@ function renderAgentWidget(state, runtime, agentId, log) {
2790
2799
  log(`[render-widgets] rendered ${agentId}-intro`);
2791
2800
  }
2792
2801
  function renderAllAgentWidgets(state, runtime, log) {
2793
- const ids = listSpecialistIds(runtime);
2794
- if (ids.length === 0) {
2795
- log("[render-widgets] no user agents — rendering welcome widget");
2802
+ if (isOnboarding(state, runtime)) {
2803
+ log("[render-widgets] onboarding active — rendering welcome widget");
2796
2804
  renderWelcomeWidget(state, log);
2797
2805
  return;
2798
2806
  }
2799
- for (const id of ids) {
2807
+ for (const id of userAgentIds(runtime)) {
2800
2808
  try {
2801
2809
  renderAgentWidget(state, runtime, id, log);
2802
2810
  } catch (e) {
@@ -2806,7 +2814,7 @@ function renderAllAgentWidgets(state, runtime, log) {
2806
2814
  }
2807
2815
  var WELCOME_SURFACE_ID = "welcome";
2808
2816
  var WELCOME_INPUT_SURFACE_ID = "welcome-input";
2809
- var ONBOARDING_SESSION_KEY = "agent:agentlife-builder:agentlife:onboarding:operator";
2817
+ var ONBOARDING_SESSION_KEY = "agent:agentlife-builder:agentlife:direct:onboarding";
2810
2818
  var ONBOARDING_PLAYBOOK = `## Zero-agent onboarding
2811
2819
 
2812
2820
  You are agent-builder running a one-time onboarding for a fresh user (no agents yet). The plugin already pushed a \`welcome-input\` surface; the user's reply in this session is a tap or text on that surface.
@@ -2983,13 +2991,13 @@ function registerSurfacesService(api, state) {
2983
2991
  state.surfaceDb = new SurfaceDb(db);
2984
2992
  }
2985
2993
  runStartupPurge(state);
2986
- const FLOW_INPUT_IDS = new Set(["welcome-input"]);
2994
+ const onboarding = isOnboarding(state, api.runtime);
2987
2995
  let inputPurged = 0;
2988
2996
  for (const [surfaceId, meta] of state.surfaceDb.entries()) {
2989
2997
  const headerLine = meta.lines[0] ?? "";
2990
2998
  if (!/\binput\b/.test(headerLine))
2991
2999
  continue;
2992
- if (FLOW_INPUT_IDS.has(surfaceId))
3000
+ if (onboarding)
2993
3001
  continue;
2994
3002
  state.surfaceDb.delete(surfaceId);
2995
3003
  inputPurged++;
@@ -2997,6 +3005,9 @@ function registerSurfacesService(api, state) {
2997
3005
  if (inputPurged > 0) {
2998
3006
  console.log("[agentlife] purged %d stale input surfaces on startup", inputPurged);
2999
3007
  }
3008
+ if (!onboarding) {
3009
+ deleteWelcomeWidget(state, console.log);
3010
+ }
3000
3011
  await loadRegistryFromDisk(state);
3001
3012
  console.log("[agentlife] surface persistence service started (SQLite: %s)", state.historyDbPath);
3002
3013
  setTimeout(async () => {
@@ -6115,15 +6126,15 @@ function registerPromptStateHook(api, state2) {
6115
6126
  if (isInternalSession(sessionKey))
6116
6127
  return;
6117
6128
  const dashboardState = buildDashboardStateContext(state2, agentId);
6118
- const isOnboarding = sessionKey === ONBOARDING_SESSION_KEY;
6119
- const appendSystemContext = isOnboarding ? dashboardState ? `${ONBOARDING_PLAYBOOK}
6129
+ const isOnboardingTurn = sessionKey === ONBOARDING_SESSION_KEY && isOnboarding(state2, api.runtime);
6130
+ const appendSystemContext = isOnboardingTurn ? dashboardState ? `${ONBOARDING_PLAYBOOK}
6120
6131
 
6121
6132
  ${dashboardState}` : ONBOARDING_PLAYBOOK : dashboardState;
6122
6133
  if (!appendSystemContext) {
6123
6134
  console.log("[agentlife:prompt-state] agentId=%s — no context to inject (surfaceDb size=%d)", agentId ?? "NONE", state2.surfaceDb?.size ?? 0);
6124
6135
  return;
6125
6136
  }
6126
- if (isOnboarding) {
6137
+ if (isOnboardingTurn) {
6127
6138
  console.log("[agentlife:prompt-state] onboarding session — injecting %d chars (playbook + dashboard)", appendSystemContext.length);
6128
6139
  } else {
6129
6140
  console.log("[agentlife:prompt-state] agentId=%s injecting %d chars dashboard state", agentId ?? "NONE", appendSystemContext.length);
@@ -6222,15 +6233,12 @@ function registerAgentGateway(api, state2) {
6222
6233
  configFields.push("subagents");
6223
6234
  if (identity)
6224
6235
  configFields.push("identity");
6225
- if (!existing) {
6226
- const provisionedIds = new Set(PROVISIONED_AGENTS.map((a) => a.id));
6227
- if (!provisionedIds.has(id)) {
6228
- try {
6229
- renderAgentWidget(state2, api.runtime, id, console.log);
6230
- deleteWelcomeWidget(state2, console.log);
6231
- } catch (e) {
6232
- console.warn("[agentlife] renderAgentWidget failed for %s: %s", id, e?.message);
6233
- }
6236
+ if (!existing && userAgentIds(api.runtime).includes(id)) {
6237
+ try {
6238
+ renderAgentWidget(state2, api.runtime, id, console.log);
6239
+ deleteWelcomeWidget(state2, console.log);
6240
+ } catch (e) {
6241
+ console.warn("[agentlife] renderAgentWidget failed for %s: %s", id, e?.message);
6234
6242
  }
6235
6243
  }
6236
6244
  respond(true, { status, id, name, model, workspace, description, ...configFields.length ? { configFields } : {} });
@@ -6624,6 +6632,9 @@ function registerUsageGateway(api, state2) {
6624
6632
  var guidedDismissSent = new Set;
6625
6633
  var warnedMissingOrigin = new Set;
6626
6634
  function registerSurfacesGateway(api, state2) {
6635
+ api.registerGatewayMethod("agentlife.onboarding.state", ({ respond }) => {
6636
+ respond(true, snapshotOnboarding(state2, api.runtime));
6637
+ }, { scope: "operator.read" });
6627
6638
  api.registerGatewayMethod("agentlife.surfaces", ({ params, respond, context }) => {
6628
6639
  captureBridge(context);
6629
6640
  const now = Date.now();
@@ -6633,13 +6644,13 @@ function registerSurfacesGateway(api, state2) {
6633
6644
  respond(true, { surfaces: [] });
6634
6645
  return;
6635
6646
  }
6636
- const FLOW_INPUT_IDS = new Set(["welcome-input"]);
6647
+ const onboarding = isOnboarding(state2, api.runtime);
6637
6648
  for (const [surfaceId, meta] of state2.surfaceDb.entries()) {
6638
6649
  if (isExpired(meta, now))
6639
6650
  continue;
6640
6651
  const headerLine = meta.lines[0] ?? "";
6641
6652
  const isInput = /\binput\b/.test(headerLine);
6642
- if (isInput && !FLOW_INPUT_IDS.has(surfaceId))
6653
+ if (isInput && !onboarding)
6643
6654
  continue;
6644
6655
  if (meta.lines.length > 0) {
6645
6656
  surfaceEntries.push({ surfaceId, dsl: meta.lines.join(`
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "agentlife",
3
- "version": "2.3.0",
3
+ "version": "2.4.1",
4
4
  "type": "module",
5
5
  "scripts": {
6
6
  "build": "bun build index.ts --outfile dist/index.js --target node --external openclaw/plugin-sdk",