# BaseAI: a TypeScript framework for local-first AI pipes, and why it was archived

> BaseAI lets you define an AI agent as a typed config file, run it against a local dev server, and stream the output into a Node app. It is archived, and its own README explains why the maintainers moved on.

**CommandCodeAI/BaseAI** — BaseAI — The Web AI Framework. The easiest way to build serverless autonomous AI agents with memory. Start building local-first, agentic pipes, tools, and memory. Deploy serverless with one command.

- Repository: https://github.com/CommandCodeAI/BaseAI
- Website: https://BaseAI.dev
- Stars: 1,281 · Forks: 112
- Language: TypeScript
- License: NOASSERTION
- Published: 2026-09-10 · Updated: 2026-09-10 · Language: en
- Canonical page: https://hysenlabs.com/projects/commandcodeai-baseai

## What BaseAI was trying to solve, and who it was for

Building an AI feature usually starts as a prompt in a scratch file and ends as a mess of provider SDK calls scattered through a codebase. BaseAI's answer was to make the agent itself a file. You describe a pipe, which is the project's word for a custom-built AI agent exposed as an API, in a TypeScript module inside a baseai directory, and the framework handles the run, the streaming and the tool wiring.

The target reader is a TypeScript developer who wants to iterate on an agent locally before deploying it. The README frames the workflow as local-first: you develop pipes on your machine with agentic tools and memory, then deploy serverless with one command. The repository layout backs that up, with packages/ for the framework itself, apps/ for the site, and examples/ split into agents, astro, nextjs, nodejs and remix.

What makes it interesting in hindsight is the framing, not the feature list. The README now opens with a note saying BaseAI is archived in favour of Langbase AI Primitives, and gives a reason: "the more we built BaseAI the more we realized frameworks are a bad idea in AI engineering." That is an unusually direct statement from a maintainer about their own project, and it should shape how you read everything below.

## How a BaseAI pipe actually runs

The mechanism is small enough to hold in your head. A pipe is a function returning an object typed as PipeI. That object carries the API key, the model string in provider:model form such as openai:gpt-4o-mini, sampling parameters, a messages array with at least a system message, and three arrays named variables, memory and tools.

At runtime you construct a Pipe from that config and call run with a messages array. The return value includes a stream, and getRunner wraps it so you can attach listeners for connect, content, end and error. The content listener fires per chunk, which is why the README's example writes each chunk straight to stdout with process.stdout.write.

The config object is where the framework's opinions live. store: true means the run is persisted, moderate: true means moderation is applied, and parallel_tool_calls: true allows multiple tools in one turn. Because it is a plain TypeScript module, you can compute any field at import time, which is a real advantage over a JSON or YAML agent definition. The trade-off is that the config is code, so it can do anything, including read environment variables at module scope. The README's own example does exactly that with process.env.LANGBASE_API_KEY!.

## Installing BaseAI and running your first pipe

The README gives a five-step path. First, initialize inside your existing app. This creates a baseai directory containing baseai.config.ts plus memory, pipes and tools subdirectories.

```bash
npx baseai@latest init
```

Second, add keys to .env. The README marks the Langbase key as needed in both production and local env files, and the provider keys as local only, needed for local pipe runs. Note the comment that all API keys are server side only.

```bash
LANGBASE_API_KEY=
OPENAI_API_KEY=
ANTHROPIC_API_KEY=
```

Third, scaffold a pipe. The command asks for name, description and other details step by step, then writes the pipe into baseai/pipes.

```bash
npx baseai@latest pipe
```

Fourth, call it from your app. The README's index.ts imports the pipe config, constructs a Pipe, runs it with a user message, and attaches a runner.

```ts
import { Pipe, getRunner } from '@baseai/core';
import pipeSummarizer from './baseai/pipes/summary';

const pipe = new Pipe(pipeSummarizer());

const { stream } = await pipe.run({
  messages: [{ role: 'user', content: userMsg }],
  stream: true,
});

const runner = getRunner(stream);
runner.on('content', content => process.stdout.write(content));
```

Fifth, start the local server in one terminal and the script in another. The README states you should see the streamed summary printed between a "Stream started." line and a "Stream ended." line.

```bash
npx baseai@latest dev
npx tsx index.ts
```

One detail worth flagging: the README's sample output contains em dashes and bold markdown that the source prompt did not, which is a reminder that you are looking at model output, not a fixture.

## Where BaseAI stops being the right tool

The strongest limitation is stated by the project itself. The README's opening line says BaseAI is archived in favour of Langbase AI Primitives, and the argument is that frameworks become blockers in a fast-moving space. If you adopt an archived framework, you own every future provider change, every SDK break and every security patch yourself. The last push to the repository was on 2026-05-16, so there is no signal of ongoing work.

There is a second constraint that is easy to miss. The local dev workflow depends on a BaseAI server process and on a LANGBASE_API_KEY, even though you are running against OpenAI or Anthropic keys locally. That means the local-first story still routes through a hosted account. If your requirement is a fully offline agent runtime, this is not it.

The third is the shape of the abstraction. A pipe config bundles model choice, sampling, system prompt, memory and tools into one object. That is convenient for a single agent and awkward when you want to share a system prompt across twelve agents with different models, or swap providers per request. You end up writing TypeScript that generates configs, which is the framework leaking.

Finally, the licence field on the repository is NOASSERTION even though the root package.json declares Apache-2.0. That mismatch is worth resolving before you depend on it, and it is not something this article can settle.

## BaseAI versus calling the provider SDK directly

The obvious alternative is no framework at all: import the OpenAI or Anthropic SDK in your own module, keep the system prompt in a constant, and stream the response yourself. The difference in approach is where the agent definition lives. BaseAI puts it in a typed object with a fixed set of fields and a CLI that scaffolds and runs it. The direct approach puts it in whatever structure you already use for configuration, which for most TypeScript teams is a module plus environment variables.

What you lose by going direct is the local dev server and the runner abstraction. The getRunner event model, with connect, content, end and error, is a genuinely small surface, and reimplementing it against a provider stream is not much work, but it is work. What you gain is that nothing in your dependency tree can be archived out from under you.

A middle path is the one the README itself recommends: use AI primitives exposed as APIs with TypeScript and Python SDKs, and let a coding agent assemble the framework you actually need. That is the maintainers' position, and given that they wrote BaseAI, it is a considered one rather than a deflection.

## Maintenance, upgrades and the licence question

Treat BaseAI as a read-only reference. The repository is archived, so there is no upgrade path to plan for and no release cadence to track. The monorepo uses pnpm workspaces and turbo, with changesets for versioning, which tells you how releases were cut while the project was alive, but that machinery is now idle.

If you already have BaseAI in a project, the practical question is what the pipes depend on. A pipe config hardcodes a model string like openai:gpt-4o-mini, so a provider deprecation is a code change in your repository, not a dependency bump. The same applies to the PipeI type: if @baseai/core stops receiving updates, your configs are pinned to whatever shape the installed version expects.

On licensing, the root package.json declares Apache-2.0 while the repository's licence field reads NOASSERTION. Those two signals disagree, and the resolution matters if you plan to redistribute the code or ship it inside a product. This is a factual discrepancy to raise with whoever handles licensing on your side, not something to assume either way.

## Conclusion

BaseAI is worth reading if you want a concrete example of how to shape an AI agent as a typed config file plus a streaming runner, and the examples directory under examples/nodejs, examples/nextjs and examples/remix shows that pattern in several app shapes. Do not start a new production project on it: the README opens by saying BaseAI is archived in favour of Langbase AI Primitives, and the last push was on 2026-05-16. Before you copy anything from it, verify two things yourself: whether the @baseai/core version you install still matches the PipeI shape shown in the README, and whether the LANGBASE_API_KEY path through baseai dev is something you want in your dependency graph at all.

## FAQ

### What does BaseAI do?

It is a TypeScript-first framework for building AI agents, which it calls pipes, with memory and tools. You define a pipe as a config object, run it locally with the BaseAI dev server, and stream the output into your app. The README states it is now archived in favour of Langbase AI Primitives.

### What is BaseAI?

BaseAI describes itself as the web AI framework for building serverless, composable AI agents with memory and tools. Its workflow centres on a baseai directory containing baseai.config.ts plus memory, pipes and tools subdirectories. The repository is archived and the last push was on 2026-05-16.

### How do I install BaseAI in an existing project?

Run npx baseai@latest init inside your app, then add your keys to .env, create an agent with npx baseai@latest pipe, and start the local server with npx baseai@latest dev. The README notes that provider keys are needed for local pipe runs while the Langbase key is needed in both local and production env files.

### Is BaseAI still maintained?

No. The README opens by saying BaseAI is archived in favour of Langbase AI Primitives, and the repository's last push was on 2026-05-16. The stated reason is that the maintainers came to see frameworks as blockers in AI engineering.

### What licence is BaseAI released under?

The signals conflict. The root package.json declares Apache-2.0, while the repository's licence field reads NOASSERTION. Resolve that discrepancy before depending on the code.

## Sources

- [CommandCodeAI/BaseAI on GitHub](https://github.com/CommandCodeAI/BaseAI)
- [Issues](https://github.com/CommandCodeAI/BaseAI/issues)
- [Project website](https://BaseAI.dev)
- [README](https://github.com/CommandCodeAI/BaseAI/blob/main/README.md)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/commandcodeai-baseai
