How to Stop Overwriting Your Client’s Theme Editor Changes
A client spends an afternoon configuring sections. You push a CSS fix. Their work is gone, and you did it. Here is why it happens and the flag that prevents it.
Why a CSS fix can delete an afternoon of work
Shopify themes keep two very different kinds of state in the same folder, and the theme editor writes to one of them.
- Code — Liquid, CSS, JS. You edit these in your editor.
- Configuration —
config/settings_data.jsonand the JSON files intemplates/. These hold which sections exist, in what order, with what settings and copy. The theme editor writes here.
When a client drags a section, changes a heading, or swaps an image in the customiser, none of that is stored in a database somewhere separate. It's written into JSON files on the theme.
shopify theme push uploads your local files over the theme's files. It isn't a merge and it isn't aware that someone else has been working. Your settings_data.json — which reflects the state whenever you last pulled — replaces theirs. The push succeeds. Nothing warns you.
The reverse direction breaks too
The same gap runs the other way. A client reorders sections while you're building. You pull later, and their JSON overwrites the section config you were setting up in code. Both directions lose work, because both are last-write-wins on the same files.
The flag that closes the gap
The Shopify CLI has a mode for this. Running the dev server with --theme-editor-sync makes changes made in the theme editor flow back down into your local files while the session is running:
shopify theme dev \
--store client-store.myshopify.com \
--theme 123456789 \
--theme-editor-sync
With that running, a client changing section settings in the customiser results in your local settings_data.json and JSON templates being updated. Their work lands in your working copy, where it can be committed, and your next push carries it forward instead of replacing it.
The JSON churn problem, and how to live with it
Two-way sync introduces its own annoyance: settings_data.json becomes a busy file. Every colour tweak and section reorder is a diff, often a large and unreadable one. Teams react by ignoring the file, which recreates the original problem.
What works better:
| Practice | Why |
|---|---|
| Commit config changes separately from code changes | Keeps code review readable and makes a config regression easy to revert on its own |
Use a commit message convention like config: | You can find "when did the homepage sections change" in seconds |
Never resolve a settings_data.json conflict by hand | Take one side wholesale. Hand-merging this file produces themes that fail to render sections |
| Agree who owns config during a phase | "You're in the customiser this week, I'm not pushing config" removes the collision entirely |
| Pull before you push, every time | The cheapest habit on this list and it catches most of it |
# See what changed on the theme before you overwrite anything
shopify theme pull --theme 123456789 --store client.myshopify.com
git diff --stat
# Config-only changes? Commit them on their own.
git add config/settings_data.json templates/
git commit -m "config: client section changes from theme editor"
The conversation that prevents most of this
Most overwrite incidents are a coordination failure wearing a technical costume. The client had no idea that "moving a section" and "your code" touch the same files, because there's no reason they would.
Setting expectations once, in plain language, at kickoff:
That paragraph does two useful things. It gives the client a safe way to participate, and it makes any future incident a shared process gap rather than your mistake.
Give them somewhere better to put feedback
A lot of client customiser editing isn't really editing — it's the only way they can show you what they mean. If the alternative is a paragraph in an email, dragging the section themselves is genuinely easier for them.
Give them a way to point at the thing on the page and say "this should be above that" and most of the risky editing stops, because the editor was never what they wanted. They wanted to be understood.
How ThemeSync handles editor changes
- Themes pushed for review run with editor sync enabled. When a theme is pushed to the store for a client to work with, the follow-on dev session runs with
--theme-editor-sync, so customiser changes come back into the tracked files rather than stranding on the theme. - The session stays up. Because the dev server runs in the cloud rather than on a laptop, the sync window isn't limited to when your machine is awake — which is when clients tend to be in the customiser.
- Everything lands in a git branch. Config changes are commits. "When did the homepage sections change, and to what" has an answer, and a bad config change can be reverted on its own.
- You can see uncommitted theme changes before pushing. A diff of what's changed on the theme versus what you're about to upload turns silent overwrites into a decision you make deliberately.
- Clients get pinned comments as the default. Pointing at an element and typing a sentence is easier than the customiser, so there's less reason for them to be in there rearranging things at all.
Takeaways
- Theme editor changes live in
config/settings_data.jsonand the JSON files undertemplates/— real files on the theme, not separate storage. theme pushoverwrites rather than merges. It will replace client configuration and report success.shopify theme dev --theme-editor-syncpulls editor changes back into your files, but only while the session is running.- Pull before every push. It's the cheapest habit that catches most of these.
- Never hand-merge a
settings_data.jsonconflict — take one side whole. - Tell clients at kickoff that the customiser and your code share files, and give them a better way to give feedback than doing it themselves.
Never overwrite a client’s work again
ThemeSync keeps editor sync running on review themes, commits config changes to git, and shows you a diff before anything gets pushed over the top.
Try ThemeSync Free →