
Andrew Hanna

Andrew Hanna

Short answer: Commit each Flow as one unversioned
.flow-meta.xml file, give every Flow a single owner per change, and tell
Git never to auto-merge Flow XML. When two branches do touch the same Flow, keep one
side and rebuild the other change in Flow Builder instead of hand-editing XML. Most
Flow merge pain comes from parallel edits and layout noise, not from Git.
A Flow is not code you wrote line by line. It is XML generated by Flow Builder, and it carries a few traps:
locationX and locationY coordinates, so dragging a box
produces a diff with no logic change. Switching a Flow between free-form and
auto-layout rewrites the positions of every element.
force-app/main/default/flows/, named after the Flow's API name with no
version suffix.
status field on the Flow itself controls whether it is active, and
Salesforce no longer recommends Flow Definitions for activation.
sf project retrieve start --metadata Flow:Case_Escalation. Check the
status value before you commit, so a draft never ships by accident.
force-app/**/flows/*.flow-meta.xml -merge to
.gitattributes. Per the
gitattributes docs, an unset
merge keeps your branch's version and declares a conflict. Avoid the
binary shortcut here, because it also switches off diffs, and you still
want to review Flow changes.
That last step matters most. A line-based merge can produce Flow XML that is perfectly valid and logically wrong, for example a connector pointing at an element the other branch deleted. A forced conflict is cheaper than a silent one. It also explains why our guide to a Salesforce-aware Git merge driver keeps Flows out of the driver's patterns: profiles and permission sets merge well by node, Flow logic does not.
git checkout --ours or --theirs on the Flow file.
For conflicts across other metadata types, see how to resolve Salesforce metadata conflicts during a merge.
Still shipping Flows with change sets? Start with how to graduate from change sets to source control, then apply the steps above.
DevOps platforms such as Gearset and Flosum add Flow-aware comparison and deployment on top of Git, and Salesforce's Lifecycle Center (formerly DevOps Center) offers AI recommendations for conflict resolution through its MCP tools. Serpent resolves conflicts on the pull request itself: Serpent AI proposes a resolution and waits for your review before applying it, and AI code review runs on every plan. See Serpent plans, or browse more Salesforce DevOps guides.
Should I commit FlowDefinition files?
No. Since Metadata API v44, the Flow's own status field controls
activation, and Salesforce no longer recommends Flow Definitions for that job.
Can Git merge two versions of the same Flow automatically?
It can produce a textually clean merge, but Git does not understand Flow logic. Force
a conflict with -merge and reapply one change in Flow Builder.
Why did a draft Flow end up in my repository?
A retrieve returns the latest version of the Flow, active or draft. Check the
status value before committing.
Do locationX and locationY changes matter?
They change layout only, not behaviour. Review them as noise, and avoid switching canvas modes so they stay stable.
Commitment free!