Handling conflicts¶
Rebasing rewrites history, and history sometimes disagrees with itself. When sync replays your commits onto an updated parent and Git cannot apply one cleanly, the rebase stops with a conflict. git-city does not paper over this or leave you guessing — it pauses cleanly, tells you exactly where it stopped, and hands you a short menu of next steps.
A pause is not a failure. It is a deliberate checkpoint: the rebase is left in progress in your working tree (exactly as a plain git rebase would), and the remaining work git-city had planned is saved to disk so it can pick up where it left off once you have resolved the conflict.
What a pause looks like¶
When a sync hits a conflict, git-city stops and prints the state of the paused operation:
git-city: sync add-login is paused.
stopped on: git rebase --onto main <base> add-login
resolve the conflict and `git add`, then:
git city continue resume the operation
git city abort undo everything and return to the start
git city info show this and the repo status
The message names the operation that paused, the exact git command it stopped on, and the three commands that get you out. There is no traceback — git-city errors are always a clean git-city: <message> on stderr.
Note
The pause is persisted to <git-dir>/git-city/runstate.json. It survives closing your terminal: come back tomorrow, finish resolving, and git city continue still works. Because the run-state holds a single operation, only the most recent paused (or completed) command is remembered.
The resolve loop¶
While paused you are in an ordinary in-progress rebase, so you resolve conflicts with ordinary Git. The cycle is:
| Step | What you do | Tool |
|---|---|---|
| 1 | Open the conflicted files and fix the <<<<<<< / >>>>>>> markers |
your editor |
| 2 | Stage the resolved files | git add <file> |
| 3 | Tell git-city to carry on | git city continue |
git city continue resumes the rebase from where it stopped and then runs the rest of the plan git-city had queued — finishing the rebase, force-pushing with --force-with-lease, and moving on to any remaining branches in an --all sync. If resuming uncovers a further conflict, git-city simply pauses again and you repeat the loop.
Tip
Forgot where you were? git city info leads with the same pause banner shown above, then prints the repo dashboard. It is read-only — run it as many times as you like.
Backing out instead¶
If you would rather not push through the conflict right now, abort:
git city abort undoes the operation entirely and returns you to exactly where you started — the in-progress rebase is unwound and any refs that had already moved are restored. Nothing is left half-applied. You can then sync again later, or change your approach (for example, reparent the branch before retrying).
| Command | Effect |
|---|---|
git city continue |
Resume after you resolved the conflict and git added |
git city abort |
Roll the whole operation back to its starting point |
git city info |
Re-print the paused state, then the dashboard (read-only) |
While an operation is paused¶
A pause holds a lock on your repository's git-city state, so a few things are intentionally blocked until you resolve it:
Warning
git city undo refuses while an operation is paused. Undo and the pause loop are two different recovery mechanisms — finish the current operation with continue, or unwind it with abort, before reaching for undo.
The right tool depends on the situation:
- Mid-conflict (sync is paused): use
continueto finish orabortto back out. - After a completed command: use
undoto reverse the last git-city command, replaying its captured inverses in reverse.
Both paths are built on the same reversible engine, which captures how to undo every step before it mutates anything.
Avoiding conflicts in the first place¶
Conflicts are most common when a branch and its parent have both moved a long way apart. Syncing often keeps the gap small, so each rebase replays only a handful of commits. Because git-city syncs parents before children, a single git city sync --all keeps an entire stack consistent and minimises the surface area for any one conflict.