A small Laravel chat application that demonstrates the
twdnhfr/laravel-deepagents
package — a deep-agent harness for the Laravel AI SDK with planning, sub-agents,
persistent memory, human-in-the-loop approval and automatic context management.
It's a single-page chat that shows the package's key features working together in a real request/response flow.
- Multi-turn conversations — the agent run state is persisted in the session
and continued on each message (
DeepAgent::continue()). - Tools — four demo tools the model can call:
get_weather,roll_dice,delete_recordsandfetch_report(seeapp/Tools). - Planning —
withTodos()gives the model thewrite_todostool; the sidebar renders its plan live fromRunState->todosas steps move through pending → in progress → completed. - Sub-agents — a
report-analystregistered withsubAgent(): the parent delegates report analysis via thetasktool, the sub-agent works in its own isolated context window (inheriting the parent's backend) and only its final answer returns to the conversation. - Persistent memory —
memory('memory/profile.md')loads a profile from the backend into the system prompt at the start of every conversation; the agent updates it viawrite_artifact. Reload the page (fresh conversation) and ask "What do you know about me?" — the history is gone, the memory isn't. - Human-in-the-loop with all three decisions — the destructive
delete_recordstool is gated withrequireApproval(); the run suspends and the UI shows the pending call. Approve runs it as requested, edit the arguments inline before approving (RunState::edit()— the call runs with your corrected input), or reject with an optional reason (RunState::reject()) that goes back to the model as the tool's result, so it reacts in-conversation instead of the turn being dropped. - Persistent artifacts & offloading — large tool outputs are clipped with
offloadLargeToolResults()and stored as run-scoped artifacts via theDatabaseBackend, so the model can read the full text back on demand withread_artifact. - Context compaction —
summarize()(with a deliberately low budget here) compacts older history into a summary once it grows too large; the UI marks the moment with a 🗜️ line, and the conversation keeps its context. - Tool trace — each reply shows which tools ran with their arguments and results.
The wiring lives almost entirely in routes/web.php, which is
heavily commented as the reference for how to use the package.
- PHP 8.3+
- Composer
- Bun (or npm — adjust the commands accordingly)
- An OpenRouter API key
git clone https://github.com/twdnhfr/deepagents-chat.git
cd deepagents-chat
make install # .env, dependencies, app key, SQLite DB, migrationsThen add your OpenRouter key to .env:
OPENROUTER_API_KEY=sk-or-...
# OPENROUTER_MODEL=openai/gpt-5.4-nano # optional, this is the defaultStart the dev server (Laravel + Vite):
make devand open the URL it prints (e.g. http://localhost:8000).
The demo uses SQLite out of the box for zero configuration. To use MySQL or Postgres instead, change the
DB_*values in.env.
Manual setup without make
cp .env.example .env
composer install
bun install
bun run build
php artisan key:generate
touch database/database.sqlite
php artisan migrate
php artisan serve # in one terminal
bun run dev # in anothermake test # or: php artisan testThe MIT License (MIT). See LICENSE.