At Forest, I work on product interfaces, operations workflows, and data integrations. I initiated an incremental move from Ember to React microfrontends and improved Workflow Builder performance on large graphs.
What Forest has to connect
Forest provides infrastructure for teams running complex operations. The product connects data sources, workflows, permissions, and actions performed by people or agents.
Its interfaces do more than display data. They help teams understand context, take action, and follow what happened across several systems.
Changing foundations without stopping delivery
The product has a substantial Ember foundation and continues to evolve. Introducing React is not a reason to replace automatically what already works.
We had to choose where React brought real value, organize its coexistence with Ember, and define the shared foundations. Meanwhile, workflows stayed connected to several data sources and large graphs still had to remain fluid during editing.
My part in the migration
I contribute to product interfaces, operations workflows, data-source integrations, and internal tooling. My scope includes the frontend and the fullstack foundations required by these journeys.
I prepared the migration around features that could be isolated, tested, and delivered progressively.
I worked with the team through the feature-by-feature migration.
Architecture choices
Compare before choosing
The first options included iframes and Shadow DOM. They introduced too many integration constraints, especially around network exchanges and communication with the host application. Proofs of concept made those trade-offs visible before we selected Module Federation with Rspack.
Migrate along useful boundaries
The migration is not driven by an abstract goal to replace a framework. It advances through groups of features that can be isolated, tested, and delivered without weakening neighboring journeys. This avoids a global rewrite and keeps deployments separate.
Let Ember and React coexist
Coexistence is part of the architecture, even if it remains temporary for some domains. Exchanges between both environments need to be explicit and stable enough that every change does not become a special case.
Organize applications and shared packages
The monorepo separates applications under apps/ and common foundations under packages/. The UI package contains shared components, while the Data package centralizes reusable contracts and data needs. This improves developer experience without forcing every area to deploy together.
Keep the Workflow Builder fluid
The Workflow Builder must remain usable when a graph grows large. The work focused on virtualizing elements that did not need to render, reducing expensive repaints, and limiting the work triggered during graph interactions.
These optimizations keep interactions fluid during editing without publishing more detail than can be documented safely.
What this approach enabled
The migration can move feature by feature without blocking existing deployments. The architecture was therefore judged by how well it supported the product, not by replacing Ember for its own sake.
