npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@jackchen_me/open-multi-agent

v1.0.1

Published

TypeScript multi-agent framework — one runTeam() call from goal to result. Auto task decomposition, parallel execution. 3 dependencies, deploys anywhere Node.js runs.

Readme

Open Multi-Agent

TypeScript framework for multi-agent orchestration. One runTeam() call from goal to result — the framework decomposes it into tasks, resolves dependencies, and runs agents in parallel.

3 runtime dependencies · 33 source files · Deploys anywhere Node.js runs · Mentioned in Latent Space AI News

GitHub stars license TypeScript coverage

English | 中文

Why Open Multi-Agent?

  • Goal In, Result OutrunTeam(team, "Build a REST API"). A coordinator agent auto-decomposes the goal into a task DAG with dependencies and assignees, runs independent tasks in parallel, and synthesizes the final output. No manual task definitions or graph wiring required.
  • TypeScript-Native — Built for the Node.js ecosystem. npm install, import, run. No Python runtime, no subprocess bridge, no sidecar services. Embed in Express, Next.js, serverless functions, or CI/CD pipelines.
  • Auditable and Lightweight — 3 runtime dependencies (@anthropic-ai/sdk, openai, zod). 33 source files. The entire codebase is readable in an afternoon.
  • Model Agnostic — Claude, GPT, Gemma 4, and local models (Ollama, vLLM, LM Studio, llama.cpp server) in the same team. Swap models per agent via baseURL.
  • Multi-Agent Collaboration — Agents with different roles, tools, and models collaborate through a message bus and shared memory.
  • Structured Output — Add outputSchema (Zod) to any agent. Output is parsed as JSON, validated, and auto-retried once on failure. Access typed results via result.structured.
  • Task Retry — Set maxRetries on tasks for automatic retry with exponential backoff. Failed attempts accumulate token usage for accurate billing.
  • Human-in-the-Loop — Optional onApproval callback on runTasks(). After each batch of tasks completes, your callback decides whether to proceed or abort remaining work.
  • Lifecycle HooksbeforeRun / afterRun on AgentConfig. Intercept the prompt before execution or post-process results after. Throw from either hook to abort.
  • Loop DetectionloopDetection on AgentConfig catches stuck agents repeating the same tool calls or text output. Configurable action: warn (default), terminate, or custom callback.
  • Observability — Optional onTrace callback emits structured spans for every LLM call, tool execution, task, and agent run — with timing, token usage, and a shared runId for correlation. Zero overhead when not subscribed, zero extra dependencies.

Quick Start

Requires Node.js >= 18.

npm install @jackchen_me/open-multi-agent

Set the API key for your provider. Local models via Ollama require no API key — see example 06.

  • ANTHROPIC_API_KEY
  • OPENAI_API_KEY
  • GEMINI_API_KEY
  • GITHUB_TOKEN (for Copilot)

Three agents, one goal — the framework handles the rest:

import { OpenMultiAgent } from '@jackchen_me/open-multi-agent'
import type { AgentConfig } from '@jackchen_me/open-multi-agent'

const architect: AgentConfig = {
  name: 'architect',
  model: 'claude-sonnet-4-6',
  systemPrompt: 'You design clean API contracts and file structures.',
  tools: ['file_write'],
}

const developer: AgentConfig = {
  name: 'developer',
  model: 'claude-sonnet-4-6',
  systemPrompt: 'You implement what the architect designs.',
  tools: ['bash', 'file_read', 'file_write', 'file_edit'],
}

const reviewer: AgentConfig = {
  name: 'reviewer',
  model: 'claude-sonnet-4-6',
  systemPrompt: 'You review code for correctness and clarity.',
  tools: ['file_read', 'grep'],
}

const orchestrator = new OpenMultiAgent({
  defaultModel: 'claude-sonnet-4-6',
  onProgress: (event) => console.log(event.type, event.agent ?? event.task ?? ''),
})

const team = orchestrator.createTeam('api-team', {
  name: 'api-team',
  agents: [architect, developer, reviewer],
  sharedMemory: true,
})

// Describe a goal — the framework breaks it into tasks and orchestrates execution
const result = await orchestrator.runTeam(team, 'Create a REST API for a todo list in /tmp/todo-api/')

console.log(`Success: ${result.success}`)
console.log(`Tokens: ${result.totalTokenUsage.output_tokens} output tokens`)

What happens under the hood:

agent_start coordinator
task_start architect
task_complete architect
task_start developer
task_start developer              // independent tasks run in parallel
task_complete developer
task_start reviewer               // unblocked after implementation
task_complete developer
task_complete reviewer
agent_complete coordinator        // synthesizes final result
Success: true
Tokens: 12847 output tokens

Three Ways to Run

| Mode | Method | When to use | |------|--------|-------------| | Single agent | runAgent() | One agent, one prompt — simplest entry point | | Auto-orchestrated team | runTeam() | Give a goal, framework plans and executes | | Explicit pipeline | runTasks() | You define the task graph and assignments |

Examples

All examples are runnable scripts in examples/. Run any of them with npx tsx:

npx tsx examples/01-single-agent.ts

| Example | What it shows | |---------|---------------| | 01 — Single Agent | runAgent() one-shot, stream() streaming, prompt() multi-turn | | 02 — Team Collaboration | runTeam() auto-orchestration with coordinator pattern | | 03 — Task Pipeline | runTasks() explicit dependency graph (design → implement → test + review) | | 04 — Multi-Model Team | defineTool() custom tools, mixed Anthropic + OpenAI providers, AgentPool | | 05 — Copilot | GitHub Copilot as an LLM provider | | 06 — Local Model | Ollama + Claude in one pipeline via baseURL (works with vLLM, LM Studio, etc.) | | 07 — Fan-Out / Aggregate | runParallel() MapReduce — 3 analysts in parallel, then synthesize | | 08 — Gemma 4 Local | runTasks() + runTeam() with local Gemma 4 via Ollama — zero API cost | | 09 — Structured Output | outputSchema (Zod) on AgentConfig — validated JSON via result.structured | | 10 — Task Retry | maxRetries / retryDelayMs / retryBackoff with task_retry progress events | | 11 — Trace Observability | onTrace callback — structured spans for LLM calls, tools, tasks, and agents | | 12 — Grok | Same as example 02 (runTeam() collaboration) with Grok (XAI_API_KEY) | | 13 — Gemini | Gemini adapter smoke test with gemini-2.5-flash (GEMINI_API_KEY) |

Architecture

┌─────────────────────────────────────────────────────────────────┐
│  OpenMultiAgent (Orchestrator)                                  │
│                                                                 │
│  createTeam()  runTeam()  runTasks()  runAgent()  getStatus()   │
└──────────────────────┬──────────────────────────────────────────┘
                       │
            ┌──────────▼──────────┐
            │  Team               │
            │  - AgentConfig[]    │
            │  - MessageBus       │
            │  - TaskQueue        │
            │  - SharedMemory     │
            └──────────┬──────────┘
                       │
         ┌─────────────┴─────────────┐
         │                           │
┌────────▼──────────┐    ┌───────────▼───────────┐
│  AgentPool        │    │  TaskQueue             │
│  - Semaphore      │    │  - dependency graph    │
│  - runParallel()  │    │  - auto unblock        │
└────────┬──────────┘    │  - cascade failure     │
         │               └───────────────────────┘
┌────────▼──────────┐
│  Agent            │
│  - run()          │    ┌──────────────────────┐
│  - prompt()       │───►│  LLMAdapter          │
│  - stream()       │    │  - AnthropicAdapter  │
└────────┬──────────┘    │  - OpenAIAdapter     │
         │               │  - CopilotAdapter    │
         │               │  - GeminiAdapter     │
         │               │  - GrokAdapter       │
         │               └──────────────────────┘
┌────────▼──────────┐
│  AgentRunner      │    ┌──────────────────────┐
│  - conversation   │───►│  ToolRegistry        │
│    loop           │    │  - defineTool()      │
│  - tool dispatch  │    │  - 5 built-in tools  │
└───────────────────┘    └──────────────────────┘

Built-in Tools

| Tool | Description | |------|-------------| | bash | Execute shell commands. Returns stdout + stderr. Supports timeout and cwd. | | file_read | Read file contents at an absolute path. Supports offset/limit for large files. | | file_write | Write or create a file. Auto-creates parent directories. | | file_edit | Edit a file by replacing an exact string match. | | grep | Search file contents with regex. Uses ripgrep when available, falls back to Node.js. |

Supported Providers

| Provider | Config | Env var | Status | |----------|--------|---------|--------| | Anthropic (Claude) | provider: 'anthropic' | ANTHROPIC_API_KEY | Verified | | OpenAI (GPT) | provider: 'openai' | OPENAI_API_KEY | Verified | | Grok (xAI) | provider: 'grok' | XAI_API_KEY | Verified | | GitHub Copilot | provider: 'copilot' | GITHUB_TOKEN | Verified | | Gemini | provider: 'gemini' | GEMINI_API_KEY | Verified | | Ollama / vLLM / LM Studio | provider: 'openai' + baseURL | — | Verified | | llama.cpp server | provider: 'openai' + baseURL | — | Verified |

Verified local models with tool-calling: Gemma 4 (see example 08).

Any OpenAI-compatible API should work via provider: 'openai' + baseURL (DeepSeek, Groq, Mistral, Qwen, MiniMax, etc.). Grok now has first-class support via provider: 'grok'.

Local Model Tool-Calling

The framework supports tool-calling with local models served by Ollama, vLLM, LM Studio, or llama.cpp. Tool-calling is handled natively by these servers via the OpenAI-compatible API.

Verified models: Gemma 4, Llama 3.1, Qwen 3, Mistral, Phi-4. See the full list at ollama.com/search?c=tools.

Fallback extraction: If a local model returns tool calls as text instead of using the tool_calls wire format (common with thinking models or misconfigured servers), the framework automatically extracts them from the text output.

Timeout: Local inference can be slow. Use timeoutMs on AgentConfig to prevent indefinite hangs:

const localAgent: AgentConfig = {
  name: 'local',
  model: 'llama3.1',
  provider: 'openai',
  baseURL: 'http://localhost:11434/v1',
  apiKey: 'ollama',
  tools: ['bash', 'file_read'],
  timeoutMs: 120_000, // abort after 2 minutes
}

Troubleshooting:

  • Model not calling tools? Ensure it appears in Ollama's Tools category. Not all models support tool-calling.
  • Using Ollama? Update to the latest version (ollama update) — older versions have known tool-calling bugs.
  • Proxy interfering? Use no_proxy=localhost when running against local servers.

LLM Configuration Examples

const grokAgent: AgentConfig = {
  name: 'grok-agent',
  provider: 'grok',
  model: 'grok-4',
  systemPrompt: 'You are a helpful assistant.',
}

(Set your XAI_API_KEY environment variable — no baseURL needed anymore.)

Contributing

Issues, feature requests, and PRs are welcome. Some areas where contributions would be especially valuable:

  • Provider integrations — Verify and document OpenAI-compatible providers (DeepSeek, Groq, Qwen, MiniMax, etc.) via baseURL. See #25. For providers that are NOT OpenAI-compatible (e.g. Gemini), a new LLMAdapter implementation is welcome — the interface requires just two methods: chat() and stream().
  • Examples — Real-world workflows and use cases.
  • Documentation — Guides, tutorials, and API docs.

Author

JackChen — Ex PM (¥100M+ revenue), now indie builder. Follow on X for AI Agent insights.

Contributors

Star History

Translations

Help translate this README — open a PR.

License

MIT