A windswept bonsai on a floating island

Get to know Cadenya

We’re developers who love to build. We set out to create a yes-code platform that makes building agents feel like the best parts of building software.

Mastra for AI agents (2026)

Mastra

By Cadenya

Mastra is a TypeScript framework for AI agents, and it runs inside a server process that you deploy. Since the Mastra 1.0 release, it covers agents with tools and a model router, observational memory, MCP, evals, and a local dev server. Mastra workflows suspend, resume, and survive a restart through a snapshot in your storage. So in production you run the rest yourself: a server or a deployer, plus Postgres storage (or another adapter) for snapshots and memory. Durable agents and durable execution across several instances add a shared cache and an event bus, such as Redis.

Pick Mastra when your team writes TypeScript and wants agents, workflows, memory, and evals in one framework, on the host you already use. Pick the Mastra platform when you want Mastra to build and host that server and bill it by the CPU hour. And if you’d rather host no server, database, or cache at all, Cadenya is a hosted agent loop with tool approval, conversation state, and context compaction built in, and a coding agent can set it up with no account, in a temporary workspace you claim later. What it offers is at the end.

Every price and limit below comes from each vendor’s own pages, checked on October 29, 2026.

What Mastra does today, since the Mastra 1.0 release

@mastra/core 1.80.0 shipped on October 28, 2026, under Apache-2.0, and folders named ee/ in the repo carry a separate license. It needs Node.js 22.13.0 or later, and Mastra also runs on Bun, Deno, and Cloudflare. Here’s what it includes:

  1. An agent takes instructions, tools, memory, and a "provider/model" string for the model router, then calls tools until the model gives a final answer.
  2. A tool is a createTool() call with an ID, a description, a Zod inputSchema, and an execute function.
  3. A workflow from createWorkflow() chains typed steps with branching, parallel steps, loops, and suspend(), on a built-in engine or on Inngest.
  4. Memory starts with message history, and agents can add observational memory, working memory, and semantic recall, all kept in your storage.
  5. MCP works in both directions: MCPClient connects agents to MCP servers, and MCPServer exposes your agents, tools, and workflows to MCP clients. Both speak the MCP 2026-07-28 revision over stdio or Streamable HTTP.
  6. Evals use scorers from @mastra/evals that grade outputs, usually from 0 to 1, on an agent or a workflow step, with a sampling rate.
  7. The dev server, npx mastra dev, opens Studio at localhost:4111, serves your agents, tools, and workflows under /api, and restarts when a file in src/mastra/ changes.

What about OpenAPI tools? Mastra’s tools page covers tools you write with createTool(), tools from remote MCP servers, and ready-made Connect tools on the Mastra platform for services like Linear, Slack, and GitHub. In Mastra, OpenAPI describes the server you deploy: with server.build.openAPIDocs on, the server publishes a spec of its own routes at /api/openapi.json. TypeScript AI agent frameworks compared covers the 1.0 changes and puts Mastra next to LangGraph.js, the AI SDK, and OpenAI Agents JS.

Mastra observational memory and the model router: what they need and cost

Observational memory runs on model calls of its own: when message history passes 30,000 tokens, an Observer model writes short notes about what happened. When the notes pass 40,000 tokens, a Reflector model condenses them. With the default model: 'auto', both use google/gemini-2.5-flash if GOOGLE_GENERATIVE_AI_API_KEY is set, and otherwise a low-cost model from your main model’s provider.

It also needs one of six storage adapters: @mastra/pg, @mastra/libsql, @mastra/mysql, @mastra/mongodb, @mastra/convex, or @mastra/oracledb. Semantic recall is off by default, and turning it on takes a vector store and an embedder.

The model router needs each provider’s key in an environment variable, such as OPENAI_API_KEY for any openai/ model, and each provider bills you directly. On the Mastra platform, the gateway bills input and output tokens at “Market Rate + 5.5%”, or you bring your own key. Agent memory and context windows compares observational memory with LangGraph and the model APIs.

Mastra deployers, server adapters and Mastra Cloud side by side

Mastra Cloud is now the Mastra platform, with separate Studio and Server products that you deploy with mastra deploy or on a push to GitHub. The framework itself deploys anywhere Node.js runs, in four main ways:

What you deployWhere state livesWhat it costs
Mastra servermastra build writes a Hono server to .mastra/output for a VM, container, or PaaSAny storage adapter, with a local libSQL file kept to one processYour hosting
Server adaptersMastra’s routes inside your own Express, Hono, Fastify, Koa, NestJS, Next.js, Elysia, or TanStack Start appAny storage adapterYour hosting
Vercel, Netlify, and Cloudflare deployersServerless functions on Vercel or Netlify, or a Cloudflare WorkerA database hosted elsewhere, because the filesystem is ephemeralYour plan on that platform
Server on the Mastra platformmastra deploy builds a Docker image, and Mastra runs it at a stable URLHosted storage provisioned on deploy, plus hosted Turso, Neon, or Postgres databasesStarter: $0 with 24 CPU hours, then $0.35 an hour. Teams: $250 a month with 250 CPU hours, then $0.25 an hour
CadenyaNothing: the loop runs on Cadenya, and your app calls an APIOn Cadenya: each objective keeps a durable event logFree for 1,000 loops a month, $49 a month for 50,000, then $0.0015 a loop

On the platform, hosted Postgres includes 5 compute hours, then $0.50 an hour on Starter or $0.40 on Teams. Hosted database storage past 1 GB is $1 a GB-month on Starter or $0.75 on Teams.

Every option runs the agent loop inside a process you deploy. So a deploy can end a turn in the middle. Mastra’s docs say a plain agent.stream() call “can’t resume after its server process exits,” and the client has to retry or reconcile that turn. Durable agents keep the turn, with more infrastructure (two sections down).

Mastra workflows: suspend, resume and Postgres storage

TypeScript AI agent frameworks compared shows the PostgresStore setup.

A suspended Mastra workflow is a snapshot in your storage, keyed by its run ID. It holds each step’s status and output, the suspend and resume payloads, and the retry attempts left. Durable execution for AI agents shows the suspend() and resume() calls.

For production, Mastra’s storage guide asks for a managed database with backups, monitoring, and connection pooling, and it names PostgreSQL as a good default. PostgresStore creates tables such as mastra_workflow_snapshot, mastra_threads, and mastra_messages on first use, and disableInit: true turns that off when your CI runs migrations. And MastraCompositeStore can route storage domains (memory, workflows, scores, schedules, and more) to different backends.

After a restart, your code finds the suspended run in storage and resumes it with Mastra’s state reader:

import { createWorkflowStateReader } from '@mastra/core/workflows'

const workflow = mastra.getWorkflow('testWorkflow')
const state = await workflow.getWorkflowRunById('run-123')

if (state?.status === 'suspended') {
  const reader = createWorkflowStateReader(state)
  const suspendedStep = reader.getSuspendedStep()
  const approvalLabel = reader.getResumeLabel('approve')

  const run = await workflow.createRun({ runId: state.runId })
  await run.resume({
    step: approvalLabel?.stepId ?? suspendedStep?.path,
    resumeData: { approved: true },
    forEachIndex: approvalLabel?.foreachIndex,
  })
}

A running step is a different case. A run holds a storage lease while it works. If a process stops renewing that lease but keeps executing the step, Mastra’s docs warn that recovery “can run that step a second time.” So keep steps with side effects idempotent, and retries and idempotency for agent tool calls shows how.

Mastra durable agents and durable execution in production

A regular Mastra agent’s stream ends with its process. A durable agent runs the loop inside a workflow, publishes each chunk to an event bus, and lets a client reconnect with observe(runId). Mastra ships three kinds:

  1. createDurableAgent() serves local development and single-process servers, with no extra infrastructure.
  2. createEventedAgent() starts the workflow in the background and hands you the chunks through the event bus.
  3. createInngestAgent() from @mastra/inngest runs the loop on Inngest with step memoization and retries.

The defaults keep everything in one process: an in-memory replay cache and a Node.js EventEmitter as the event bus. A second instance needs three shared pieces: a cache such as RedisServerCache from @mastra/redis, a distributed event bus such as RedisStreamsPubSub, and run storage. Recovery across replicas also needs a store with run fencing, like @mastra/pg, @mastra/libsql, or @mastra/mongodb on a replica set, or an event bus whose lease every replica shares.

Crash recovery stays off until you turn it on:

import { Mastra } from '@mastra/core'
import { PostgresStore } from '@mastra/pg'

export const mastra = new Mastra({
  agents: { myAgent: durableAgent },
  storage: new PostgresStore({ connectionString: process.env.DATABASE_URL! }),
  recovery: { durableAgents: 'auto' },
})

With it on, the server re-drives runs stuck in running from their last snapshot when it boots. The docs warn that recovery “can reissue LLM calls (with real cost) and re-execute tool calls,” so tools with side effects need to be idempotent. Splitting workflow steps, schedules, and background tools into worker processes adds a distributed event bus, shared storage, and a network path to the API.

Mastra tool approval and human in the loop after a restart

Mastra pauses a tool call in two ways. requireApproval on a tool, or requireToolApproval on a call, stops it before execute runs, and a tool can also call suspend() inside execute to ask the user for data. TypeScript AI agent frameworks compared shows the approve and decline calls.

In production, the decision often arrives after a page refresh, after a restart, or on another instance. listSuspendedRuns() finds the pending run for a thread in storage:

// In the request handler that receives the user's decision
const { runs } = await agent.listSuspendedRuns({
  threadId: 'thread-123',
  resourceId: 'user-456',
})

const run = runs[0]
const toolCall = run?.toolCalls[0]

if (run && toolCall) {
  let stream
  if (toolCall.requiresApproval) {
    // Suspended by requireApproval: approve or decline the tool call
    stream = await agent.approveToolCall({ runId: run.runId, toolCallId: toolCall.toolCallId })
  } else {
    // Suspended by suspend(): resume with the data the tool asked for
    console.log('Tool asked:', toolCall.suspendPayload)
    stream = await agent.resumeStream({ name: 'San Francisco' }, { runId: run.runId })
  }
  for await (const chunk of stream.textStream) process.stdout.write(chunk)
}

Each run lists its suspended tool calls with requiresApproval, so your handler knows whether to approve or to resume with data. The same lookup works over HTTP as GET /agents/:agentId/suspended-runs. Suspended runs only survive a restart on a persistent storage provider, so this is one more job for your Postgres storage.

Two details matter for a chat or Slack agent. An approval request from a subagent goes up to the supervisor, so you answer it once, at the top. And autoResumeSuspendedTools: true resumes a suspend() tool from the user’s next message on the same thread, but it never approves a requireApproval tool. Human-in-the-loop approvals for AI agents compares how other frameworks pause and resume a tool call.

What does Cadenya offer that Mastra doesn’t?

Mastra gives you the agent loop as a library, and you run the server and the database around it, plus a cache and an event bus once you scale out. Cadenya runs the loop for you, with tool approval, conversation state, and context compaction built in, and nothing to host. Use it in place of a Mastra server. Here’s what that covers:

  1. There’s nothing else to run. You add no Postgres for snapshots, no Redis cache or event bus, no worker, no Inngest, and no Mastra server to build. The loop runs on Cadenya and your app stays a stateless web tier, so your deploys and restarts never touch a running objective.
  2. There’s no server to license. Cadenya hosts the engine, so there’s no ee/ folder to check, and the TypeScript, Python, Ruby, and Go SDKs are Apache-2.0.
  3. You keep no old code alive while runs wait. Cadenya picks the variation once, when it creates the objective, and the objective keeps that configuration snapshot even if you edit the variation later.
  4. Approvals wait outside your process. When a tool needs approval, Cadenya parks the loop on toolApprovalRequested, and several tool calls can wait at once. Your backend answers through the API or a webhook handler, with no run state in your app.
  5. The SDKs ship often. All four SDKs are at 1.9.0, and the TypeScript SDK has shipped 113 versions since April 2026. It runs on Node.js 18, where Mastra’s packages ask for 22.13.0.
  6. The price fits in one line. Free covers 1,000 loops a month with no card, and Growth is $49 a month for 50,000 loops, then $0.0015 a loop. A loop is one LLM request made during an objective, so there are no CPU hours or database rows to estimate.
  7. The agent loop is already written. Cadenya calls the model, runs the tools, streams its events over server-sent events, and compacts the context window as a conversation grows. Each objective keeps a durable event log, and a waiting objective resumes with its history when your user sends a Continue message.
  8. Tools come from your OpenAPI spec or an MCP server. Point a tool set at an OpenAPI 3 document, and Cadenya reads every operation and checks a URL source for changes each hour. A tool set can also take an MCP server’s URL as its source.
  9. The approval screen comes included. The React UI kit’s ConversationsPanel supplies the conversation list, message thread, composer, tool approvals, and live event stream. A denial carries a memo that steers the agent (“Use the read-only lookup tool instead.”).
  10. You pick any model from your own provider. The model is a setting on a variation, chosen from the AI providers in your workspace, and you pay your provider directly. Your code points at the agent, so a model change happens in a variation, not in a deploy.

How objectives work covers the event log, approvals, and Continue, and the free plan needs no card.

No account yet? A coding agent can create a temporary workspace with cadenya workspaces create --temporary, run its first objectives there, and hand you a link to claim it, as auth.md explains. To create an account, sign up at app.cadenya.com/signup, then copy your API key from the API keys page at app.cadenya.com/account/apiKeys.

Grow wherever AI goes next.

Start shipping agents that are equipped to evolve.

A pine bonsai overlooking a mountain lake