@elizaos/plugin-bootstrap 1.0.0-beta.48 → 1.0.0-beta.49

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/dist/index.js CHANGED
@@ -174,6 +174,10 @@ var choiceAction = {
174
174
  similes: ["SELECT_OPTION", "SELECT", "PICK", "CHOOSE"],
175
175
  description: "Selects an option for a pending task that has multiple options",
176
176
  validate: async (runtime, message, state) => {
177
+ if (!state) {
178
+ logger.error("State is required for validating the action");
179
+ throw new Error("State is required for validating the action");
180
+ }
177
181
  const pendingTasks = await runtime.getTasks({
178
182
  roomId: message.roomId,
179
183
  tags: ["AWAITING_CHOICE"]
@@ -199,12 +203,12 @@ var choiceAction = {
199
203
  throw new Error("No tasks currently have options to select from.");
200
204
  }
201
205
  const formattedTasks = tasksWithOptions.map((task) => {
202
- const shortId = task.id.substring(0, 8);
206
+ const shortId = task.id?.substring(0, 8);
203
207
  return {
204
208
  taskId: shortId,
205
209
  fullId: task.id,
206
210
  name: task.name,
207
- options: task.metadata.options.map((opt) => ({
211
+ options: task.metadata?.options?.map((opt) => ({
208
212
  name: typeof opt === "string" ? opt : opt.name,
209
213
  description: typeof opt === "string" ? opt : opt.description || opt.name
210
214
  }))
@@ -213,12 +217,12 @@ var choiceAction = {
213
217
  const tasksString = formattedTasks.map((task) => {
214
218
  return `Task ID: ${task.taskId} - ${task.name}
215
219
  Available options:
216
- ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
220
+ ${task.options?.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
217
221
  }).join("\n");
218
222
  const prompt = composePrompt({
219
223
  state: {
220
224
  tasks: tasksString,
221
- recentMessages: message.content.text
225
+ recentMessages: message.content.text || ""
222
226
  },
223
227
  template: optionExtractionTemplate
224
228
  });
@@ -232,7 +236,7 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
232
236
  const taskMap = new Map(formattedTasks.map((task) => [task.taskId, task]));
233
237
  const taskInfo = taskMap.get(taskId);
234
238
  if (!taskInfo) {
235
- await callback({
239
+ await callback?.({
236
240
  text: `Could not find a task matching ID: ${taskId}. Please try again.`,
237
241
  actions: ["SELECT_OPTION_ERROR"],
238
242
  source: message.content.source
@@ -241,7 +245,7 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
241
245
  }
242
246
  const selectedTask = tasksWithOptions.find((task) => task.id === taskInfo.fullId);
243
247
  if (!selectedTask) {
244
- await callback({
248
+ await callback?.({
245
249
  text: "Error locating the selected task. Please try again.",
246
250
  actions: ["SELECT_OPTION_ERROR"],
247
251
  source: message.content.source
@@ -249,8 +253,16 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
249
253
  return;
250
254
  }
251
255
  if (selectedOption === "ABORT") {
256
+ if (!selectedTask?.id) {
257
+ await callback?.({
258
+ text: "Error locating the selected task. Please try again.",
259
+ actions: ["SELECT_OPTION_ERROR"],
260
+ source: message.content.source
261
+ });
262
+ return;
263
+ }
252
264
  await runtime.deleteTask(selectedTask.id);
253
- await callback({
265
+ await callback?.({
254
266
  text: `Task "${selectedTask.name}" has been cancelled.`,
255
267
  actions: ["CHOOSE_OPTION_CANCELLED"],
256
268
  source: message.content.source
@@ -259,8 +271,8 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
259
271
  }
260
272
  try {
261
273
  const taskWorker = runtime.getTaskWorker(selectedTask.name);
262
- await taskWorker.execute(runtime, { option: selectedOption }, selectedTask);
263
- await callback({
274
+ await taskWorker?.execute(runtime, { option: selectedOption }, selectedTask);
275
+ await callback?.({
264
276
  text: `Selected option: ${selectedOption} for task: ${selectedTask.name}`,
265
277
  actions: ["CHOOSE_OPTION"],
266
278
  source: message.content.source
@@ -268,7 +280,7 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
268
280
  return;
269
281
  } catch (error) {
270
282
  logger.error("Error executing task with option:", error);
271
- await callback({
283
+ await callback?.({
272
284
  text: "There was an error processing your selection.",
273
285
  actions: ["SELECT_OPTION_ERROR"],
274
286
  source: message.content.source
@@ -278,24 +290,24 @@ ${task.options.map((opt) => `- ${opt.name}: ${opt.description}`).join("\n")}`;
278
290
  }
279
291
  let optionsText = "Please select a valid option from one of these tasks:\n\n";
280
292
  tasksWithOptions.forEach((task) => {
281
- const shortId = task.id.substring(0, 8);
293
+ const shortId = task.id?.substring(0, 8);
282
294
  optionsText += `**${task.name}** (ID: ${shortId}):
283
295
  `;
284
- const options = task.metadata.options.map(
296
+ const options = task.metadata?.options?.map(
285
297
  (opt) => typeof opt === "string" ? opt : opt.name
286
298
  );
287
- options.push("ABORT");
288
- optionsText += options.map((opt) => `- ${opt}`).join("\n");
299
+ options?.push("ABORT");
300
+ optionsText += options?.map((opt) => `- ${opt}`).join("\n");
289
301
  optionsText += "\n\n";
290
302
  });
291
- await callback({
303
+ await callback?.({
292
304
  text: optionsText,
293
305
  actions: ["SELECT_OPTION_INVALID"],
294
306
  source: message.content.source
295
307
  });
296
308
  } catch (error) {
297
309
  logger.error("Error in select option handler:", error);
298
- await callback({
310
+ await callback?.({
299
311
  text: "There was an error processing the option selection.",
300
312
  actions: ["SELECT_OPTION_ERROR"],
301
313
  source: message.content.source
@@ -369,6 +381,10 @@ var followRoomAction = {
369
381
  return roomState !== "FOLLOWED" && roomState !== "MUTED";
370
382
  },
371
383
  handler: async (runtime, message, state, _options, _callback, _responses) => {
384
+ if (!state) {
385
+ logger2.error("State is required for followRoomAction");
386
+ throw new Error("State is required for followRoomAction");
387
+ }
372
388
  async function _shouldFollow(state2) {
373
389
  const shouldFollowPrompt = composePromptFromState({
374
390
  state: state2,
@@ -965,6 +981,10 @@ var muteRoomAction = {
965
981
  return roomState !== "MUTED";
966
982
  },
967
983
  handler: async (runtime, message, state, _options, _callback, _responses) => {
984
+ if (!state) {
985
+ logger3.error("State is required for muting a room");
986
+ throw new Error("State is required for muting a room");
987
+ }
968
988
  async function _shouldMute(state2) {
969
989
  const shouldMutePrompt = composePromptFromState2({
970
990
  state: state2,
@@ -1438,17 +1458,20 @@ var updateRoleAction = {
1438
1458
  );
1439
1459
  },
1440
1460
  handler: async (runtime, message, state, _options, callback) => {
1461
+ if (!state) {
1462
+ logger4.error("State is required for role assignment");
1463
+ throw new Error("State is required for role assignment");
1464
+ }
1441
1465
  const { roomId } = message;
1442
- const channelType = message.content.channelType;
1443
1466
  const serverId = message.content.serverId;
1444
1467
  const worldId = runtime.getSetting("WORLD_ID");
1445
- let world;
1468
+ let world = null;
1446
1469
  if (worldId) {
1447
1470
  world = await runtime.getWorld(worldId);
1448
1471
  }
1449
1472
  if (!world) {
1450
1473
  logger4.error("World not found");
1451
- await callback({
1474
+ await callback?.({
1452
1475
  text: "I couldn't find the world. This action only works in a world."
1453
1476
  });
1454
1477
  return;
@@ -1518,7 +1541,7 @@ var updateRoleAction = {
1518
1541
  }
1519
1542
  );
1520
1543
  if (!result?.length) {
1521
- await callback({
1544
+ await callback?.({
1522
1545
  text: "No valid role assignments found in the request.",
1523
1546
  actions: ["UPDATE_ROLE"],
1524
1547
  source: "discord"
@@ -1533,8 +1556,8 @@ var updateRoleAction = {
1533
1556
  }
1534
1557
  const currentRole = world.metadata.roles[assignment.entityId];
1535
1558
  if (!canModifyRole(requesterRole, currentRole, assignment.newRole)) {
1536
- await callback({
1537
- text: `You don't have permission to change ${targetEntity.names[0]}'s role to ${assignment.newRole}.`,
1559
+ await callback?.({
1560
+ text: `You don't have permission to change ${targetEntity?.names[0]}'s role to ${assignment.newRole}.`,
1538
1561
  actions: ["UPDATE_ROLE"],
1539
1562
  source: "discord"
1540
1563
  });
@@ -1542,8 +1565,8 @@ var updateRoleAction = {
1542
1565
  }
1543
1566
  world.metadata.roles[assignment.entityId] = assignment.newRole;
1544
1567
  worldUpdated = true;
1545
- await callback({
1546
- text: `Updated ${targetEntity.names[0]}'s role to ${assignment.newRole}.`,
1568
+ await callback?.({
1569
+ text: `Updated ${targetEntity?.names[0]}'s role to ${assignment.newRole}.`,
1547
1570
  actions: ["UPDATE_ROLE"],
1548
1571
  source: "discord"
1549
1572
  });
@@ -1672,6 +1695,18 @@ var sendMessageAction = {
1672
1695
  },
1673
1696
  handler: async (runtime, message, state, _options, callback, responses) => {
1674
1697
  try {
1698
+ if (!state) {
1699
+ logger5.error("State is required for sendMessage action");
1700
+ throw new Error("State is required for sendMessage action");
1701
+ }
1702
+ if (!callback) {
1703
+ logger5.error("Callback is required for sendMessage action");
1704
+ throw new Error("Callback is required for sendMessage action");
1705
+ }
1706
+ if (!responses) {
1707
+ logger5.error("Responses are required for sendMessage action");
1708
+ throw new Error("Responses are required for sendMessage action");
1709
+ }
1675
1710
  for (const response of responses) {
1676
1711
  await callback(response.content);
1677
1712
  }
@@ -1747,7 +1782,7 @@ var sendMessageAction = {
1747
1782
  } else if (targetData.targetType === "room") {
1748
1783
  const rooms = await runtime.getRooms(worldId);
1749
1784
  const targetRoom = rooms.find((r) => {
1750
- return r.name.toLowerCase() === targetData.identifiers.roomName?.toLowerCase();
1785
+ return r.name?.toLowerCase() === targetData.identifiers.roomName?.toLowerCase();
1751
1786
  });
1752
1787
  if (!targetRoom) {
1753
1788
  await callback({
@@ -1784,7 +1819,7 @@ var sendMessageAction = {
1784
1819
  }
1785
1820
  } catch (error) {
1786
1821
  logger5.error(`Error in sendMessage handler: ${error}`);
1787
- await callback({
1822
+ await callback?.({
1788
1823
  text: "There was an error processing your message request.",
1789
1824
  actions: ["SEND_MESSAGE_ERROR"],
1790
1825
  source: message.content.source
@@ -2020,7 +2055,7 @@ async function extractSettingValues(runtime, _message, state, worldSettings) {
2020
2055
  If a setting is mentioned but no clear value is provided, do not include it.
2021
2056
  `;
2022
2057
  try {
2023
- let extractValidSettings = function(obj, worldSettings2) {
2058
+ let extractValidSettings2 = function(obj, worldSettings2) {
2024
2059
  const extracted = [];
2025
2060
  function traverse(node) {
2026
2061
  if (Array.isArray(node)) {
@@ -2040,6 +2075,7 @@ async function extractSettingValues(runtime, _message, state, worldSettings) {
2040
2075
  traverse(obj);
2041
2076
  return extracted;
2042
2077
  };
2078
+ var extractValidSettings = extractValidSettings2;
2043
2079
  const result = await runtime.useModel(
2044
2080
  ModelType7.OBJECT_LARGE,
2045
2081
  {
@@ -2061,7 +2097,7 @@ async function extractSettingValues(runtime, _message, state, worldSettings) {
2061
2097
  if (!result) {
2062
2098
  return [];
2063
2099
  }
2064
- const extractedSettings = extractValidSettings(result, worldSettings);
2100
+ const extractedSettings = extractValidSettings2(result, worldSettings);
2065
2101
  return extractedSettings;
2066
2102
  } catch (error) {
2067
2103
  console.error("Error extracting settings:", error);
@@ -2250,10 +2286,10 @@ var updateSettingsAction = {
2250
2286
  if (!worlds) {
2251
2287
  return false;
2252
2288
  }
2253
- const world = worlds.find((world2) => world2.metadata.settings);
2254
- const worldSettings = world.metadata.settings;
2289
+ const world = worlds.find((world2) => world2.metadata?.settings);
2290
+ const worldSettings = world?.metadata?.settings;
2255
2291
  if (!worldSettings) {
2256
- logger6.error(`No settings state found for server ${world.serverId}`);
2292
+ logger6.error(`No settings state found for server ${world?.serverId}`);
2257
2293
  return false;
2258
2294
  }
2259
2295
  logger6.debug(`Found valid settings state for server ${world.serverId}`);
@@ -2265,16 +2301,32 @@ var updateSettingsAction = {
2265
2301
  },
2266
2302
  handler: async (runtime, message, state, _options, callback) => {
2267
2303
  try {
2304
+ if (!state) {
2305
+ logger6.error("State is required for settings handler");
2306
+ throw new Error("State is required for settings handler");
2307
+ }
2308
+ if (!message) {
2309
+ logger6.error("Message is required for settings handler");
2310
+ throw new Error("Message is required for settings handler");
2311
+ }
2312
+ if (!callback) {
2313
+ logger6.error("Callback is required for settings handler");
2314
+ throw new Error("Callback is required for settings handler");
2315
+ }
2268
2316
  logger6.info(`Handler looking for server for user ${message.entityId}`);
2269
2317
  const worlds = await findWorldsForOwner(runtime, message.entityId);
2270
- const serverOwnership = worlds.find((world) => world.metadata.settings);
2318
+ const serverOwnership = worlds?.find((world) => world.metadata?.settings);
2271
2319
  if (!serverOwnership) {
2272
2320
  logger6.error(`No server found for user ${message.entityId} in handler`);
2273
2321
  await generateErrorResponse(runtime, state, callback);
2274
2322
  return;
2275
2323
  }
2276
- const serverId = serverOwnership.serverId;
2324
+ const serverId = serverOwnership?.serverId;
2277
2325
  logger6.info(`Using server ID: ${serverId}`);
2326
+ if (!serverId) {
2327
+ logger6.error(`No server ID found for user ${message.entityId} in handler`);
2328
+ return;
2329
+ }
2278
2330
  const worldSettings = await getWorldSettings(runtime, serverId);
2279
2331
  if (!worldSettings) {
2280
2332
  logger6.error(`No settings state found for server ${serverId} in handler`);
@@ -2311,7 +2363,9 @@ var updateSettingsAction = {
2311
2363
  }
2312
2364
  } catch (error) {
2313
2365
  logger6.error(`Error in settings handler: ${error}`);
2314
- await generateErrorResponse(runtime, state, callback);
2366
+ if (state && callback) {
2367
+ await generateErrorResponse(runtime, state, callback);
2368
+ }
2315
2369
  }
2316
2370
  },
2317
2371
  examples: [
@@ -2529,7 +2583,7 @@ var unfollowRoomAction = {
2529
2583
  const parsedResponse = parseBooleanFromText(response.trim());
2530
2584
  return parsedResponse;
2531
2585
  }
2532
- if (await _shouldUnfollow(state)) {
2586
+ if (state && await _shouldUnfollow(state)) {
2533
2587
  await runtime.setParticipantUserState(message.roomId, runtime.agentId, null);
2534
2588
  const room = state.data.room ?? await runtime.getRoom(message.roomId);
2535
2589
  await runtime.createMemory(
@@ -2892,10 +2946,14 @@ var unmuteRoomAction = {
2892
2946
  logger7.warn(`Unclear boolean response: ${response}, defaulting to false`);
2893
2947
  return false;
2894
2948
  }
2895
- if (await _shouldUnmute(state)) {
2949
+ if (state && await _shouldUnmute(state)) {
2896
2950
  await runtime.setParticipantUserState(message.roomId, runtime.agentId, null);
2897
2951
  }
2898
2952
  const room = await runtime.getRoom(message.roomId);
2953
+ if (!room) {
2954
+ logger7.warn(`Room not found: ${message.roomId}`);
2955
+ return false;
2956
+ }
2899
2957
  await runtime.createMemory(
2900
2958
  {
2901
2959
  entityId: message.entityId,
@@ -3071,6 +3129,22 @@ var updateEntityAction = {
3071
3129
  },
3072
3130
  handler: async (runtime, message, state, _options, callback, responses) => {
3073
3131
  try {
3132
+ if (!state) {
3133
+ logger8.error("State is required for the updateEntity action");
3134
+ throw new Error("State is required for the updateEntity action");
3135
+ }
3136
+ if (!callback) {
3137
+ logger8.error("State is required for the updateEntity action");
3138
+ throw new Error("Callback is required for the updateEntity action");
3139
+ }
3140
+ if (!responses) {
3141
+ logger8.error("Responses are required for the updateEntity action");
3142
+ throw new Error("Responses are required for the updateEntity action");
3143
+ }
3144
+ if (!message) {
3145
+ logger8.error("Message is required for the updateEntity action");
3146
+ throw new Error("Message is required for the updateEntity action");
3147
+ }
3074
3148
  for (const response of responses) {
3075
3149
  await callback(response.content);
3076
3150
  }
@@ -3133,7 +3207,8 @@ var updateEntityAction = {
3133
3207
  data: componentData,
3134
3208
  agentId,
3135
3209
  roomId: message.roomId,
3136
- sourceEntityId
3210
+ sourceEntityId,
3211
+ createdAt: existingComponent.createdAt
3137
3212
  });
3138
3213
  await callback({
3139
3214
  text: `I've updated the ${componentType} information for ${entity.names[0]}.`,
@@ -3149,7 +3224,8 @@ var updateEntityAction = {
3149
3224
  data: componentData,
3150
3225
  agentId,
3151
3226
  roomId: message.roomId,
3152
- sourceEntityId
3227
+ sourceEntityId,
3228
+ createdAt: Date.now()
3153
3229
  });
3154
3230
  await callback({
3155
3231
  text: `I've added new ${componentType} information for ${entity.names[0]}.`,
@@ -3159,7 +3235,7 @@ var updateEntityAction = {
3159
3235
  }
3160
3236
  } catch (error) {
3161
3237
  logger8.error(`Error in updateEntity handler: ${error}`);
3162
- await callback({
3238
+ await callback?.({
3163
3239
  text: "There was an error processing the entity information.",
3164
3240
  actions: ["UPDATE_ENTITY_ERROR"],
3165
3241
  source: message.content.source
@@ -3300,23 +3376,27 @@ function resolveEntity(entityId, entities) {
3300
3376
  }
3301
3377
  let entity;
3302
3378
  entity = entities.find((a2) => a2.id === entityId);
3303
- if (entity) {
3379
+ if (entity?.id) {
3304
3380
  return entity.id;
3305
3381
  }
3306
- entity = entities.find((a2) => a2.id.includes(entityId));
3307
- if (entity) {
3382
+ entity = entities.find((a2) => a2.id?.includes(entityId));
3383
+ if (entity?.id) {
3308
3384
  return entity.id;
3309
3385
  }
3310
3386
  entity = entities.find(
3311
3387
  (a2) => a2.names.some((n2) => n2.toLowerCase().includes(entityId.toLowerCase()))
3312
3388
  );
3313
- if (entity) {
3389
+ if (entity?.id) {
3314
3390
  return entity.id;
3315
3391
  }
3316
3392
  throw new Error(`Could not resolve entityId "${entityId}" to a valid UUID`);
3317
3393
  }
3318
3394
  async function handler(runtime, message, state) {
3319
3395
  const { agentId, roomId } = message;
3396
+ if (!agentId || !roomId) {
3397
+ logger9.warn("Missing agentId or roomId in message", message);
3398
+ return;
3399
+ }
3320
3400
  const [existingRelationships, entities, knownFacts] = await Promise.all([
3321
3401
  runtime.getRelationships({
3322
3402
  entityId: message.entityId
@@ -3331,7 +3411,7 @@ async function handler(runtime, message, state) {
3331
3411
  ]);
3332
3412
  const prompt = composePrompt4({
3333
3413
  state: {
3334
- ...state.values,
3414
+ ...state?.values || {},
3335
3415
  knownFacts: formatFacts(knownFacts),
3336
3416
  roomType: message.content.channelType,
3337
3417
  entitiesInRoom: JSON.stringify(entities),
@@ -3411,7 +3491,10 @@ async function handler(runtime, message, state) {
3411
3491
  });
3412
3492
  }
3413
3493
  }
3414
- await runtime.setCache(`${message.roomId}-reflection-last-processed`, message.id);
3494
+ await runtime.setCache(
3495
+ `${message.roomId}-reflection-last-processed`,
3496
+ message?.id || ""
3497
+ );
3415
3498
  return reflection;
3416
3499
  } catch (error) {
3417
3500
  logger9.error("Error in reflection handler:", error);
@@ -3866,7 +3949,7 @@ var characterProvider = {
3866
3949
  () => Math.random().toString(36).substring(2, 8)
3867
3950
  );
3868
3951
  return example.map((message2) => {
3869
- let messageString = `${message2.name}: ${message2.content.text}${message2.content.action || message2.content.actions ? ` (actions: ${message2.content.action || message2.content.actions.join(", ")})` : ""}`;
3952
+ let messageString = `${message2.name}: ${message2.content.text}${message2.content.action || message2.content.actions ? ` (actions: ${message2.content.action || message2.content.actions?.join(", ")})` : ""}`;
3870
3953
  exampleNames.forEach((name, index) => {
3871
3954
  const placeholder = `{{name${index + 1}}}`;
3872
3955
  messageString = messageString.replaceAll(placeholder, name);
@@ -3880,7 +3963,7 @@ var characterProvider = {
3880
3963
  ) : "";
3881
3964
  const room = state.data.room ?? await runtime.getRoom(message.roomId);
3882
3965
  const isPostFormat = room?.type === ChannelType4.FEED || room?.type === ChannelType4.THREAD;
3883
- const postDirections = character?.style?.all?.length > 0 || character?.style?.post?.length > 0 ? addHeader4(
3966
+ const postDirections = character?.style?.all?.length && character?.style?.all?.length > 0 || character?.style?.post?.length && character?.style?.post?.length > 0 ? addHeader4(
3884
3967
  `# Post Directions for ${character.name}`,
3885
3968
  (() => {
3886
3969
  const all = character?.style?.all || [];
@@ -3888,7 +3971,7 @@ var characterProvider = {
3888
3971
  return [...all, ...post].join("\n");
3889
3972
  })()
3890
3973
  ) : "";
3891
- const messageDirections = character?.style?.all?.length > 0 || character?.style?.chat?.length > 0 ? addHeader4(
3974
+ const messageDirections = character?.style?.all?.length && character?.style?.all?.length > 0 || character?.style?.chat?.length && character?.style?.chat?.length > 0 ? addHeader4(
3892
3975
  `# Message Directions for ${character.name}`,
3893
3976
  (() => {
3894
3977
  const all = character?.style?.all || [];
@@ -3980,7 +4063,7 @@ var choiceProvider = {
3980
4063
  const options = task.metadata.options;
3981
4064
  options.forEach((option) => {
3982
4065
  if (typeof option === "string") {
3983
- const description = task.metadata?.options.find((o) => o.name === option)?.description || "";
4066
+ const description = task.metadata?.options?.find((o) => o.name === option)?.description || "";
3984
4067
  output += ` - \`${option}\` ${description ? `- ${description}` : ""}
3985
4068
  `;
3986
4069
  } else {
@@ -4115,7 +4198,7 @@ function formatEvaluatorExamples(evaluators) {
4115
4198
  const placeholder = `{{name${index + 1}}}`;
4116
4199
  messageString = messageString.replaceAll(placeholder, name);
4117
4200
  });
4118
- return messageString + (message.content.action || message.content.actions ? ` (${message.content.action || message.content.actions.join(", ")})` : "");
4201
+ return messageString + (message.content.action || message.content.actions ? ` (${message.content.action || message.content.actions?.join(", ")})` : "");
4119
4202
  }).join("\n");
4120
4203
  return `Prompt:
4121
4204
  ${formattedPrompt}
@@ -4574,12 +4657,16 @@ var roleProvider = {
4574
4657
  for (const entityId of Object.keys(roles)) {
4575
4658
  const userRole = roles[entityId];
4576
4659
  const user = await runtime.getEntityById(entityId);
4577
- const name = user.metadata[room.source]?.name;
4578
- const username = user.metadata[room.source]?.username;
4579
- const names = user.names;
4660
+ const name = user?.metadata?.[room.source]?.name;
4661
+ const username = user?.metadata?.[room.source]?.username;
4662
+ const names = user?.names;
4580
4663
  if (owners.some((owner) => owner.username === username) || admins.some((admin) => admin.username === username) || members.some((member) => member.username === username)) {
4581
4664
  continue;
4582
4665
  }
4666
+ if (!name || !username || !names) {
4667
+ logger12.warn(`User ${entityId} has no name or username, skipping`);
4668
+ continue;
4669
+ }
4583
4670
  switch (userRole) {
4584
4671
  case "OWNER":
4585
4672
  owners.push({ name, username, names });
@@ -4672,13 +4759,13 @@ function generateStatusMessage(runtime, worldSettings, isOnboarding, state) {
4672
4759
  };
4673
4760
  }).filter(Boolean);
4674
4761
  const requiredUnconfigured = formattedSettings.filter(
4675
- (s) => s.required && !s.configured
4762
+ (s) => s?.required && !s.configured
4676
4763
  ).length;
4677
4764
  if (isOnboarding) {
4678
4765
  const settingsList = formattedSettings.map((s) => {
4679
- const label = s.required ? "(Required)" : "(Optional)";
4680
- return `${s.key}: ${s.value} ${label}
4681
- (${s.name}) ${s.usageDescription}`;
4766
+ const label = s?.required ? "(Required)" : "(Optional)";
4767
+ return `${s?.key}: ${s?.value} ${label}
4768
+ (${s?.name}) ${s?.usageDescription}`;
4682
4769
  }).join("\n\n");
4683
4770
  const validKeys = `Valid setting keys: ${Object.keys(worldSettings).join(", ")}`;
4684
4771
  const commonInstructions = `Instructions for ${runtime.character.name}:
@@ -4688,7 +4775,7 @@ function generateStatusMessage(runtime, worldSettings, isOnboarding, state) {
4688
4775
  - Do not call UPDATE_SETTINGS just because the user has started onboarding or you think a setting needs to be configured. Only update when the user clearly provides a specific value for a setting you are currently asking about.
4689
4776
  - Answer setting-related questions using only the name, description, and value from the list.`;
4690
4777
  if (requiredUnconfigured > 0) {
4691
- return `# PRIORITY TASK: Onboarding with ${state.senderName}
4778
+ return `# PRIORITY TASK: Onboarding with ${state?.senderName}
4692
4779
 
4693
4780
  ${runtime.character.name} needs to help the user configure ${requiredUnconfigured} required settings:
4694
4781
 
@@ -4712,9 +4799,9 @@ function generateStatusMessage(runtime, worldSettings, isOnboarding, state) {
4712
4799
 
4713
4800
  ${requiredUnconfigured > 0 ? `IMPORTANT!: ${requiredUnconfigured} required settings still need configuration. ${runtime.character.name} should get onboarded with the OWNER as soon as possible.
4714
4801
 
4715
- ` : "All required settings are configured.\n\n"}${formattedSettings.map((s) => `### ${s.name}
4716
- **Value:** ${s.value}
4717
- **Description:** ${s.description}`).join("\n\n")}`;
4802
+ ` : "All required settings are configured.\n\n"}${formattedSettings.map((s) => `### ${s?.name}
4803
+ **Value:** ${s?.value}
4804
+ **Description:** ${s?.description}`).join("\n\n")}`;
4718
4805
  } catch (error) {
4719
4806
  logger13.error(`Error generating status message: ${error}`);
4720
4807
  return "Error generating configuration status.";
@@ -4758,11 +4845,11 @@ var settingsProvider = {
4758
4845
  }
4759
4846
  const type = room.type;
4760
4847
  const isOnboarding = type === ChannelType7.DM;
4761
- let world;
4762
- let serverId;
4763
- let worldSettings;
4848
+ let world = null;
4849
+ let serverId = void 0;
4850
+ let worldSettings = null;
4764
4851
  if (isOnboarding) {
4765
- world = userWorlds.find((world2) => world2.metadata.settings);
4852
+ world = userWorlds?.find((world2) => world2.metadata?.settings);
4766
4853
  if (!world) {
4767
4854
  logger13.error("No world found for user during onboarding");
4768
4855
  throw new Error("No server ownership found for onboarding");
@@ -4909,6 +4996,17 @@ var worldProvider = {
4909
4996
  }
4910
4997
  logger14.debug(`\u{1F310} World provider: Found room "${currentRoom.name}" (${currentRoom.type})`);
4911
4998
  const worldId = currentRoom.worldId;
4999
+ if (!worldId) {
5000
+ logger14.warn(`World provider: World ID not found for roomId ${message.roomId}`);
5001
+ return {
5002
+ data: {
5003
+ world: {
5004
+ info: "Unable to retrieve world information - world ID not found"
5005
+ }
5006
+ },
5007
+ text: "Unable to retrieve world information - world ID not found"
5008
+ };
5009
+ }
4912
5010
  const world = await runtime.getWorld(worldId);
4913
5011
  if (!world) {
4914
5012
  logger14.warn(`World provider: World not found for worldId ${worldId}`);
@@ -4937,6 +5035,10 @@ var worldProvider = {
4937
5035
  other: []
4938
5036
  };
4939
5037
  for (const room of worldRooms) {
5038
+ if (!room?.id || !room.name) {
5039
+ logger14.warn(`World provider: Room ID or name is missing for room ${room.id}`);
5040
+ continue;
5041
+ }
4940
5042
  const roomInfo = {
4941
5043
  id: room.id,
4942
5044
  name: room.name,
@@ -5416,7 +5518,7 @@ var TaskService = class _TaskService extends Service2 {
5416
5518
  await this.executeTask(task);
5417
5519
  continue;
5418
5520
  }
5419
- if (task.metadata.updatedAt === task.metadata.createdAt) {
5521
+ if (task.metadata?.updatedAt === task.metadata?.createdAt) {
5420
5522
  if (task.tags?.includes("immediate")) {
5421
5523
  logger16.debug("immediately running task", task.name);
5422
5524
  await this.executeTask(task);
@@ -5441,8 +5543,8 @@ var TaskService = class _TaskService extends Service2 {
5441
5543
  */
5442
5544
  async executeTask(task) {
5443
5545
  try {
5444
- if (!task) {
5445
- logger16.debug(`Task ${task.id} not found`);
5546
+ if (!task || !task.id) {
5547
+ logger16.debug(`Task not found`);
5446
5548
  return;
5447
5549
  }
5448
5550
  const worker = this.runtime.getTaskWorker(task.name);
@@ -5538,7 +5640,7 @@ var messageReceivedHandler = async ({
5538
5640
  source: "messageHandler"
5539
5641
  });
5540
5642
  const timeoutDuration = 60 * 60 * 1e3;
5541
- let timeoutId;
5643
+ let timeoutId = void 0;
5542
5644
  const timeoutPromise = new Promise((_, reject) => {
5543
5645
  timeoutId = setTimeout(async () => {
5544
5646
  await runtime.emitEvent(EventType2.RUN_TIMEOUT, {
@@ -5643,7 +5745,7 @@ var messageReceivedHandler = async ({
5643
5745
  );
5644
5746
  return;
5645
5747
  }
5646
- if (responseContent) {
5748
+ if (responseContent && message.id) {
5647
5749
  responseContent.inReplyTo = createUniqueUuid4(runtime, message.id);
5648
5750
  const responseMesssage = {
5649
5751
  id: asUUID(v4_default()),
@@ -5659,10 +5761,10 @@ var messageReceivedHandler = async ({
5659
5761
  if (agentResponses.size === 0) {
5660
5762
  latestResponseIds.delete(runtime.agentId);
5661
5763
  }
5662
- if (responseContent?.providers.length > 0) {
5663
- state = await runtime.composeState(message, null, [...responseContent?.providers]);
5764
+ if (responseContent?.providers?.length && responseContent.providers.length > 0) {
5765
+ state = await runtime.composeState(message, void 0, [...responseContent?.providers]);
5664
5766
  }
5665
- if (responseContent && responseContent.simple && responseContent.text && (responseContent.actions.length === 0 || responseContent.actions.length === 1 && responseContent.actions[0].toUpperCase() === "REPLY")) {
5767
+ if (responseContent && responseContent.simple && responseContent.text && (responseContent.actions?.length === 0 || responseContent.actions?.length === 1 && responseContent.actions[0].toUpperCase() === "REPLY")) {
5666
5768
  await callback(responseContent);
5667
5769
  } else {
5668
5770
  await runtime.processActions(message, responseMessages, state, callback);
@@ -5677,6 +5779,10 @@ var messageReceivedHandler = async ({
5677
5779
  );
5678
5780
  return;
5679
5781
  }
5782
+ if (!message.id) {
5783
+ logger17.error("Message ID is missing, cannot create ignore response.");
5784
+ return;
5785
+ }
5680
5786
  const ignoreContent = {
5681
5787
  thought: "Agent decided not to respond to this message.",
5682
5788
  actions: ["IGNORE"],
@@ -5787,7 +5893,7 @@ var postGeneratedHandler = async ({
5787
5893
  type: "message"
5788
5894
  }
5789
5895
  };
5790
- let state = await runtime.composeState(message, null, [
5896
+ let state = await runtime.composeState(message, void 0, [
5791
5897
  "PROVIDERS",
5792
5898
  "CHARACTER",
5793
5899
  //'RECENT_MESSAGES',
@@ -5825,7 +5931,7 @@ var postGeneratedHandler = async ({
5825
5931
  logger17.warn("*** Missing required fields, retrying... ***");
5826
5932
  }
5827
5933
  }
5828
- state = await runtime.composeState(message, responseContent.providers);
5934
+ state = await runtime.composeState(message, responseContent?.providers);
5829
5935
  const postPrompt = composePromptFromState9({
5830
5936
  state,
5831
5937
  template: runtime.character.templates?.postCreationTemplate || postCreationTemplate
@@ -5897,13 +6003,13 @@ var postGeneratedHandler = async ({
5897
6003
  }
5898
6004
  ];
5899
6005
  for (const message2 of responseMessages) {
5900
- await callback(message2.content);
6006
+ await callback?.(message2.content);
5901
6007
  }
5902
6008
  };
5903
6009
  var syncSingleUser = async (entityId, runtime, serverId, channelId, type, source) => {
5904
6010
  try {
5905
6011
  const entity = await runtime.getEntityById(entityId);
5906
- logger17.info(`Syncing user: ${entity?.metadata[source]?.username || entityId}`);
6012
+ logger17.info(`Syncing user: ${entity?.metadata?.[source]?.username || entityId}`);
5907
6013
  if (!channelId) {
5908
6014
  logger17.warn(`Cannot sync user ${entity?.id} without a valid channelId`);
5909
6015
  return;
@@ -5913,8 +6019,8 @@ var syncSingleUser = async (entityId, runtime, serverId, channelId, type, source
5913
6019
  await runtime.ensureConnection({
5914
6020
  entityId,
5915
6021
  roomId,
5916
- userName: entity?.metadata[source].username || entityId,
5917
- name: entity?.metadata[source].name || entity?.metadata[source].username || `User${entityId}`,
6022
+ userName: entity?.metadata?.[source].username || entityId,
6023
+ name: entity?.metadata?.[source].name || entity?.metadata?.[source].username || `User${entityId}`,
5918
6024
  source,
5919
6025
  channelId,
5920
6026
  serverId,
@@ -5963,14 +6069,22 @@ var handleServerSync = async ({
5963
6069
  for (let i2 = 0; i2 < entities.length; i2 += batchSize) {
5964
6070
  const entityBatch = entities.slice(i2, i2 + batchSize);
5965
6071
  const firstRoomUserIsIn = rooms.length > 0 ? rooms[0] : null;
6072
+ if (!firstRoomUserIsIn) {
6073
+ logger17.warn(`No rooms found for syncing users`);
6074
+ continue;
6075
+ }
5966
6076
  await Promise.all(
5967
6077
  entityBatch.map(async (entity) => {
5968
6078
  try {
6079
+ if (!entity?.id) {
6080
+ logger17.warn(`No entity ID found for syncing users`);
6081
+ return;
6082
+ }
5969
6083
  await runtime.ensureConnection({
5970
6084
  entityId: entity.id,
5971
6085
  roomId: firstRoomUserIsIn.id,
5972
- userName: entity.metadata[source].username,
5973
- name: entity.metadata[source].name,
6086
+ userName: entity.metadata?.[source].username,
6087
+ name: entity.metadata?.[source].name,
5974
6088
  source,
5975
6089
  channelId: firstRoomUserIsIn.channelId,
5976
6090
  serverId: world.serverId,
@@ -5978,7 +6092,7 @@ var handleServerSync = async ({
5978
6092
  worldId: world.id
5979
6093
  });
5980
6094
  } catch (err) {
5981
- logger17.warn(`Failed to sync user ${entity.metadata.username}: ${err}`);
6095
+ logger17.warn(`Failed to sync user ${entity.metadata?.username}: ${err}`);
5982
6096
  }
5983
6097
  })
5984
6098
  );
@@ -6035,6 +6149,10 @@ var controlMessageHandler = async ({
6035
6149
  var events = {
6036
6150
  [EventType2.MESSAGE_RECEIVED]: [
6037
6151
  async (payload) => {
6152
+ if (!payload.callback) {
6153
+ logger17.error("No callback provided for message");
6154
+ return;
6155
+ }
6038
6156
  await messageReceivedHandler({
6039
6157
  runtime: payload.runtime,
6040
6158
  message: payload.message,
@@ -6045,6 +6163,10 @@ var events = {
6045
6163
  ],
6046
6164
  [EventType2.VOICE_MESSAGE_RECEIVED]: [
6047
6165
  async (payload) => {
6166
+ if (!payload.callback) {
6167
+ logger17.error("No callback provided for voice message");
6168
+ return;
6169
+ }
6048
6170
  await messageReceivedHandler({
6049
6171
  runtime: payload.runtime,
6050
6172
  message: payload.message,
@@ -6082,6 +6204,18 @@ var events = {
6082
6204
  ],
6083
6205
  [EventType2.ENTITY_JOINED]: [
6084
6206
  async (payload) => {
6207
+ if (!payload.worldId) {
6208
+ logger17.error("No callback provided for entity joined");
6209
+ return;
6210
+ }
6211
+ if (!payload.roomId) {
6212
+ logger17.error("No roomId provided for entity joined");
6213
+ return;
6214
+ }
6215
+ if (!payload.metadata?.type) {
6216
+ logger17.error("No type provided for entity joined");
6217
+ return;
6218
+ }
6085
6219
  await syncSingleUser(
6086
6220
  payload.entityId,
6087
6221
  payload.runtime,
@@ -6151,6 +6285,7 @@ var bootstrapPlugin = {
6151
6285
  updateRoleAction,
6152
6286
  updateSettingsAction
6153
6287
  ],
6288
+ // this is jank, these events are not valid
6154
6289
  events,
6155
6290
  evaluators: [reflectionEvaluator],
6156
6291
  providers: [