{"_id":"@agentbase-sdk/react","_rev":"5-34f6285d9c48ab11a9cd6592d809fab5","name":"@agentbase-sdk/react","dist-tags":{"latest":"0.1.4"},"versions":{"0.1.0":{"name":"@agentbase-sdk/react","version":"0.1.0","keywords":["agentbase","react","hooks","ai","chat","sdk","streaming"],"author":"","license":"MIT","_id":"@agentbase-sdk/react@0.1.0","maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"dist":{"shasum":"dc4a6cdf7210ca56367e648726bafe6b0a15a942","tarball":"https://registry.npmjs.org/@agentbase-sdk/react/-/react-0.1.0.tgz","fileCount":7,"integrity":"sha512-8xC66Q4XfHql2Vo31TWqCEJrS+slV2TRI5o77zCU9R9ZjpEET4syKu3chkjrrrd0y3YQG6LAIshOalWVPTrNgQ==","signatures":[{"sig":"MEUCIQCZ7KggMMlbzaROrVHAaeVkfc1EG/HKWW2hBj2K/CmljAIgY4eqhFGhst9YCxQub/ckzVJrm5VLC2T8xGQmQKw6Wnk=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":37607},"main":"dist/index.js","types":"dist/index.d.ts","module":"dist/index.mjs","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.mjs","require":"./dist/index.js"}},"scripts":{"dev":"tsup src/index.ts --format cjs,esm --dts --watch","lint":"eslint src --ext .ts,.tsx","build":"tsup src/index.ts --format cjs,esm --dts","typecheck":"tsc --noEmit"},"_npmUser":{"name":"agentbasedev","email":"team@agentbase.sh"},"_npmVersion":"11.3.0","description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","directories":{},"_nodeVersion":"23.5.0","dependencies":{},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"tsup":"^8.0.0","react":"^18.2.0","typescript":"^5.3.0","@types/react":"^18.2.0"},"peerDependencies":{"react":"^18.0.0 || ^19.0.0"},"_npmOperationalInternal":{"tmp":"tmp/react_0.1.0_1762769831606_0.20710900039911895","host":"s3://npm-registry-packages-npm-production"}},"0.1.1":{"name":"@agentbase-sdk/react","version":"0.1.1","keywords":["agentbase","react","hooks","ai","agent","sdk"],"author":"","license":"MIT","_id":"@agentbase-sdk/react@0.1.1","maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"dist":{"shasum":"204559e38f9f64fdbe9fbe2d50373db5d3c8b034","tarball":"https://registry.npmjs.org/@agentbase-sdk/react/-/react-0.1.1.tgz","fileCount":7,"integrity":"sha512-QUtH9CkLWuz5gnF1zEi4uakFlPfaFZwww10nd9ywHtV6Q5U8HUIfTlP0eomGcutINylJGvsOh7ii+CL1QgRS8g==","signatures":[{"sig":"MEYCIQC1xM8dZ7PsO4cYT49Qs37Q5TVRl/kYviC+ZqhUpQsJlwIhAOlj2y5j1FrE+S1fEU3YE+Njm9qTVd8XUzySZxeeeS64","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":37830},"main":"dist/index.js","types":"dist/index.d.ts","module":"dist/index.mjs","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.mjs","require":"./dist/index.js"}},"scripts":{"dev":"tsup src/index.ts --format cjs,esm --dts --watch","lint":"eslint src --ext .ts,.tsx","build":"tsup src/index.ts --format cjs,esm --dts","typecheck":"tsc --noEmit"},"_npmUser":{"name":"agentbasedev","email":"team@agentbase.sh"},"_npmVersion":"11.3.0","description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","directories":{},"_nodeVersion":"23.5.0","dependencies":{},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"tsup":"^8.0.0","react":"^18.2.0","typescript":"^5.3.0","@types/react":"^18.2.0"},"peerDependencies":{"react":"^18.0.0 || ^19.0.0"},"_npmOperationalInternal":{"tmp":"tmp/react_0.1.1_1762770032215_0.5734414674364969","host":"s3://npm-registry-packages-npm-production"}},"0.1.2":{"name":"@agentbase-sdk/react","version":"0.1.2","keywords":["agentbase","react","hooks","ai","agent","sdk"],"author":"","license":"MIT","_id":"@agentbase-sdk/react@0.1.2","maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"dist":{"shasum":"6d80db8825d8d164b47d01fd473589e4404c5391","tarball":"https://registry.npmjs.org/@agentbase-sdk/react/-/react-0.1.2.tgz","fileCount":7,"integrity":"sha512-j2bdry77CsJuMhxKHdt8NvNdTXiVhBLXtjwgfusDtW320C/vOc3aSgKYdK42aPD14UKSSc7rmsgoBn3IuRNthA==","signatures":[{"sig":"MEUCIC+5UmcEI6Z3D5lSqRHDuqJyb9hZBSEwfOVLTsg9HgKPAiEA31OhlDbROKpSXor7oprKwU0PO4xvQAXIHST/jvHu9Go=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":42243},"main":"dist/index.js","types":"dist/index.d.ts","module":"dist/index.mjs","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.mjs","require":"./dist/index.js"}},"scripts":{"dev":"tsup src/index.ts --format cjs,esm --dts --watch","lint":"eslint src --ext .ts,.tsx","build":"tsup src/index.ts --format cjs,esm --dts","typecheck":"tsc --noEmit"},"_npmUser":{"name":"agentbasedev","email":"team@agentbase.sh"},"_npmVersion":"11.3.0","description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","directories":{},"_nodeVersion":"23.5.0","dependencies":{},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"tsup":"^8.0.0","react":"^18.2.0","typescript":"^5.3.0","@types/react":"^18.2.0"},"peerDependencies":{"react":"^18.0.0 || ^19.0.0"},"_npmOperationalInternal":{"tmp":"tmp/react_0.1.2_1762807935686_0.8032241744676023","host":"s3://npm-registry-packages-npm-production"}},"0.1.3":{"name":"@agentbase-sdk/react","version":"0.1.3","keywords":["agentbase","react","hooks","ai","agent","sdk"],"author":"","license":"MIT","_id":"@agentbase-sdk/react@0.1.3","maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"dist":{"shasum":"2a62bc673132a7e54ccde1105e52616f1a074ad7","tarball":"https://registry.npmjs.org/@agentbase-sdk/react/-/react-0.1.3.tgz","fileCount":7,"integrity":"sha512-5xtN0Ja4tGKji/aM1NcpGWo6t6j3V1iZVmTjt3S0AoVuACHXpvfvyWQqoXXW02Xx7XrHUhrpwsh3HnsWvB+mVg==","signatures":[{"sig":"MEUCIQD4oWWurr4oh9Vb6R1L9dvuzPaz4bfcYwK1ksKa7JrhPwIgetLzJ/Kw+f9LvBf92D2yM4eokpkDdCHhRhpG3uPS9Eg=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":42584},"main":"dist/index.js","types":"dist/index.d.ts","module":"dist/index.mjs","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.mjs","require":"./dist/index.js"}},"scripts":{"dev":"tsup src/index.ts --format cjs,esm --dts --watch","lint":"eslint src --ext .ts,.tsx","build":"tsup src/index.ts --format cjs,esm --dts","typecheck":"tsc --noEmit"},"_npmUser":{"name":"agentbasedev","email":"team@agentbase.sh"},"_npmVersion":"11.3.0","description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","directories":{},"_nodeVersion":"23.5.0","dependencies":{},"publishConfig":{"access":"public"},"_hasShrinkwrap":false,"devDependencies":{"tsup":"^8.0.0","react":"^18.2.0","typescript":"^5.3.0","@types/react":"^18.2.0"},"peerDependencies":{"react":"^18.0.0 || ^19.0.0"},"_npmOperationalInternal":{"tmp":"tmp/react_0.1.3_1762830362608_0.4715385229319744","host":"s3://npm-registry-packages-npm-production"}},"0.1.4":{"name":"@agentbase-sdk/react","version":"0.1.4","description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","publishConfig":{"access":"public"},"main":"dist/index.js","module":"dist/index.mjs","types":"dist/index.d.ts","exports":{".":{"types":"./dist/index.d.ts","import":"./dist/index.mjs","require":"./dist/index.js"}},"scripts":{"build":"tsup src/index.ts --format cjs,esm --dts","dev":"tsup src/index.ts --format cjs,esm --dts --watch","lint":"eslint src --ext .ts,.tsx","typecheck":"tsc --noEmit"},"keywords":["agentbase","react","hooks","ai","agent","sdk"],"author":"","license":"MIT","peerDependencies":{"react":"^18.0.0 || ^19.0.0"},"devDependencies":{"@types/react":"^18.2.0","react":"^18.2.0","tsup":"^8.0.0","typescript":"^5.3.0"},"dependencies":{},"_id":"@agentbase-sdk/react@0.1.4","gitHead":"333b5c1e6d14cbd25c29809b01dbc226b011ee7c","_nodeVersion":"23.5.0","_npmVersion":"11.3.0","dist":{"integrity":"sha512-pRCBxo1D1aZ0r5KalTjDrllydUTaMCfB/vn98hYDIfVSovaBxh6FMgwaRl7UtXj8/6lGYd0ZTU7AVIWnN730Kw==","shasum":"e6d565184b0735074d60be2e1ffe1ff16da589f9","tarball":"https://registry.npmjs.org/@agentbase-sdk/react/-/react-0.1.4.tgz","fileCount":7,"unpackedSize":52002,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIFBiLP6ibHH5ig22Z4q8QMspP10/p3ecn/gejji9Q1GIAiEAnKsCtWHeb9jNFyvPL3U7ITmNB5aPnKXPvTHGK95/XCc="}]},"_npmUser":{"name":"agentbasedev","email":"team@agentbase.sh"},"directories":{},"maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/react_0.1.4_1763665615281_0.3634048102021077"},"_hasShrinkwrap":false}},"time":{"created":"2025-11-10T10:17:11.500Z","modified":"2025-11-20T19:06:55.689Z","0.1.0":"2025-11-10T10:17:11.809Z","0.1.1":"2025-11-10T10:20:32.398Z","0.1.2":"2025-11-10T20:52:15.908Z","0.1.3":"2025-11-11T03:06:02.842Z","0.1.4":"2025-11-20T19:06:55.481Z"},"license":"MIT","keywords":["agentbase","react","hooks","ai","agent","sdk"],"description":"React hooks for Agentbase SDK - build conversational AI interfaces with ease","maintainers":[{"name":"agentbasedev","email":"team@agentbase.sh"}],"readme":"# Agentbase React SDK\n\nReact hooks for building conversational AI interfaces with [Agentbase](https://agentbase.sh). Simple, powerful, and focused.\n\n## Features\n\n- **Simple API** - Clean hook with just what you need: `send`, `stop`, `clear`\n- **Streaming Support** - Real-time streaming of agent responses\n- **Multi-Agent Flows** - Support for agent handoffs and transfers\n- **Session Management** - Automatic session tracking and continuation of previous conversations\n- **TypeScript** - Full TypeScript support with type definitions\n- **Server-Side** - Keep your API keys secure on the server\n\n## Installation\n\n```bash\nnpm install @agentbase-sdk/react agentbase-sdk\n```\n\n## Quick Start\n\n### 1. Create a Server-Side API Route\n\nThe React SDK calls a server-side endpoint to keep your Agentbase API key secure. Here's an example using Next.js App Router:\n\n```typescript\n// app/api/agent/route.ts\nimport Agentbase from \"agentbase-sdk\";\nimport { NextRequest } from \"next/server\";\n\n// Initialize Agentbase client (reuse across requests)\nconst agentbase = new Agentbase({\n  apiKey: process.env.AGENTBASE_API_KEY!,\n});\n\nexport const runtime = \"edge\"; // Optional: Use Edge Runtime for better performance\n\nexport async function GET(req: NextRequest) {\n  try {\n    // Get session ID from query parameters\n    const { searchParams } = new URL(req.url);\n    const sessionId = searchParams.get(\"session\");\n\n    if (!sessionId) {\n      return new Response(\"Session ID is required\", { status: 400 });\n    }\n\n    // Fetch messages for the session\n    const response = await fetch(\n      `https://api.agentbase.sh/sessions/${sessionId}/messages`,\n      {\n        method: \"GET\",\n        headers: {\n          \"Content-Type\": \"application/json\",\n          Authorization: `Bearer ${process.env.AGENTBASE_API_KEY}`,\n        },\n      }\n    );\n\n    if (!response.ok) {\n      throw new Error(`Failed to fetch messages: ${response.status}`);\n    }\n\n    const data = await response.json();\n\n    return new Response(JSON.stringify(data), {\n      headers: {\n        \"Content-Type\": \"application/json\",\n      },\n    });\n  } catch (error) {\n    console.error(\"Get messages error:\", error);\n    return new Response(\"Internal server error\", { status: 500 });\n  }\n}\n\nexport async function POST(req: NextRequest) {\n  try {\n    // Parse request body\n    const body = await req.json();\n    const {\n      message,\n      session,\n      system,\n      mode = \"fast\",\n      rules,\n      mcp_servers,\n      agents,\n      streaming_tokens = false,\n    } = body;\n\n    // Validate required fields\n    if (!message) {\n      return new Response(\"Message is required\", { status: 400 });\n    }\n\n    // Prepare Agentbase parameters\n    const params: any = {\n      message,\n      mode,\n      streaming_tokens,\n    };\n\n    if (session) params.session = session;\n    if (system) params.system = system;\n    if (rules) params.rules = rules;\n    if (mcp_servers) params.mcp_servers = mcp_servers;\n    if (agents) params.agents = agents;\n\n    // Create a TransformStream to convert async iterator to ReadableStream\n    const encoder = new TextEncoder();\n    const stream = new TransformStream();\n    const writer = stream.writable.getWriter();\n\n    // Start streaming in the background\n    (async () => {\n      try {\n        const responseStream = await agentbase.runAgent(params);\n\n        for await (const response of responseStream) {\n          // Format as Server-Sent Events\n          const data = `data: ${JSON.stringify(response)}\\n\\n`;\n          await writer.write(encoder.encode(data));\n        }\n\n        await writer.close();\n      } catch (error) {\n        console.error(\"Streaming error:\", error);\n        await writer.abort(error);\n      }\n    })();\n\n    // Return the stream as SSE\n    return new Response(stream.readable, {\n      headers: {\n        \"Content-Type\": \"text/event-stream\",\n        \"Cache-Control\": \"no-cache\",\n        Connection: \"keep-alive\",\n      },\n    });\n  } catch (error) {\n    console.error(\"Chat API error:\", error);\n    return new Response(\"Internal server error\", { status: 500 });\n  }\n}\n```\n\nSee [examples/nextjs](examples/nextjs) for the complete working example.\n\n### 2. Use the `useAgent` Hook in Your Component\n\n```tsx\n\"use client\";\n\nimport { useAgent } from \"@agentbase-sdk/react\";\nimport { useState } from \"react\";\n\nexport default function Chat() {\n  const [input, setInput] = useState(\"\");\n  const { messages, send, stop, clear, isRunning, error, session } = useAgent({\n    api: \"/api/agent\",\n    system: \"You are a helpful AI assistant. Be concise and friendly.\",\n    mode: \"fast\",\n    onError: (error) => {\n      console.error(\"Agent error:\", error);\n    },\n  });\n\n  const handleSubmit = (e: React.FormEvent) => {\n    e.preventDefault();\n    if (!input.trim() || isRunning) return;\n\n    send(input);\n    setInput(\"\");\n  };\n\n  return (\n    <div>\n      {/* Session Info */}\n      {session && <div>Session: {session.substring(0, 8)}...</div>}\n\n      {/* Error Display */}\n      {error && <div>Error: {error.message}</div>}\n\n      {/* Messages */}\n      <div>\n        {messages.map((message, msgIndex) => (\n          <div key={msgIndex}>\n            <strong>{message.role === \"user\" ? \"You\" : \"Assistant\"}:</strong>\n\n            {/* Render all content items */}\n            {message.content.map((item, index) => (\n              <div key={index}>\n                {item.type === \"text\" && (\n                  <div>{item.text}</div>\n                )}\n                {item.type === \"thinking\" && (\n                  <div style={{ fontStyle: \"italic\", opacity: 0.7 }}>\n                    💭 {item.text}\n                  </div>\n                )}\n                {item.type === \"tool_use\" && (\n                  <div>\n                    <strong>🔧 Tool Use:</strong>\n                    <pre>{item.text}</pre>\n                  </div>\n                )}\n                {item.type === \"tool_response\" && (\n                  <div>\n                    <strong>✅ Tool Result:</strong>\n                    <pre>{item.text}</pre>\n                  </div>\n                )}\n                {item.type === \"transfer\" && (\n                  <div>\n                    🔄 Transferred to: {item.agent}\n                    {item.context && <div>{item.context}</div>}\n                  </div>\n                )}\n              </div>\n            ))}\n          </div>\n        ))}\n\n        {/* Loading indicator */}\n        {isRunning && <div>...</div>}\n      </div>\n\n      {/* Controls */}\n      <button onClick={clear} disabled={messages.length === 0}>\n        Clear\n      </button>\n\n      {/* Input Form */}\n      <form onSubmit={handleSubmit}>\n        <input\n          value={input}\n          onChange={(e) => setInput(e.target.value)}\n          placeholder=\"Type your message...\"\n          disabled={isRunning}\n        />\n        {isRunning ? (\n          <button type=\"button\" onClick={stop}>\n            Stop\n          </button>\n        ) : (\n          <button type=\"submit\" disabled={!input.trim()}>\n            Send\n          </button>\n        )}\n      </form>\n    </div>\n  );\n}\n```\n\n## API Reference\n\n### `useAgent(options)`\n\nThe main hook for building agent interfaces.\n\n#### Options\n\n```typescript\ninterface UseAgentOptions {\n  // Required: API endpoint to call\n  api: string;\n\n  // Optional: Session ID to continue a previous conversation\n  // If provided, chat history will be fetched automatically\n  sessionId?: string;\n\n  // Optional: System prompt for the agent\n  system?: string;\n\n  // Optional: Agent mode (default: \"fast\")\n  mode?: \"flash\" | \"fast\" | \"max\";\n\n  // Optional: Rules for the agent\n  rules?: string[];\n\n  // Optional: MCP servers configuration\n  mcpServers?: Array<{\n    serverName: string;\n    serverUrl: string;\n  }>;\n\n  // Optional: Agent handoffs for multi-agent flows\n  agents?: Array<{\n    name: string;\n    description?: string;\n  }>;\n\n  // Optional: Stream tokens individually\n  streamingTokens?: boolean;\n\n  // Optional: Initial messages\n  initialMessages?: Message[];\n\n  // Optional: Error callback\n  onError?: (error: Error) => void;\n\n  // Optional: Custom headers and body\n  headers?: Record<string, string>;\n  body?: Record<string, any>;\n}\n```\n\n#### Returns\n\n```typescript\ninterface UseAgentReturn {\n  // Message history\n  messages: Message[];\n\n  // Send a message to the agent\n  send: (message: string) => Promise<void>;\n\n  // Stop the current agent run\n  stop: () => void;\n\n  // Clear all messages (locally and on server)\n  clear: () => Promise<void>;\n\n  // State\n  isRunning: boolean;\n  error: Error | null;\n  session: string | null;\n}\n```\n\n## Examples\n\n### Continuing a Previous Session\n\nPass a `sessionId` to the `useAgent` hook to continue a previous conversation. The hook will automatically:\n1. Fetch the chat history from your API's GET endpoint\n2. Display all previous messages\n3. Continue the conversation in the same session when you send new messages\n\n```tsx\n\"use client\";\n\nimport { useAgent } from \"@agentbase-sdk/react\";\nimport { useState } from \"react\";\n\nfunction ContinueSessionChat() {\n  const [input, setInput] = useState(\"\");\n  const [sessionInput, setSessionInput] = useState(\"\");\n  const [currentSessionId, setCurrentSessionId] = useState<string | undefined>();\n\n  const { messages, send, isRunning, session } = useAgent({\n    api: \"/api/agent\",\n    sessionId: currentSessionId, // Pass the session ID to continue\n    system: \"You are a helpful assistant.\",\n  });\n\n  const handleLoadSession = () => {\n    if (sessionInput.trim()) {\n      setCurrentSessionId(sessionInput.trim());\n    }\n  };\n\n  const handleSubmit = (e: React.FormEvent) => {\n    e.preventDefault();\n    if (!input.trim() || isRunning) return;\n    send(input);\n    setInput(\"\");\n  };\n\n  return (\n    <div>\n      {/* Load Session */}\n      <div>\n        <input\n          value={sessionInput}\n          onChange={(e) => setSessionInput(e.target.value)}\n          placeholder=\"Enter session ID to continue...\"\n        />\n        <button onClick={handleLoadSession}>Load Session</button>\n      </div>\n\n      {/* Current Session */}\n      {session && <div>Current Session: {session}</div>}\n\n      {/* Messages */}\n      <div>\n        {messages.map((msg, idx) => (\n          <div key={idx}>\n            <strong>{msg.role}:</strong>\n            {msg.content.map((item, i) => (\n              <div key={i}>\n                {item.type === \"text\" && <span>{item.text}</span>}\n              </div>\n            ))}\n          </div>\n        ))}\n      </div>\n\n      {/* Input */}\n      <form onSubmit={handleSubmit}>\n        <input\n          value={input}\n          onChange={(e) => setInput(e.target.value)}\n          disabled={isRunning}\n          placeholder=\"Type your message...\"\n        />\n        <button type=\"submit\" disabled={isRunning || !input.trim()}>\n          Send\n        </button>\n      </form>\n    </div>\n  );\n}\n```\n\n### Basic Chat\n\n```tsx\n\"use client\";\n\nimport { useAgent } from \"@agentbase-sdk/react\";\nimport { useState } from \"react\";\n\nfunction BasicChat() {\n  const [input, setInput] = useState(\"\");\n  const { messages, send, isRunning } = useAgent({\n    api: \"/api/agent\",\n    system: \"You are a helpful assistant.\",\n  });\n\n  return (\n    <div>\n      {messages.map((msg, idx) => (\n        <div key={idx}>\n          <strong>{msg.role}:</strong>\n          {msg.content.map((item, i) => (\n            <div key={i}>\n              {item.type === \"text\" && <span>{item.text}</span>}\n            </div>\n          ))}\n        </div>\n      ))}\n      <form\n        onSubmit={(e) => {\n          e.preventDefault();\n          if (!input.trim() || isRunning) return;\n          send(input);\n          setInput(\"\");\n        }}\n      >\n        <input\n          value={input}\n          onChange={(e) => setInput(e.target.value)}\n          disabled={isRunning}\n        />\n        <button type=\"submit\" disabled={isRunning || !input.trim()}>\n          Send\n        </button>\n      </form>\n    </div>\n  );\n}\n```\n\n### Advanced Features\n\n```tsx\n\"use client\";\n\nimport { useAgent } from \"@agentbase-sdk/react\";\nimport { useState } from \"react\";\n\nfunction AdvancedChat() {\n  const [input, setInput] = useState(\"\");\n  const { messages, send, stop, clear, isRunning, error, session } = useAgent({\n    api: \"/api/agent\",\n    system: \"You are a helpful assistant.\",\n    mode: \"fast\",\n    onError: (error) => console.error(\"Error:\", error),\n  });\n\n  const handleSubmit = (e: React.FormEvent) => {\n    e.preventDefault();\n    if (!input.trim() || isRunning) return;\n    send(input);\n    setInput(\"\");\n  };\n\n  return (\n    <div>\n      {/* Session Info */}\n      {session && <div>Session: {session.substring(0, 8)}...</div>}\n\n      {/* Error Display */}\n      {error && <div style={{ color: \"red\" }}>Error: {error.message}</div>}\n\n      {/* Messages */}\n      <div>\n        {messages.map((msg, idx) => (\n          <div key={idx}>\n            <strong>{msg.role}:</strong>\n            {msg.content.map((item, i) => (\n              <div key={i}>\n                {item.type === \"text\" && <div>{item.text}</div>}\n                {item.type === \"thinking\" && (\n                  <div style={{ fontStyle: \"italic\", opacity: 0.7 }}>\n                    💭 {item.text}\n                  </div>\n                )}\n                {item.type === \"tool_use\" && (\n                  <div>\n                    <strong>🔧 Tool:</strong>\n                    <pre>{item.text}</pre>\n                  </div>\n                )}\n              </div>\n            ))}\n          </div>\n        ))}\n      </div>\n\n      {/* Controls */}\n      <div>\n        <button onClick={clear} disabled={messages.length === 0}>\n          Clear\n        </button>\n        {isRunning && <button onClick={stop}>Stop</button>}\n      </div>\n\n      {/* Input */}\n      <form onSubmit={handleSubmit}>\n        <input\n          value={input}\n          onChange={(e) => setInput(e.target.value)}\n          disabled={isRunning}\n          placeholder=\"Type your message...\"\n        />\n        <button type=\"submit\" disabled={isRunning || !input.trim()}>\n          Send\n        </button>\n      </form>\n    </div>\n  );\n}\n```\n\n### Multi-Agent Flow\n\n```tsx\n\"use client\";\n\nimport { useAgent } from \"@agentbase-sdk/react\";\nimport { useState } from \"react\";\n\nfunction MultiAgentChat() {\n  const [input, setInput] = useState(\"\");\n  const { messages, send, isRunning } = useAgent({\n    api: \"/api/agent\",\n    system: \"You classify products and route to specialized agents.\",\n    mode: \"fast\",\n    agents: [\n      {\n        name: \"Personal Care Agent\",\n        description: \"Handles personal care products\",\n      },\n      {\n        name: \"Cosmetics Agent\",\n        description: \"Handles makeup and cosmetics\",\n      },\n    ],\n  });\n\n  const handleSubmit = (e: React.FormEvent) => {\n    e.preventDefault();\n    if (!input.trim() || isRunning) return;\n    send(input);\n    setInput(\"\");\n  };\n\n  return (\n    <div>\n      {messages.map((msg, idx) => (\n        <div key={idx}>\n          <strong>{msg.role}:</strong>\n          {msg.content.map((item, i) => (\n            <div key={i}>\n              {item.type === \"text\" && <div>{item.text}</div>}\n              {item.type === \"transfer\" && (\n                <div style={{ background: \"#f0f0f0\", padding: \"8px\" }}>\n                  🔄 Transferred to: <strong>{item.agent}</strong>\n                  {item.context && <div>Context: {item.context}</div>}\n                </div>\n              )}\n            </div>\n          ))}\n        </div>\n      ))}\n      <form onSubmit={handleSubmit}>\n        <input\n          value={input}\n          onChange={(e) => setInput(e.target.value)}\n          disabled={isRunning}\n          placeholder=\"Type your message...\"\n        />\n        <button type=\"submit\" disabled={isRunning || !input.trim()}>\n          Send\n        </button>\n      </form>\n    </div>\n  );\n}\n```\n\n## Message Structure\n\nMessages have the following structure:\n\n```typescript\ninterface Message {\n  role: \"user\" | \"assistant\";\n  content: MessageContent;\n  createdAt: Date;\n}\n\ntype MessageContent = MessageContentItem[];\n\ninterface MessageContentItem {\n  type: \"text\" | \"thinking\" | \"tool_use\" | \"tool_response\" | \"transfer\";\n  text: string;\n  agent?: string; // For transfer events\n  context?: string; // For transfer events\n}\n```\n\n## Full Example\n\nCheck out the [examples/nextjs](examples/nextjs) directory for a complete Next.js project with:\n\n- Next.js 14 App Router\n- TypeScript\n- Tailwind CSS\n- Server-side API route\n- Full chat interface with all features\n\n## TypeScript\n\nThe library is written in TypeScript and includes full type definitions. All types are exported:\n\n```typescript\nimport type {\n  UseAgentOptions,\n  UseAgentReturn,\n  Message,\n  MessageContent,\n  MessageContentItem,\n  AgentResponse,\n} from \"@agentbase-sdk/react\";\n```\n\n## Development\n\nSee [DEVELOPMENT.md](DEVELOPMENT.md) for detailed development instructions.\n\n```bash\n# Install dependencies\nnpm install\n\n# Build the library\nnpm run build\n\n# Watch mode for development\nnpm run dev\n\n# Type checking\nnpm run typecheck\n```\n\n## License\n\nMIT\n\n## Links\n\n- [Agentbase](https://agentbase.sh)\n- [Documentation](https://docs.agentbase.sh)\n\n## Contributing\n\nContributions are welcome! Please feel free to submit a Pull Request.\n","readmeFilename":"README.md"}