Skip to main content

Command Palette

Search for a command to run...

Introducing InAppAI: Open-Source AI Agents for React

Add AI agents to your SaaS that take action, not just answer questions. Learn how Tools, Context, and Agents work together.

Published
4 min readView as Markdown
Introducing InAppAI: Open-Source AI Agents for React

SaaS users in 2026 don't want AI that answers questions. They want AI that does things for them.

"Schedule a meeting with John for Tuesday" "Generate a report for Q4 sales" "Add a task to follow up with the client"

Not a walkthrough. Not a help article. Just done.

This is the difference between a chatbot and an agent:

  • Chatbot → Tells users how to do something

  • Agent → Does it for them

If you're building a SaaS product, this post shows you how to add agents that take real action in your app.

What SaaS Teams Get From Agents

Before diving into code, here's why this matters for your product:

Faster onboarding — New users describe what they want in plain language. The agent gets them there without learning your UI first.

Higher feature adoption — Complex features that users never discover become simple requests. "Show me overdue invoices" is easier than navigating three menus.

Less support load — When users can say "update my billing address" and it just happens, they don't need to open tickets.

Real differentiation — "AI-powered" is baseline now. "AI that operates for you" is what stands out.

How It Works: Agents, Context, and Tools

InAppAI is built on three concepts:

ConceptWhat it does
AgentServer-side AI config (provider, model, knowledge base)
ContextReal-time app state the agent can see
ToolsFunctions the agent can execute

Here's how they connect:

User: "Add a high-priority task for Monday"
          ↓
    ┌─────────────┐
    │    AGENT    │  ← Understands intent
    └─────────────┘
          ↓
    ┌─────────────┐
    │   CONTEXT   │  ← Sees current tasks, user info, filters
    └─────────────┘
          ↓
    ┌─────────────┐
    │    TOOLS    │  ← Calls addTask({ text: "...", priority: "high" })
    └─────────────┘
          ↓
    Task created, UI updates

Getting Started

npm install @inappai/react
import { InAppAI } from '@inappai/react';

function App() {
  const [messages, setMessages] = useState([]);

  return (
    <InAppAI
      agentId="your-agent-id"
      messages={messages}
      onMessagesChange={setMessages}
      tools={tools}
      context={() => appState}
      displayMode="popup"
    />
  );
}

The agentId connects to your server-side config. Everything else—provider selection, rate limiting, knowledge base—is handled there.

Defining Tools

Tools are functions your agent can call. Each tool has a name, description, parameters (JSON Schema), and a handler that runs client-side:

const tools = [
  {
    name: 'createTask',
    description: 'Create a new task when the user wants to add something to their list',
    parameters: {
      type: 'object',
      properties: {
        text: { type: 'string', description: 'Task description' },
        priority: {
          type: 'string',
          enum: ['low', 'medium', 'high'],
          description: 'Priority level'
        },
        dueDate: { type: 'string', description: 'Due date (ISO format)' },
      },
      required: ['text'],
    },
    handler: async ({ text, priority = 'medium', dueDate }) => {
      const newTask = await api.createTask({ text, priority, dueDate });
      setTasks(prev => [...prev, newTask]);
      return { success: true, task: newTask };
    },
  },
  {
    name: 'listTasks',
    description: 'Get tasks, optionally filtered by status or priority',
    parameters: {
      type: 'object',
      properties: {
        status: { type: 'string', enum: ['all', 'active', 'completed'] },
        priority: { type: 'string', enum: ['low', 'medium', 'high'] },
      },
    },
    handler: async ({ status = 'all', priority }) => {
      let filtered = tasks;
      if (status === 'active') filtered = tasks.filter(t => !t.completed);
      if (status === 'completed') filtered = tasks.filter(t => t.completed);
      if (priority) filtered = filtered.filter(t => t.priority === priority);
      return { tasks: filtered, count: filtered.length };
    },
  },
];

The agent reads the descriptions and parameters to decide which tool to call. The handler runs in your React component with full access to state and APIs.

Providing Context

Context lets the agent see your app state. Pass it as a function so the agent always gets fresh data—even after tools execute:

<InAppAI
  // ...
  context={() => ({
    tasks: tasks.map(t => ({ id: t.id, text: t.text, completed: t.completed })),
    user: { name: user.name, plan: user.plan },
    currentView: 'dashboard',
  })}
/>

When the agent creates a task, it calls context() again to see the updated list. This lets it confirm: "Done! I've added 'Review Q4 budget' to your tasks."

Why Server-Side Agents?

The agent config lives on your server, not in the client. This gives you:

  • Security — API keys never touch the browser

  • Flexibility — Switch from GPT-4 to Claude without redeploying

  • Control — Add rate limits per user or tenant

  • Knowledge — Enable RAG with your docs without client complexity

Your frontend just passes the agentId. Everything else is configured server-side.

Real Examples

With tools and context set up, users can say:

  • "Add a high-priority task for Monday"

  • "What tasks are overdue?"

  • "Mark the budget review as done"

  • "Show me all high-priority items"

The agent understands intent, sees the current state, picks the right tool, and executes it.

Get Started

Try the demo: react-demo.inappai.com

Read the docs: inappai.com/docs

Star on GitHub: github.com/inappai/react

InAppAI is MIT-licensed. You don't need to redesign your product—add the component, define your tools, and start experimenting.


Questions? Drop a comment or open an issue on GitHub.