Skip to main content
This guide covers migrating from any v1 agent (forest-express-sequelize, forest-express-mongoose, forest-rails, django-forestadmin v1) to the current generation. The migration unlocks workflows, the MCP server for AI agents, multi-datasource, decision traces, and everything Forest has shipped since the original admin-panel era. Most teams complete the migration in 1-2 days with zero downtime.

What v2 changes

The new generation is a rebuilt agent with a cleaner, more composable customization API. The biggest changes you’ll see during migration:
  • Multi-datasource is native. A single agent can connect to multiple databases and APIs.
  • Customization happens via a fluent API on collections. agent.customizeCollection('users', users => users.addField(...)).
  • Computed fields declare their dependencies explicitly. dependencies: ['firstName', 'lastName'].
  • Relationships are first-class. Many-to-one, one-to-many, many-to-many, and external relations replace most legacy “smart relationships”.
  • Routes are no longer overridden directly. Most v1 route overrides become hooks or computed fields.

Before you start

1

Upgrade the legacy agent

Releases of @forestadmin/forestadmin-client before 1.36.2 cache a failed permission lookup for 15 minutes, so a slow response during one of the migration’s restarts can lock users out of an environment.
2

Decide where the new agent will run

In-app or standalone: settle it before writing code. See Deployment options.
3

Migrate into a new environment, not a new project

Layouts, segments, workspaces, roles and teams belong to the project and don’t carry over to another one. Add an environment to your existing project (Project Settings → Environments → Add) and point it at the new agent.
4

Inventory your customizations

List every Smart Action, Smart Field, Smart Relationship, Smart Segment, and route override in your current project. Each step page below covers one of these surfaces.
5

Back up your project

Export your current Forest project layout. While the layout is preserved across the agent swap, having a baseline is good practice.
6

Plan parallel running

Both agents can run side by side during migration.
Running both agents in one process is not recommended: every deploy of the new agent would also restart the legacy one you are relying on. If they share a host, they also need separate paths — see Running two agents at once.

Migration steps

1

Install the new agent

Install the new packages alongside your existing ones, and run the new agent in its own process, on a different port.
2

Migrate datasources

Re-declare your data sources using the new datasource API. See Datasources.
3

Match the old field names

Your layout refers to every field by name, so the new agent must expose the same names as the old one. A mismatch raises no error: the configuration on that field just disappears. Check this before migrating any customization — see Datasources.
4

Migrate Smart Actions

Convert each Smart Action to the new addAction API. See Smart Actions.
5

Migrate Smart Fields

Convert computed fields to addField with explicit dependencies. See Smart Fields.
6

Migrate Smart Relationships

Convert legacy smart relationships to native relations or external relations. See Smart Relationships.
7

Migrate Smart Segments

Update segments to use condition trees instead of ORM-specific queries. See Smart Segments.
8

Rehearse against your real layout

A branch starts from production’s layout, so you can test the new agent against it without touching production:
Naming mistakes show up here as missing columns or broken actions. This is usually enough.
9

Populate a shared test environment (optional)

Only if your team needs a shared pre-production environment. A new environment in the same project inherits production’s layout, but not its role permissions. Production runs the legacy agent and node-test the new one, so their schemas differ and copying permissions across environments refuses them. Move the permissions through a file instead, once the new agent has started on node-test:
  1. Back up the target, so you can re-apply it to undo: forest roles:export --env node-test --output node-test-backup.csv
  2. Export production: forest roles:export --env production --output roles.csv
  3. Rename the columns to the new agent’s names. The file has one column per collection permission and Smart Action grant, headed collection:permission or collection:action:grant. If you kept the legacy names, there’s nothing to rename. Drop the columns of collections the new agent doesn’t expose: a column naming a collection the environment doesn’t have fails that role’s update.
  4. Apply it: forest roles:apply --env node-test roles.csv. It lists the changes and asks before applying them.
Smart Action conditions aren’t carried over. Set them again on the new environment.
10

Test side by side

Run both agents simultaneously. Point the test environment at the new agent and verify behavior matches the legacy one, especially actions, computed fields, and segments.
11

Switch your environment URL

Once you’re confident, point your production environment’s URL at the new agent. The UI configuration is preserved.
12

Keep the rollback available

To roll back, point the URL back at the legacy agent. Keep it running until you’re sure you won’t need to.
13

Remove legacy packages

Once production has been stable on the new agent for a few days, remove the legacy packages and clean up the old code.

What’s preserved

Your Forest UI configuration is not affected by the agent migration:
  • Layouts, segments, dashboards, charts
  • Roles, permissions, scopes, teams
  • Workspaces, workflows, inboxes
  • Approval workflow configurations
  • Smart Action visibility settings
These all live in Forest’s UI configuration and continue to work as long as the new agent exposes the same collection and field names.

What needs updating

Common issues

Restore the old names with rename (collections) and renameField (fields) rather than editing the layout — see Datasources.
Sequelize, Mongoose, ActiveRecord and Mongoid have matching datasources. Other Node.js ORMs connect through datasource-sql, or datasource-mongo for MongoDB. Both read the database directly. That works, but your model callbacks won’t fire, and the agent introspects the whole schema at every boot unless you cache it.
Whether a callback fires depends on the datasource:
  • datasource-sequelize: per-record hooks such as beforeCreate don’t run (details).
  • datasource-mongoose: save middleware doesn’t run.
  • ActiveRecord: all callbacks run as before.
  • Mongoid: callbacks run on create and single-record edits, not on multi-record edits or deletes.
  • datasource-sql: none of your callbacks run.
If one that no longer fires must run on Forest edits, move it into an agent hook. Don’t reimplement one that still fires, or it runs twice.
Not as the new agent’s schema: the two generations write different formats. Keep it to diff against while you check names.
The Smart Action form API is more structured in v2. Fields are declared explicitly. See Smart Actions for the new form syntax.
The new agent supports batched computed fields: getValues receives an array of records. If you naively port a v1 get function inside a .map(async ...), you’ll keep the same N+1 problem. Aggregate the underlying query.
The new relationship API requires you to declare both sides. If you only declared one direction, the UI may not surface it. See Smart Relationships.

Get help

Step pages

Per-feature migration instructions with side-by-side examples.

Community

Migration questions and patterns from other teams.

Support

Direct help from the Forest team.