Docs
Tier-1 vs Tier-2
When to use a declarative manifest (Tier-1) vs arbitrary TypeScript in a Vercel Sandbox (Tier-2), and how to publish each.
On this page
Tier-1 — Manifest-only (start here)
A Tier-1 agent is a single YAML manifest. No code. Fully self-serve from the dashboard.
The shape it fits is: form input → optional file ingest → AI call(s) → optional Python compute → rendered report.
That covers a surprising amount of ground: document analyzers, receipt extractors, sentiment classifiers, policy Q&A bots, data enrichment pipelines. If your agent takes something in, runs AI over it, and produces a readable result, Tier-1 is probably the right choice.
Pick Tier-1 when you want to:
- Ship fast without writing code
- Offer a single, focused workflow
- Accept files (PDFs, images, CSVs), text queries, or URLs as input
- Return a rendered HTML/Markdown report or structured JSON
Tier-2 — Code in a Vercel Sandbox
Tier-2 agents are arbitrary TypeScript/JavaScript running in a Vercel Sandbox per request. Pick Tier-2 when you need any of the following:
| Need | Example |
|---|---|
| Multiple HTTP routes | /api/evaluate, /dashboard, /webhook |
| Scheduled jobs | Daily digest, nightly data sync |
| OAuth integrations | Reddit, GitHub, Twitter — acting as the user |
| Outbound channels | Email via Resend, git commits, Slack messages |
| Persistent per-tenant data | Per-user databases or vector stores |
| Custom UI surfaces | More than a single rendered report |
How to publish a Tier-2 agent
1. Start from a Tier-1 agent
You need an apps row first. Create a Tier-1 agent at
/dashboard/apps/new using the slug you want, or have an admin run the
hand-onboard script. The slug in your manifest must match the apps row slug exactly.
2. Develop locally from a template
Clone one of the existing Tier-2 agents in the repo as a starting point (e.g.
agents/saas-idea-validator/). Edit:
src/endpoints.ts— your HTTP handlerssrc/install.ts— tenant install hooksrc/schedules.ts— cron handlers
Update your manifest.yaml for Tier-2:
manifest_version: 2
slug: <your-slug>
runtime: node20
package:
entry: dist/
ui:
routes:
- path: /
method: GET
kind: html
integrations:
- id: gemini
kind: api_key
required: true3. Build and zip
Run the build script:
npx tsx scripts/build-agent-package.ts agents/<your-slug>This compiles and bundles your TypeScript, then produces a .zip ready for upload.
(The CLI also prints a curl command — ignore it, use the dashboard instead.)
4. Upload and activate
Navigate to /dashboard/apps/<your-slug>/publish. Drag the zip onto the
drop zone. The server:
- Extracts
manifest.yaml(ormanifest.json) from the zip. - Validates it against the v2 schema.
- Confirms the slug in the manifest matches the URL slug.
- Uploads the zip to Supabase Storage.
- Inserts an
agent_packagesrow withis_active=false.
The version list below the drop zone shows all uploaded packages. Click Activate to make a version live. Activation:
- Sets the new package to
is_active=trueand all siblings tofalse. - Syncs
agent_schedulesto match the manifest'sschedule[]. - Provisions a per-tenant Postgres schema if
data.mode === 'platform_owned'.
After activation, your agent serves at /user/<slug>/<path> for HTML routes and
/user/<slug>/api/<path> for JSON API routes. The /agents/<slug> catalog listing
points users at the first GET route declared in the manifest.