Your app bill is now bigger than your Shopify plan. You can't say which apps are earning their keep. Something breaks every peak season, and no one is sure what caused it.
All of it is fixable. We work on Shopify, so every date, native feature and limit below is a Shopify one, specific enough that you can check it against your own admin this week.
If you’re on WooCommerce, Magento (Adobe Commerce) or BigCommerce, the sequence still holds.
What this guide covers
-
Find your symptom and go straight to the section that fixes it
-
What you get out of it, stated plainly, including what it won't do
-
The five jobs every stack does, and why each needs one owner
-
The costs that never reach an invoice, including what our 1,000-store speed study found
-
A 90-day roadmap: count, decide, reconnect, remove
-
What a sane stack looks like at your revenue stage
-
Direct connections or middleware, and how the main platforms charge
-
Who should own each number, which is where most stacks fail
Signs your Shopify tech stack is too complex
Merchants rarely tell us their stack is too complex. They describe a symptom. Find yours in the left column and read that section first.
|
What you're seeing |
What's usually behind it |
Where to start |
|
App bill is bigger than your Shopify plan |
Apps doing jobs Shopify now does free, plus two or three no one uses |
Check native first |
|
Site is slow and you don't know which app did it |
Storefront apps stacking up, each one within its own limit |
Count everything, judge nothing |
|
Stock numbers disagree between systems |
Two systems both think they own the stock number |
Name the owner of every number |
|
You oversell during drops or peak |
A channel is reading on-hand stock instead of what's actually sellable |
Name the owner of every number |
|
Someone runs a spreadsheet every Monday |
A workaround became the process |
Fix how the data moves |
|
Something breaks every Black Friday |
Connections with no error handling, under load |
Decide what happens when a sync fails |
|
You're scared to remove anything |
No record of what each app touches |
Count everything, judge nothing |
|
An app you removed is still causing problems |
Leftover theme code and metafields |
Remove carefully, then verify |
If more than three of those sound familiar, start with ownership rather than with any single app. Nothing in your stack has a named owner yet.
What simplifying your stack changes, and what it doesn’t
-
A smaller bill. Most audits find two or three apps no one uses and one or two that Shopify now does free.
-
A faster storefront. Only if you cut storefront apps. Cutting back-office apps saves money and changes nothing a shopper sees.
-
Hours back every week. The spreadsheet someone runs on Monday is a job a connection should do.
-
Numbers you can act on. When one system owns each number, your reports stop disagreeing and no one rebuilds revenue by hand.
-
A quieter peak. Most peak failures come from connections breaking under load.
-
Changes that don't scare you. With one owner per number, you can swap a tool without wondering what else reads from it.
What it won't do is make you more money on its own. Simplifying removes drag. Growth still comes from the work you do on top.

The billing page from a real Shopify store, with the monthly total moving between cycles.
The five jobs every eCommerce stack does
A tech stack sounds abstract until you break it into the work it does. Every store does the same five things, whether it runs on Shopify, Magento, BigCommerce, or something custom.

The five jobs, and the connection layer that sits under all of them.
Underneath those five sits a sixth layer no one buys on purpose and everybody has: the connections. Every file export, every app sync, every webhook, every spreadsheet someone updates on Monday morning.
That layer causes most of the pain, and almost nobody audits it.
One owner per job
A clean stack is not one with fewer tools. It's one where each job has exactly one system that owns it.
-
Two systems both own the stock number, and you oversell
-
Two systems both own the customer record, and your segmentation is wrong
-
Nothing owns the revenue number, and finance rebuilds it by hand every month
Naming the owner of each number is the first job of any simplification work, and everything after that is cleanup.
How app stacks get complicated
The fix depends on the cause, so it pays to be fair about how stacks get this way. We see the same patterns.
The feature you needed once.
Someone wanted a size chart for a product launch in 2023. The launch ended. The app is still installed, still billing, still loading a script on every product page.
The workaround that became the process.
A nightly CSV export was meant to hold things together for two weeks while a proper connection got built. Two years later somebody's job description includes running that export, and the connection was never built.
The overlap no one mapped.
Your reviews app sends email. Your loyalty app sends email. Your ESP sends email. Three tools have a copy of your customer list and three tools are writing to it.
The platform catching up.
Shopify shipped a free version of something you're paying for. Bundles, subscriptions, B2B pricing, product recommendations, and search filters have all moved into the platform in the last few years. If you bought the app first, you probably weren't told when that changed. Merchants also report paying for apps that mostly wrap Shopify Flow, which is free on every paid plan.
Each of those decisions was right on the day it was made. Few teams go back and ask whether it still is, and Shopify won't prompt you to.
The hidden costs of a bloated app stack
Subscription spend is the easy number to find, and usually the smallest. If you want to work out when a custom build overtakes a stack of monthly fees, our app stack payback calculator does it from four inputs. The costs below are the ones that never show up on a bill.

How Shopify apps slow down your storefront
We tested 1,000 Shopify stores against Google's Core Web Vitals thresholds using PageSpeed Insights and Chrome UX Report data. Just 48% passed all three on mobile. Median LCP came in at 2.26 seconds, right at the edge of Google's 2.5 second threshold.

Core Web Vitals pass rate on mobile, by vertical, across 1,000 Shopify stores.
Beauty sits at the bottom, and not because beauty brands are careless. Heavier imagery, video, user-generated content widgets and loyalty modules all cost milliseconds, and every one of them was a deliberate decision.
To be published in the App Store, an app must not reduce storefront Lighthouse performance scores by more than 10 points. Each app clears that bar on its own. Nothing checks the total.

One app sitting among the largest network payloads on a real store

How each metric correlates with the weighted composite score in our study.
LCP is where we'd start. In our study it correlated with the composite score at 0.77, against 0.57 for INP and 0.38 for CLS.
One caveat on that: our composite weights LCP at 40%, INP at 30%, CLS at 10% and the Lighthouse performance score at 20%, and LCP also feeds the Lighthouse score itself, so some of that correlation is built into how the measure is constructed.

Read it as a reasonable starting point rather than a ranking. If you want the revenue side, our site speed revenue calculator turns load time and traffic into a monthly figure.


A PageSpeed Insights mobile result for a real store.
Another example Lighthouse diagnostics flagging unused CSS and legacy JavaScript, with the apps responsible named.
Reconciliation labor
This never gets budgeted. Someone compares your store against the 3PL portal on Monday. Someone else rebuilds the revenue number for the board deck because the ERP and the storefront disagree on refunds.
Count those hours for a month. Most teams find a part-time role hiding inside their ops function.
When this gets fixed properly, the saving shows up in maintenance costs. Alto Music cut ongoing maintenance by 40% moving off Magento 2, and STX runs at roughly 40% lower total cost of ownership than it did on Adobe Commerce. Both came from the stack needing less daily attention.
Dependencies with expiry dates
Platforms deprecate things, and legacy code doesn't warn you.
Shopify Scripts, which were Plus-only, stopped executing on June 30, 2026, with editing and publishing disabled from April 15. Discount, shipping, and payment logic living in Scripts had to move to Shopify Functions or stop working.
The deadline moved more than once before it landed, which is part of why some teams were caught out. Merchants with an inventory of what their stack ran handled the migration in weeks. The ones without found out from a customer.
How to simplify your Shopify tech stack in 90 days

Removing things comes last. The gap between counting and cutting is where most of the value gets created.
The four phases, with the output of each.
|
Phase |
Days |
What you do |
What you have at the end |
|
1. Count |
1 to 14 |
Inventory every app, integration, and manual process |
One sheet showing what you run, what it costs, and who uses it |
|
2. Decide |
15 to 30 |
Sort each line into keep, replace, consolidate, or remove |
A decision per line with a named owner |
|
3. Reconnect |
31 to 60 |
Fix how data moves and name the owner of each number |
An integration design, not a pile of syncs |
|
4. Remove |
61 to 90 |
Uninstall in a safe order, clean the residue, watch the numbers |
A smaller stack and a monitor that tells you when it drifts |
If you're mid-peak or three weeks from a launch, run phase one anyway. Counting changes nothing and takes a few hours a week. Hold phases two through four until trading calms down.
Days 1 to 14: audit every app, integration and manual process
Open a sheet. One row per app, per integration, and per manual process. The manual processes matter most and get left out most often, so start there by asking your ops and support teams what they do every week that a computer should be doing.
|
Column |
Why it's there |
|
What it does |
One sentence a non-technical person understands |
|
Where it runs |
Storefront or back office. Only storefront apps slow your site down |
|
Monthly cost |
Including usage charges, not just the plan price |
|
Who uses it |
A name, not a department |
|
How data gets in and out |
Native sync, API, middleware, CSV, or a person |
|
Renewal or notice date |
The only day of the year you have any leverage |
|
What breaks if it goes tomorrow |
The column that writes your removal list for you |
Three of those columns do most of the work.
Where it runs splits your stack in two. A back-office app that syncs orders to your accounting system costs you money but not milliseconds. A storefront app loads code on every page a shopper sees. Ten back-office apps and two storefront apps is a very different store from the reverse, and the speed numbers above only apply to the second group.
What a filled-in row looks like
|
App or process |
Where it runs |
Monthly cost |
Who uses it |
How data gets in and out |
What breaks if it goes tomorrow |
|
Email platform |
Back office |
$350 |
marketing |
Native sync |
All lifecycle email. Customer record lives here |
|
Loyalty app |
Storefront |
$199 |
marketing |
Native sync |
Points balances. Also sends email, which overlaps the ESP |
|
Size chart app |
Storefront |
$14 |
No one |
None |
Nothing. Added for a 2023 launch |
|
Monday 3PL stock check |
Back office |
6 hours of Priya’s time |
ops |
Someone does it |
Nothing breaks. You stop catching stock drift |
|
Old popup app |
Storefront |
$0, uninstalled |
No one |
None |
Nothing. Script still loading in theme.liquid |
Where to look so you don't miss anything:
-
Settings > Apps and sales channels for installed apps, and the same page for sales channels, which people forget are apps.
-
Settings > Billing for the actual charges, which often don't match what people think they're paying. Usage-based apps bill differently from their listed plan price.
-
Settings > Notifications > Webhooks for webhooks created by hand in the admin. Webhooks that apps register for themselves don't appear here, so check those app by app or through the API.
-
Settings > Custom data for metafield and metaobject definitions, including ones from apps you've already removed.
-
Your theme code, searched for script tags and app snippets. Apps built as theme app extensions keep their code on Shopify's CDN and remove it cleanly. Older apps that injected code into your theme files leave it behind when you uninstall.
-
Your bank statement and your card, for the integrations billed outside Shopify. Middleware, ERP connectors, and anything your developer set up directly won't appear in Shopify billing at all.
Don't decide anything for two weeks. The point of this phase is a complete picture, and you will keep finding rows until the end of it.

Installed Apps list from a real Shopify store

Metafield definition from a real Shopify store
Days 15 to 30: keep, replace, consolidate or remove
Each row in your sheet gets exactly one of these, with a name next to it.
Keep. It does a job no other tool does, someone uses it, and it earns its cost. Most of your stack should land here, and that's fine.
Replace with native. Shopify now does it, for free, inside the admin. Check this before anything else, because it's the fastest money you'll ever save.
Consolidate. Two or three tools overlap. Pick the one that does the most and move the rest of the work into it.
Remove. Nothing breaks when it goes.
Shopify features that replace paid apps
Shopify has absorbed a lot of what used to be app territory, and the pace picked up through 2026. Check these against your sheet before you renew anything:
|
What you might be paying for |
What Shopify now does natively |
|
Fixed bundles and multipacks |
The first-party Bundles app, free, which reduces component stock for you |
|
Subscriptions |
Shopify Subscriptions, built into the admin |
|
Wholesale pricing and company accounts |
Native B2B, which moved to every paid plan on April 2, 2026 with company profiles, catalogs, volume pricing, and net terms |
|
Search filters and product recommendations |
Search & Discovery, free |
|
Admin automation and alerts |
Shopify Flow, on every paid plan |
|
Translations and market content |
Translate & Adapt, free |
|
Basic forms |
Shopify Forms, free |
|
Discount, shipping, and payment logic |
Shopify Functions, which replaced Scripts |
Native isn't automatically better.
The first-party Bundles app won't do volume or tiered pricing, won't handle mix-and-match, and can't be sold with selling plans, which rules out subscriptions, pre-orders and try-before-you-buy. A brand running build-your-own boxes still needs an app.
Native B2B caps every plan below Plus at three catalogs, counted across all markets, and has no built-in application form for new wholesale accounts.
Check whether the native version does the specific thing your business needs, not simply whether one exists. Run that comparison honestly and you'll usually find two or three apps you can drop and one you should keep paying for.

A real flow form a live Shopify store
Choosing between two overlapping apps
When two tools overlap, the winner is whichever one owns the data. Interface quality is a tiebreaker at best. If your ESP holds the customer record and your loyalty app holds a partial copy, the ESP wins and the loyalty app should read from it.
Pick the nicer interface instead and you'll keep two copies of the customer record, which gives you segmentation you can't trust.
What a sane stack looks like at your size
There's no right number of tools, but there is a rough shape at each stage. Use this to spot what you're missing and what you've bought too early.

Which system holds the stock number at each revenue stage.
|
Stage |
Stock owned by |
Connections |
What's usually too early |
|
Under $1M |
Shopify |
Native app syncs, direct |
ERP, PIM, middleware, headless |
|
$1M to $10M |
Shopify, or an inventory system once wholesale starts |
Direct, plus one 3PL connection |
Middleware, unless you sell on three or more channels |
|
$10M to $50M |
ERP or inventory system |
Middleware starts to pay |
Custom-built connections you'll maintain yourself |
|
$50M+ |
ERP, with channel-aware available-to-sell |
Middleware, with monitoring and alerting |
Treating any single system as the one source of truth for everything |
The handover sits around $10M. Wholesale, a second warehouse, or a marketplace all move stock ownership out of Shopify, and brands that add the channel and leave the connections alone are the ones reconciling by hand six months later.
Days 31 to 60: redesign how your data moves
Two systems, one connection. Three systems, three connections. The growth looks harmless until you write it down.

Six systems connected directly, and the same six through one layer.
|
Systems |
Direct connections |
Connections through a central layer |
|
3 |
3 |
3 |
|
4 |
6 |
4 |
|
5 |
10 |
5 |
|
6 |
15 |
6 |
|
8 |
28 |
8 |
A central layer is why the right-hand column stays flat. Each system connects once, to the middle, and the middle handles the mapping, the retries, and the logging.
Direct connections vs middleware: when to move to an integration layer
Direct connections are not wrong. They're cheaper to start, carry no platform fee, and for a store running a storefront plus an accounting package plus a 3PL, they're usually the right answer.

Shopify's App Store listings for the major ERP connectors.
The case for middleware builds when:
-
You run five or more systems that share data
-
You sell on more than one channel and stock has to be right on all of them
-
You've rebuilt the same connection twice
-
No one can say where a failed sync goes or who gets notified
-
Peak trading breaks something every year
The 2025/26 Patchworks Retail Integration Report, a survey of 200 senior UK retail decision makers conducted by OnePoll, found 13% had adopted an integration platform while 31% were still on custom-built connections.
Some connections shouldn't exist at all. If a sync was built to keep two systems agreeing about a number only one of them should own, a better sync won't help. Delete one copy of the number.
How the main platforms charge
We build on Celigo, Boomi, Patchworks, and Jitterbit depending on the systems involved. Published list pricing is thin across all of them, and the figures circulating online disagree by an order of magnitude, so treat any number you find as a starting point for a quote rather than a price.
What you can compare is how each one charges, because that decides whether it gets expensive at your volume.
|
Platform |
Charges by |
Suits |
|
Celigo |
Endpoints and flows, flat rate |
NetSuite and eCommerce stacks that want a predictable bill |
|
Boomi |
Connections plus message volume |
Large estates with mixed on-premise and cloud systems |
|
Patchworks (Shero Recommends) |
Connectors and operations |
Retail and eCommerce, often bundled with partner support. |
|
Jitterbit |
Connections, tiered |
Stacks with EDI and trading partners |
Ask any vendor what happens to the bill when your order volume doubles. Per-message and per-operation pricing scales with your success. Flat per-endpoint pricing doesn't. Neither is wrong, but one of them surprises you in November.
The main thing you're buying is visibility: one place that shows every flow, every failure and every retry, instead of five systems each telling you a different story.

"Using an iPaaS has made two of the most challenging aspects of my integration work much easier. First, as any developer will tell you, it saves countless hours of traditional debugging. Second, and just as importantly, Patchworks' visual workflow makes it much easier to communicate and collaborate with the client's team throughout the integration process."
Dejvid Haxhiu – Senior Back End Developer at Shero Commerce
Which syncs need real time and which don’t
There's a reflex to make everything instant. Resist it. Instant costs more and breaks more often, and most of your data doesn't need it.
|
Needs to be instant |
Fine on a schedule |
|
Stock coming down after an order |
Product catalog updates |
|
Order capture |
Cost prices |
|
Anything that causes an oversell if it lags |
Financial postings |
Scheduled jobs are more reliable and far easier to debug when something goes wrong.
Shopify's API design pushes you the same way. The GraphQL Admin API is rate-limited on calculated query cost through a leaky bucket, sized by plan, so a connection that hammers the API record by record will throttle. Input arrays cap at 250 items and pagination caps at 25,000 objects.
For anything touching more than a few hundred records, bulk operations run outside the normal rate limit entirely. An integration built without knowing any of that works fine in testing and falls over on the first big catalog sync.
Decide what happens when a sync fails
Most integration problems trace back to connections built without a clear data map, without error handling, and without a rule for what happens when two systems disagree.
Before anyone writes code, three things need answers:
-
Which fields move in which direction, entity by entity, for orders, inventory, pricing, customers, products, and fulfillment status
-
What triggers a sync, and what resolves a conflict when both sides changed
-
Where a failed record goes. It should be logged with a reason and retried on the next cycle, with an alert to a named person. Silently dropped records are how a small mismatch becomes a month of reconciliation
Teams skip this because it feels like paperwork. It decides whether your integration breaks loudly or quietly.
The deeper version of this conversation, including why ERP data updating Shopify in real time is often the wrong call, is in our Shopify ERP integration guide.
Which system should own your inventory, customer and revenue data
For each number your business runs on, one system owns it and the others read from it. Write that down and send it round.
|
Number |
Owner |
Everyone else |
|
Available-to-sell stock |
One system, chosen deliberately |
Reads it |
|
Order status |
Shopify, usually |
Reads it |
|
Customer record |
Your ESP or CRM, usually |
Reads it |
|
Product content and attributes |
Your PIM, or Shopify if you have no PIM |
Reads it |
|
Revenue, cost, and tax |
Your ERP or accounting system |
Reads it |
Stock is where this gets argued about. Shopify already splits inventory into states, and most sync problems come from treating them as one number.

4,200 units on hand, split into committed, unavailable and available.
Show a channel the warehouse figure and you will oversell during a drop. So pick the owner based on where allocation actually happens:
-
Your store owns stock when nearly all demand lands there and your 3PL reports receipts and shipments back
-
Your ERP or inventory system owns stock when you sell wholesale, run multiple channels, or reserve units against orders the storefront never sees
-
The 3PL never owns stock. It reports physical reality. It doesn't know what you've promised
The same logic applies to product data through a PIM and to the customer record through a CRM. One owner, everyone else reads.
Get this wrong and no amount of sync frequency saves you. Two systems that both believe they can decrement the same unit will eventually both decrement it, and polling faster only narrows the window.
Days 61 to 90: how to uninstall Shopify apps safely
Uninstalling starts a cleanup most merchants skip.
Go one at a time, and leave a gap.
One removal per day at most, with the numbers watched in between. Pull five apps on a Friday and you'll spend the next month guessing which one took your conversion rate with it.
Duplicate the theme first.
Before any removal, duplicate your live theme and name it with the date and the app you're about to pull. If the removal goes wrong, you publish the old theme and move on.
Export anything you want to keep.
Reviews, loyalty balances, subscription contracts, and segment definitions usually live in the app, not in Shopify. Once it's uninstalled, that data is the vendor's problem and your leverage is gone. Export first, confirm the export opens, then uninstall.
Expect leftovers, and know where they hide.
Apps built as theme app extensions keep their code on Shopify's CDN, and it goes cleanly when the app does. Older apps that wrote into your theme files leave snippets, asset files, and lines in theme.liquid behind. Search your theme for the app's name and CDN domain after every removal.
This matters beyond speed: leftover code from an old app is a common reason a new app in the same category starts behaving oddly.

The Initiator column traces which file loaded a script, which is how leftover code gets found.
Metafields are the awkward one.
Metafield and metaobject definitions created in an app-reserved namespace have historically been editable only by the app that created them, which can mean reinstalling, clearing the definitions, then uninstalling again.
Shopify's handling of app-owned data has changed over time, so check the current behaviour before you plan around it. Clearing what you can before you uninstall saves the round trip either way.
Watch four things for two weeks after each removal. Conversion rate, mobile Core Web Vitals, support ticket volume, and any number the removed app used to write to. If none of them move, that removal is done.

Duplicate the theme before any removal. App embeds can be switched off from the same screen.
How to keep your app stack from growing back
A stack you cleaned once will be messy again in eighteen months unless you change how things get in. Three habits cover it.
Ask one question before every install.
Which of the five jobs does this do, and what already owns it? If something does, you’re adding a second opinion about a number. Sometimes that’s justified. It should never be accidental.
Give every app an owner and a review date.
An app with no owner is an app no one will cancel.
Review quarterly.
Thirty minutes with the sheet from phase one. Is anyone using it, is it still the best tool, has Shopify shipped a native version. Put the developer changelog on the same calendar, so the next deprecation reaches you before it reaches your customers.
What to do this week
Open a sheet. List every app with its monthly cost and the name of the person who uses it. It takes an afternoon, and it's usually uncomfortable, because two or three lines will have no name next to them at all. The rest of this guide runs on that sheet.
If the stack question is tangled up with a platform move, the integration scope belongs in the migration budget from the start rather than appearing after launch.
If the connection layer is the hard part, a call with our strategists will clear out the clutter.
