Maya Tran
May 5, 2026
•
10 min

You built the app. It works. But every time a user opens it, they're staring at a spinner for three seconds before anything shows up—and by the time they've filtered a table, waited for a refresh, and triggered a cascade of dependent queries, they've already opened a Slack thread asking if something is broken. It's not broken. It's just slow. And slow internal tools get abandoned.
After building dashboards, ops portals, and custom tooling for clients across fintech, energy, SaaS, and e-commerce, we've seen the same performance killers appear again and again in Retool projects. Some are obvious once you know what to look for. Others are subtle architectural decisions that compound over time. Here are 12 fixes we actually use on real client projects—ordered by how often we encounter them.
The most common performance issue we see in Retool isn't bad SQL—it's that every query on the page fires simultaneously the moment the app loads. Retool's default behavior is to run queries on page load unless you tell it not to. If your page has 12 queries and 10 of them are set to run on load, you're hammering your database with 10 concurrent requests before the user has done anything.
The fix starts with auditing every query and asking: does this actually need to run on load, or does it only need to run when the user interacts with something? Dropdown filters, date range pickers, search inputs—these should be triggering queries, not the page load event.
For queries that do need to fire on load, sequence them deliberately. Use the success event handler on a primary query to trigger dependent secondary queries, rather than letting everything race at once. This staggers the load, prioritizes the data the user sees first, and stops you from overwhelming a database connection pool with a burst of parallel requests.
One client in fintech came to us with a dashboard that fired 18 queries on load. Fourteen of them were powering components below the fold. We moved those to run on tab change or on scroll interaction, and their perceived load time dropped by more than half without touching a single line of SQL.
Pulling too much data is the second-fastest way to kill performance. We've inherited Retool apps where a table query was returning 50,000 rows client-side and relying on Retool's built-in search and filter to handle it. That's not a feature—that's a symptom of not thinking about where the work should happen.
Filtering and pagination belong in the database, not in the browser. If you're using Retool's table search on a dataset larger than a few hundred rows, you're doing it wrong. Write the WHERE clause. Add the LIMIT and OFFSET. Bind them to your filter components. Let your database do what databases are good at.
JavaScript transformers run synchronously in the browser. A transformer looping over 10,000 rows to flatten a nested object or compute a derived field is blocking the UI thread. We've seen transformers add 400–800ms of rendering lag on their own.
The rule we use: if a transformation can be done in the query itself—a CASE statement, a JSON_AGG, a computed column—do it there. Save transformers for lightweight reshaping that genuinely can't happen at the database layer. And if you must use a transformer on a large dataset, look at whether you can reduce the dataset first.
We see teams storing large API responses in Retool state variables and then reading from those variables across multiple components. State in Retool isn't optimized for large payloads. It triggers reactivity across the component tree every time it updates. If you're storing a 2MB API response in state and five components are watching it, you're paying that reactivity cost five times on every update.
Keep state small. Store IDs, selections, and UI flags—not entire datasets. If multiple components need access to the same data, they should be reading from the same query directly, not from a state variable that mirrors it.
Retool's reactivity model means that when a variable changes, every query that depends on it re-runs. This is powerful, but it creates a performance trap if your dependency graph is tangled.
The cascade effect looks like this: a user selects a value from a dropdown. That dropdown's value is referenced in Query A. Query A's result feeds into a transformer. That transformer's output is referenced in Query B. Query B triggers Query C. One user interaction causes three sequential round-trips to the database, each waiting for the previous one to complete. The user waits two or three seconds for what felt like a simple filter.
The first step is mapping your dependencies explicitly. In every project we take on, we diagram which queries depend on which variables and which other queries. If you have chains longer than two hops, you have a problem worth solving.
Usually the fix is restructuring the query to join what was previously split across multiple dependent queries. A single SQL query with two JOINs almost always outperforms three sequential queries with Retool dependencies between them. More data manipulation in the database, less orchestration in Retool.
If any query is bound to a text input—search boxes, filter fields—and it's set to re-run on every keystroke, you're firing a database query for every character the user types. Add debouncing. In Retool, you can use an event handler with a delay, or trigger the query explicitly on blur or on a button press rather than binding it directly to the input value. A 300–500ms debounce on a search field eliminates dozens of unnecessary queries per user session.
Not every query should be reactive. Write-heavy forms, bulk action triggers, and any query that takes user confirmation before executing should be set to manual trigger only. Reactive queries are for read operations where you want the UI to stay in sync automatically. For everything else, explicit is better than automatic.
When a Retool app grows organically, it tends to become a single page with tabs, hidden containers, and conditional visibility controlling what the user sees. This feels like a logical way to organize things. It's also a performance disaster.
Every component on the page—visible or not—participates in Retool's rendering cycle. Every query set to run on load fires regardless of which tab the user is on. A "hidden" section isn't skipped; it's just not displayed. You're paying the full performance cost for every part of the app, even the parts the user isn't looking at.
The correct architecture for a tool that has grown beyond two or three distinct workflows is a multipage app. Retool's multipage support lets you scope queries, components, and state to individual pages. When a user is on the Orders page, the Inventory page's queries aren't running. This alone can reduce initial load query count by 60–70% on apps we've inherited.
A good rule of thumb we use with clients: if a workflow requires more than five queries and has its own distinct user action set, it should be its own page. Don't use tabs to simulate pages when actual pages exist.
For cases where a single page genuinely needs to stay unified—a dashboard that combines several data views, for example—use container visibility to lazy load heavy components. Set a container to hidden by default, load its data query on a user interaction, and make the container visible once the data is ready. Users see the lightweight parts of the page immediately and wait only when they actively request the heavy parts.
This pattern works particularly well for charts and large tables that aren't critical to the initial view. Don't render a complex time-series chart on page load if the user has to scroll past three other components to even see it.
Retool gives you query-level caching through the cache query results setting. Most teams don't use it. On any query where the underlying data doesn't change frequently—lookup tables, reference data, user permission sets, configuration values—turn caching on with an appropriate TTL. There's no reason to hit the database every time a user opens a modal to pick from a list of 15 product categories that hasn't changed in a month.
Set cache TTLs that match your actual data freshness requirements. A list of countries can cache for hours. Order status data might cache for 30 seconds. Transactional data that needs to reflect the latest state immediately shouldn't be cached at all. Make the decision deliberately for each query rather than using the defaults.
Retool performance problems are often Retool symptoms of database problems. Before you restructure your app architecture, look at your slow queries in your database's query analyzer. Missing indexes on columns used in WHERE clauses, JOIN conditions, and ORDER BY expressions are responsible for more Retool slowness than any Retool-specific issue.
On a client project last year—an e-commerce ops portal built on Supabase—we found that one query powering a main table was doing a full sequential scan across 800,000 rows because no index existed on the created_at column being used in the date range filter. Adding a single index cut that query from 3.2 seconds to 80 milliseconds. The Retool app felt like a different product.
Any time you're returning raw transactional rows to Retool and aggregating them in a transformer—summing revenue, grouping by category, computing averages—you're pulling more data than you need and doing more work in the browser than necessary. GROUP BY, SUM(), AVG(), COUNT(): these are fast at the database layer. Use them. Return the aggregated result, not the raw rows.
If your data requirements are complex enough that your Retool queries are becoming hard to maintain—multiple joins, heavy business logic, data from multiple sources being merged—consider adding an API layer between Retool and your database. A lightweight endpoint that accepts parameters, runs the complex logic server-side, and returns a clean shaped response is easier to optimize, easier to test, and easier to cache than equivalent logic spread across Retool transformers and chained queries.
This isn't always the right call—it adds a layer of infrastructure—but for apps that have outgrown direct database queries, it's the right architectural move. We've implemented this pattern for several clients using simple serverless functions in front of their Supabase instances, and the performance and maintainability gains are significant.
When we take on a new client project with an existing Retool app, we run through the same audit before touching any code. Here's the list, ordered by how quickly each check pays off.
None of these fixes require a rebuild from scratch. Most of them are targeted interventions that can be done in a few hours on an existing app. The compound effect of applying several of them together is usually dramatic—apps that felt sluggish and unreliable become noticeably snappier after a focused audit session.
Internal tools that perform well get used. Internal tools that don't get worked around—or replaced. If your Retool app is slow, the fixes are almost always available. You just have to know where to look.
Looking to supercharge your operations? We’re masters in Retool and experts at building internal tools, dashboards, admin panels, and portals that scale with your business. Let’s turn your ideas into powerful tools that drive real impact.
Curious how we’ve done it for others? Explore our Use Cases to see real-world examples, or check out Our Work to discover how we’ve helped teams like yours streamline operations and unlock growth.

🔎 Internal tools often fail because of one simple thing: Navigation.
Too many clicks, buried menus, lost users.
We broke it down in this 4-slide carousel:
1️⃣ The problem (too many clicks)
2️⃣ The fix (clear navigation structure)
3️⃣ The Retool advantage (drag-and-drop layouts)
4️⃣ The impact (happier teams)
💡 With Retool, you can design internal tools that are easy to use, fast to build, and simple to maintain.
👉 Swipe through the carousel and see how better UX = better productivity.
📞 Ready to streamline your tools? Book a call with us at Retoolers.

🚀From idea → app in minutesBuilding internal tools used to take weeks.
Now, with AI App Generation in Retool, you can describe what you want in plain English and let AI do the heavy lifting.
At Retoolers, we help teams move faster by combining AI + Retool to create tools that actually fit their workflows.
👉 Check out our blog for the full breakdown: https://lnkd.in/gMAiqy9F
As part of our process, you’ll receive a FREE business analysis to assess your needs, followed by a FREE wireframe to visualize the solution. After that, we’ll provide you with the most accurate pricing and the best solution tailored to your business. Stay tuned—we’ll be in touch shortly!



