Merging and Swapping
Tidy Tags ships two related primitives for consolidating taxonomy: merge (tag-only, deletes the source tags) and swap (works across element types, leaves the source elements in place). Both repoint relations safely inside a transaction so you never lose an entry's link to a tag.
Merge vs. swap
- Merge is tag-only. It repoints every relation to the target tag and deletes the source tags in a single transaction. Use it when consolidating duplicate tags inside a tag group.
- Swap is element-type-agnostic. It runs the same relation repointing logic but does not delete the source elements. Use it for entry-backed sources (where deletion is unsafe) and for cross-source consolidation (Tag → Team, Team → Competition, etc.).
The duplicate scanner picks the right primitive for you: tag-group clusters offer Merge, entry-backed and cross-source clusters offer Swap.
How merging works
When you merge tags, Tidy Tags:
- Starts a database transaction.
- Reads every row in
{{%relations}}whosetargetIdis one of the source tags. - For each such row, checks whether a relation with the same
fieldId,sourceId, andsourceSiteIdalready points at the target tag. If one does, the source row is deleted (it would otherwise become a duplicate relation). If not, it's updated to point at the target. - Deletes each source tag element (all sites) via
Craft::$app->elements->deleteElement(). - Commits the transaction.
This preserves every entry's relationship to the merged tag while cleaning up redundant rows. If anything goes wrong mid-way, the transaction is rolled back and your data is untouched.
Multi-site behavior
Merges operate on tag elements, which means they apply across all sites the source tags exist in. If the target tag is missing a translation that the source had, you should rename the target in the affected site after the merge — see Usage for the rename workflow.
How swap works
Swap is the element-type-agnostic version of merge. It runs steps 1–3 above inside a transaction but never deletes the source elements. Use it when:
- You're consolidating across sources — Tag → Team, Team → Competition, or any cross-type combination surfaced by the Across sources tab on the Duplicates page.
- You're cleaning up entry-backed duplicates and want to verify by hand before deleting. Entries carry URLs, bodies, drafts, and authors that Tidy Tags shouldn't silently clobber.
After a swap, the source entries are orphaned (no relations point at them) but still present. Delete them through Craft's normal entry UI once you're satisfied.
Swap is exposed through the duplicate scanner's Swap relations button on every entry-backed and cross-source cluster, and via the tidytags/tags/swap action endpoint — see Action Endpoints.
After a large merge or swap
Craft aggressively caches element and template output. After consolidating a large batch of tags or entries, clear the caches so front-end templates pick up the new state immediately:
php craft clear-caches/all
Picking a winner
When you merge, you choose which tag is the target (the one that survives) and which are the sources (the ones that get deleted). A good rule of thumb:
- Pick the tag with the cleanest, most canonical casing —
JavaScriptoverjavascript. - Prefer the tag that already has the most entry relations, so less data moves.
- Prefer the tag that already has translations in every site you care about.