AI Study Assistant - AG-UI Demo

November 19, 2025 ยท View on GitHub

This repository demonstrates how to build a study assistant agent using Microsoft Agent Framework, AG-UI Protocol, and CopilotKit.

This project was created as part of a blog post exploring AG-UI (Agent-User Interaction Protocol) - a game-changer for agent-user interactions.

๐Ÿ“– Blog Post

Read the full article: A Game-Changer for Agent-User Interactions: AG-UI Protocol

What Is AG-UI?

AG-UI is an open, lightweight, event-based protocol designed to standardize how AI agents connect to user-facing applications. It provides a consistent and flexible way to handle interactions between the agent backend and the frontend user interface.

How AG-UI Fits in the Agentic Stack

  • MCP (Model Context Protocol): Connects agents to external tools
  • A2A (Agent-to-Agent Protocol): Enables agents to communicate with each other
  • AG-UI (Agent-User Interaction Protocol): Bridges agents to user interfaces

Simply put: MCP gives agents tools, A2A lets them talk to each other, and AG-UI lets them talk to users.

Project Overview

This demo implements a Study Assistant agent that helps students plan study schedules based on their exam timetable. It showcases:

  • โœ… Backend Tool Calling: Server-side agent tools (e.g., get_academic_calendar)
  • โœ… Frontend Actions: Client-side tools (e.g., setThemeColor)
  • โœ… Generative UI: Dynamic rendering of tool execution status
  • โœ… Real-time Communication: Event-driven agent-to-UI interaction

Prerequisites

  • Azure OpenAI Account (or GitHub Models API)
    • For Azure OpenAI: Set up your endpoint and deployment
    • For GitHub Models: Retrieve token from these instructions
    • Or generate via gh auth token (requires GitHub CLI)
  • .NET 9.0 SDK
    • Download directly
    • macOS/Linux
      • Install via Homebrew (brew install dotnet@9) or

      • Install via curl install script
        curl -sSL https://dot.net/v1/dotnet-install.sh | bash /dev/stdin --channel 9.0
        export PATH="$HOME/.dotnet:$PATH"
        
    • Windows
  • Node.js 20+
    • Download directly
    • macOS/Linux
      • Install via Homebrew (brew install node@24) or

      • Install via curl install script
        # Download and install nvm:
        curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.3/install.sh | bash
        
        # in lieu of restarting the shell
        \. "$HOME/.nvm/nvm.sh"
        
        # Download and install Node.js:
        nvm install 24
        
    • Windows
  • Any of the following package managers:

Note: This repository ignores lock files (package-lock.json, yarn.lock, pnpm-lock.yaml, bun.lockb) to avoid conflicts between different package managers. Each developer should generate their own lock file using their preferred package manager. After that, make sure to delete it from the .gitignore.

Getting Started

  1. Install dependencies using your preferred package manager:

    # Using pnpm (recommended)
    pnpm install
    
    # Using npm
    npm install
    
    # Using yarn
    yarn install
    
    # Using bun
    bun install
    

    Note: This will automatically setup the C# agent as well (restore NuGet packages).

    If you have manual issues, you can run:

    npm run install:agent
    
  2. Set up your GitHub token for GitHub Models:

    First, get your GitHub token:

    gh auth token
    

    Then, navigate to the agent directory and set it as a user secret:

    cd agent
    dotnet user-secrets set GitHubToken "<your-token>"
    cd ..
    

    Or set it in one command:

    cd agent; dotnet user-secrets set GitHubToken "$(gh auth token)"; cd ..
    
  3. Start the development server:

    # Using pnpm
    pnpm dev
    
    # Using npm
    npm run dev
    
    # Using yarn
    yarn dev
    
    # Using bun
    bun run dev
    

    This will start both the Next.js UI (port 3000) and C# agent server (port 8000) concurrently.

Available Scripts

The following scripts can also be run using your preferred package manager:

  • dev - Starts both UI and agent servers in development mode
  • dev:debug - Starts development servers with debug logging enabled
  • dev:ui - Starts only the Next.js UI server
  • dev:agent - Starts only the C# agent server
  • build - Builds the Next.js application for production
  • start - Starts the production server
  • lint - Runs ESLint for code linting
  • install:agent - Restores NuGet packages for the C# agent

Project Structure

โ”œโ”€โ”€ agent/                  # C# Agent (Microsoft Agent Framework)
โ”‚   โ”œโ”€โ”€ Program.cs         # Main agent implementation with AG-UI tools
โ”‚   โ”œโ”€โ”€ ProverbsAgent.csproj  # .NET project file
โ”‚   โ””โ”€โ”€ Properties/        # Configuration (launch settings)
โ”œโ”€โ”€ src/
โ”‚   โ”œโ”€โ”€ app/
โ”‚   โ”‚   โ”œโ”€โ”€ page.tsx      # Main UI with CopilotKit sidebar
โ”‚   โ”‚   โ”œโ”€โ”€ layout.tsx    # CopilotKit provider setup
โ”‚   โ”‚   โ””โ”€โ”€ api/
โ”‚   โ”‚       โ””โ”€โ”€ copilotkit/
โ”‚   โ”‚           โ””โ”€โ”€ route.ts  # AG-UI integration endpoint
โ”‚   โ”œโ”€โ”€ components/       
โ”‚   โ”‚   โ””โ”€โ”€ timetable.tsx # Timetable card component
โ”‚   โ””โ”€โ”€ lib/             # Types and utilities
โ””โ”€โ”€ scripts/             # Helper scripts for agent setup/run

Architecture

Server-Side (AG-UI Server)

The agent is built using Microsoft Agent Framework and exposed via the AG-UI protocol:

// Define a backend tool
var GetAcademicCalendar = AIFunctionFactory.Create(
    ([Description("Get academic calendar for the semester")] string semester) => 
        $"The academic calendar for {semester} includes midterms on March 15 and finals on May 20.",
    name: "get_academic_calendar",
    description: "Fetch the academic calendar for the specified semester.");

// Create AI agent with tool
AIAgent agent = chatClient.AsIChatClient().CreateAIAgent(
    name: "AGUIAssistant",
    instructions: "You are a helpful assistant named Bhidu.",
    tools: new[] { GetAcademicCalendar });

// Expose via AG-UI in one line!
app.MapAGUI("/", agent);

Client-Side (AG-UI Client)

The frontend connects to the AG-UI server using CopilotKit:

// Connect to AG-UI server
const runtime = new CopilotRuntime({
  agents: {
    my_agent: new HttpAgent({ url: "http://localhost:8000/" }),
  },
});

// Render tool execution status
useRenderToolCall({
  name: "get_academic_calendar",
  render: ({ status, args, result }) => {
    return (
      <div>
        {status !== "complete" && "Calling get_academic_calendar API..."}
        {status === "complete" && `Called API for ${args.semester}`}
        {result && <TimeTableCard timetable={result} />}
      </div>
    );
  },
});

Features Demonstrated

This demo showcases key AG-UI protocol features:

  • ๏ฟฝ๏ธ Backend Tools: Server-side agent tools (get_academic_calendar) executed on the backend
  • ๐ŸŽจ Frontend Actions: Client-side tools (setThemeColor) executed in the browser
  • ๐Ÿ“Š Generative UI: Dynamic rendering of tool execution with useRenderToolCall
  • ๏ฟฝ Agentic Chat: Natural language interface with real-time tool calling
  • โšก Event-Driven: Real-time bi-directional communication between agent and UI

Why AG-UI Matters

Before AG-UI: Developers had to build custom UI layers for every agent, handling tool execution, streaming, and state management manually.

With AG-UI: All modern agent capabilities (long-running queries, tool calling, multi-turn conversations, memory, token streaming) work out of the box with a standardized protocol.

๐Ÿ“š Documentation & References

๐ŸŽฏ Key Takeaway

With Microsoft Agent Framework and AG-UI, developers finally have a simple, standardized way to bring intelligent agents into real-time, interactive applications. It's fast, flexible, and framework-agnostic - the missing UI link in the agentic ecosystem.

Blog Context

This repository accompanies a blog post that explores:

  1. The Agentic Protocol Triad:

    • MCP (Model Context Protocol) - gives agents tools
    • A2A (Agent-to-Agent Protocol) - lets agents talk to each other
    • AG-UI (Agent-User Interaction Protocol) - lets agents talk to users
  2. Step-by-Step Implementation:

    • Server-side: Creating an AI agent with Microsoft Agent Framework
    • Server-side: Exposing the agent via AG-UI in one line (app.MapAGUI("/", agent))
    • Client-side: Connecting to the agent using CopilotKit
    • Client-side: Rendering tool execution status with useRenderToolCall
  3. Why It Matters:

    • Eliminates the need to build custom UI layers for every agent
    • Standardizes agent-to-UI communication
    • Works with any transport (SSE, WebSockets, webhooks)
    • Framework-agnostic approach

Contributing

This repository serves as a demonstration for the blog post. Feel free to:

  • Fork and experiment with your own agent implementations
  • Submit issues for bugs or clarifications
  • Share your own AG-UI experiences

Acknowledgments

Special thanks to:

License

This project is licensed under the MIT License - see the LICENSE file for details.

Troubleshooting

Agent Connection Issues

If you see "I'm having trouble connecting to my tools", make sure:

  1. The C# agent is running on port 8000
  2. Your GitHub token is set correctly via user secrets
  3. Both servers started successfully (check terminal output)

.NET SDK Not Installed

If you don't have .NET 9.0 installed:

macOS/Linux (Homebrew):

brew install dotnet@9
dotnet --version

macOS/Linux (Install Script):

curl -sSL https://dot.net/v1/dotnet-install.sh | bash /dev/stdin --channel 9.0
export PATH="$HOME/.dotnet:$PATH"

Windows (WinGet):

winget install --id=Microsoft.DotNet.SDK.9 -e

Windows/macOS (Direct Download):

.NET SDK Issues

If you encounter .NET-related errors:

# Verify .NET SDK is installed
dotnet --version  # Should be 9.0.x or higher

# Restore packages manually
cd agent
dotnet restore
dotnet run

GitHub Token Issues

If the agent fails to start with "GitHubToken not found":

cd agent
dotnet user-secrets set GitHubToken "$(gh auth token)"

Or manually:

# Get your token
gh auth token

# Set it as a user secret
cd agent
dotnet user-secrets set GitHubToken "YOUR_TOKEN_HERE"

Port Conflicts

If port 8000 is already in use, you can change it in:

  • agent/Properties/launchSettings.json - Update applicationUrl
  • src/app/api/copilotkit/route.ts - Update the HttpAgent URL