Guides
Retool Module Versioning: How to Pin a Specific Version
If you're relying on Retool module versioning to keep your apps stable, you've probably already run into this wall: you release a new major version of a module, and suddenly every app consuming that module — including ones you weren't touching — breaks. There's currently no native way to pin a specific module version to a specific app in Retool, and it's one of the most requested features in the community. This guide explains exactly what the problem is, why it's painful, and the best workarounds available right now.
What Is Retool Module Versioning and Why Does It Break Apps?
Retool modules are reusable UI components or logic blocks you can share across multiple apps. Retool does support versioning for modules — you can cut a 1.0.0, 1.7.3, or 2.0.0 release. The problem is that all apps consuming a module always use the latest published version. There is no per-app version selector.
Here's the scenario that breaks teams: App A is stable and running on module version 1.7.3. You build App B, which needs a new feature that requires a breaking change — so you release module version 2.0.0. The moment that release goes out, App A is now also running 2.0.0. No warning, no prompt, no rollback. App A breaks in production.
This is not a edge case. It's a fundamental gap in how Retool handles module dependency management, and it affects any team that shares modules across apps with independent release cycles.
Why You Can't Just Roll Back a Module Version
Unlike a Git branch or a npm package with a lockfile, Retool modules don't give consuming apps any mechanism to declare which version they depend on. The version history exists in Retool's UI, but it's informational — you can view past versions, but you cannot reassign an app to consume a specific older version. Once you publish, every downstream app updates immediately.
This also means you can't safely do iterative development on a shared module without risking live apps. Even saving a new draft or cutting a release in staging can cascade in unexpected ways depending on your environment setup.
The Current Workarounds for Pinning Retool Module Versions
Until Retool ships a native version-pinning feature, here are the practical options teams are using today:
- Duplicate the module: Before making breaking changes, create a copy of the module — for example,
PaymentForm_v2— and migrate only the new app to it. The originalPaymentFormmodule stays frozen for legacy apps. It's messy, but it's the most reliable isolation strategy available right now. - Use environment-scoped modules: If your Retool org uses separate staging and production environments, you can hold a module at a stable version in production while iterating in staging. This doesn't help if both apps live in the same environment, but it buys you a review gate before changes hit live apps.
- Gate breaking changes behind feature flags: Instead of cutting a new major version immediately, keep backward-compatible behavior inside the module using conditional logic — for example, checking a passed-in
propto determine which code path to execute. This lets you ship new behavior to new apps without breaking old ones, until you can migrate everything. - Freeze consuming apps before releasing: Communicate with your team before any major module release, manually audit which apps use the module (Retool shows you this in the module detail view), and make sure those apps are updated or protected before publishing. Tedious, but it prevents surprise breakages.
How to Duplicate a Retool Module to Isolate Breaking Changes
The duplication workaround is the most common stopgap. Here's how to do it cleanly:
- Open the module you need to fork in the Retool editor.
- Use the Duplicate option from the app/module list (three-dot menu). Name the copy clearly — append
_v2or a date suffix so your team knows it's a versioned fork. - Make your breaking changes only in the new duplicate module.
- Update only the new app to import the
_v2module. Leave all existing apps pointing at the original. - Once all apps have been migrated to the new version, you can deprecate and eventually delete the old module.
It's not elegant. You're essentially doing manual dependency management. But it works, and it's significantly safer than letting a 2.0.0 release silently break a production app at 2am.
What Retool Should Build (and What to Watch For)
The right fix is a version selector at the app level — something like a package.json lockfile per app, where each app declares "PaymentForm": "1.7.3" and only upgrades on explicit action by a developer. Some teams have also requested the ability to tie module versions to app versions, so that when you publish a new app version, it locks in the module versions it was tested against.
This is an actively requested feature in the Retool community. If it's blocking your team, upvote the thread and add your use case — product teams do read those threads, and specificity helps. In the meantime, the duplication strategy above is your safest bet for protecting stable apps from breaking module changes.
Ready to build?
We scope, design, and ship your Retool app — fast.