@johpaz/hive-sdk 0.3.0 → 0.3.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.
package/README.md CHANGED
@@ -230,4 +230,4 @@ npm view @johpaz/hive-sdk dist-tags # verificar después del release
230
230
 
231
231
  ---
232
232
 
233
- *Hive SDK v0.3.0 — MIT*
233
+ *Hive SDK v0.3.1 — MIT*
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@johpaz/hive-sdk",
3
- "version": "0.3.0",
3
+ "version": "0.3.1",
4
4
  "private": false,
5
5
  "description": "Hive SDK — The Agent Harness SDK. Build, deploy, and scale AI agent applications with multi-channel support, context engineering, and swarm orchestration.",
6
6
  "license": "MIT",
@@ -1378,12 +1378,12 @@ export class AgentLoop {
1378
1378
  // Resolve from database with priority: explicit param → DB lookup → single user/agent
1379
1379
  const threadId = config.configurable?.thread_id || (await resolveUserId({})) || "default"
1380
1380
  const agentId = config.configurable?.agent_id || (await resolveAgentId(config.configurable?.agent_id)) || (await this._resolveCoordinatorId()) || "main"
1381
- const systemPromptOverride = config.configurable?.system_prompt
1381
+ const systemPromptOverride = config.configurable?.system_prompt ?? undefined
1382
1382
  const channel = config.configurable?.channel
1383
1383
  const userId = config.configurable?.user_id || (await resolveUserId({
1384
1384
  channel: config.configurable?.channel ? (config.configurable?.channel as string).split(':')[0] : null,
1385
1385
  channelUserId: config.configurable?.thread_id
1386
- }))
1386
+ })) || undefined
1387
1387
 
1388
1388
  // Log MCP Manager status
1389
1389
  log.info(`[AgentLoop.stream] MCP Manager available: ${this.mcpManager !== null}`)
@@ -188,7 +188,7 @@ export async function compileContext(opts: {
188
188
 
189
189
  // [STEP-1] Load agent config
190
190
  log.info(`[context-compiler] [STEP-1] Loading agent config for id=${agentId}`)
191
- let agent: ReturnType<typeof fromAgentDoc>
191
+ let agent: ReturnType<typeof fromAgentDoc> | undefined
192
192
  try {
193
193
  const agentsCol = await col<AgentDoc>("agents")
194
194
  const entry = await agentsCol.get(agentId)
@@ -119,7 +119,7 @@ export class AgentRunner {
119
119
  let imageArtifacts: ModelResponse["imageArtifacts"]
120
120
  let lastAgentContent = ""
121
121
  let accumulatedAgentContent = "" // Accumulate content from all agent chunks
122
- let toolCalls: ModelResponse["toolCalls"] = []
122
+ let toolCalls: NonNullable<ModelResponse["toolCalls"]> = []
123
123
  let totalInputTokens = 0
124
124
  let totalOutputTokens = 0
125
125
 
@@ -9,6 +9,7 @@
9
9
  */
10
10
 
11
11
  import { z } from "zod";
12
+ import type { MCPClientManager } from "../mcp/index.ts";
12
13
  import type { ToolDefinition } from "../tools/ToolRegistry.ts";
13
14
  import type { SkillDefinition } from "../skills/defineSkill.ts";
14
15
  import type { Tool, ToolParameter } from "../tools/types.ts";
@@ -260,7 +261,7 @@ export async function createAgent(config: AgentConfig): Promise<Agent> {
260
261
  await syncCapabilityIndexes();
261
262
 
262
263
  // ─── MCP ──────────────────────────────────────────────────────────────────
263
- let mcpManager = null;
264
+ let mcpManager: MCPClientManager | null = null;
264
265
  if (config.mcpServers && Object.keys(config.mcpServers).length > 0) {
265
266
  const { MCPClientManager } = await import("../mcp/index.ts");
266
267
  const mcpConfig = {
@@ -21,9 +21,15 @@ export function toIndexable(value: string | null | undefined): string {
21
21
  return value ?? NO_PARENT;
22
22
  }
23
23
 
24
- /** Decode a value stored via {@link toIndexable} back to its nullable form. */
25
- export function fromIndexable(value: string): string | null {
26
- return value === NO_PARENT ? null : value;
24
+ /**
25
+ * Decode a value stored via {@link toIndexable} back to its nullable form.
26
+ *
27
+ * Acepta `null`/`undefined` porque una fila puede no tener el campo —el que
28
+ * llama suele escribir `fromIndexable(doc.parent_id ?? null)`— y devolver `null`
29
+ * es la respuesta correcta, no un caso a evitar en cada llamada.
30
+ */
31
+ export function fromIndexable(value: string | null | undefined): string | null {
32
+ return value === NO_PARENT || value == null ? null : value;
27
33
  }
28
34
 
29
35
  export async function col<T>(name: string) {
@@ -561,13 +561,19 @@ const LEGACY_CRON_PERSONA = {
561
561
  function migrateLegacyCatalogPersona(existing: AgentDoc, current: AgentDoc): AgentDoc {
562
562
  if (existing.id !== LEGACY_CRON_PERSONA.id || existing.source !== "catalog") return existing;
563
563
 
564
- let systemPrompt = existing.system_prompt;
564
+ // `system_prompt` es nullable en AgentDoc y esto corre en cada arranque: una
565
+ // fila sin prompt hacía estallar el seed entero con un TypeError, no un error
566
+ // de datos. Sin prompt no hay nada que migrar, así que se devuelve tal cual.
567
+ if (existing.system_prompt === null) return existing;
568
+
569
+ let systemPrompt: string = existing.system_prompt;
570
+ const currentPrompt = current.system_prompt ?? "";
565
571
  const hasLegacyStockPrompt = systemPrompt.includes(LEGACY_CRON_PERSONA.role)
566
572
  && systemPrompt.includes(LEGACY_CRON_PERSONA.receives);
567
573
  if (hasLegacyStockPrompt) {
568
574
  systemPrompt = systemPrompt
569
- .replace(LEGACY_CRON_PERSONA.role, current.system_prompt.match(/# ROL\n([^\n]+)/)?.[1] ?? LEGACY_CRON_PERSONA.role)
570
- .replace(LEGACY_CRON_PERSONA.receives, current.system_prompt.match(/# QUÉ RECIBES\n([^\n]+)/)?.[1] ?? LEGACY_CRON_PERSONA.receives);
575
+ .replace(LEGACY_CRON_PERSONA.role, currentPrompt.match(/# ROL\n([^\n]+)/)?.[1] ?? LEGACY_CRON_PERSONA.role)
576
+ .replace(LEGACY_CRON_PERSONA.receives, currentPrompt.match(/# QUÉ RECIBES\n([^\n]+)/)?.[1] ?? LEGACY_CRON_PERSONA.receives);
571
577
  if (!systemPrompt.includes(LEGACY_CRON_PERSONA.calendarProhibition)) {
572
578
  systemPrompt = systemPrompt.replace(
573
579
  "- No hablás con el usuario",