Skip to content

mistweaverco/diffconflicts.nvim

diffconflicts logo

diffconflicts.nvim

Made with love GitHub release (latest by date) License GitHub issues Discord

RequirementsInstallationUsage

A Neovim plugin for resolving merge conflicts.

Make resolving merge conflicts in Neovim a breeze.

Screenshots

diffconflicts screenshot

All you need to do is edit the left side to resolve the conflicts.

By default, saving the file (:w) will automatically advance to the next conflicting file.

Origins

Origins of this plugin

This started as "just a port from vimscript to lua."

The OG plugin is vim-diffconflicts and it's author is Nathaniel Whiteinge.

It has since evolved into more of a rewrite and some new features.

The core idea of providing a two-way-diff view for resolving merge conflicts remains the same.

Two-way-diffs are arguably the best way to resolve merge conflicts.

I'm forever grateful to Nathaniel for creating the original plugin and inspiring this one.

Requirements

Requirements for this plugin
  • Neovim 0.10+
  • Git 2.25+ (for git mergetool support)
  • Jujutsu v0.18+ (optional, for jj resolve support)

Installation

Installation example for this plugin

Use your favorite plugin manager to install diffconflicts.nvim.

For example, with Lazy:

{
  "mistweaverco/diffconflicts.nvim",
  opts = {
    -- Optional configuration
    commands = {
      -- Command to open the diff conflicts view, default is "DiffConflicts"
      -- set to nil to disable the command
      diff_conflicts = "DiffConflicts",
      -- Command to show the history of conflicts, default is "DiffConflictsShowHistory"
      -- set to nil to disable the command
      show_history = "DiffConflictsShowHistory",
      -- Command to resolve conflicts with history, default is "DiffConflictsWithHistory"
      -- set to nil to disable the command
      with_history = "DiffConflictsWithHistory",
    },
    -- Quality-of-life options
    qol = {
      -- After saving (:w), automatically close the diff view and jump to the next
      -- conflict in the file (if any).
      advance_on_save = true,
      -- If no conflicts remain after saving, quit Neovim (:qa). This is useful
      -- when running from `git mergetool` / `jj resolve`.
      quit_on_done = true,
    },
  }
}

Configure

Configuration is required to use this plugin as a merge tool with Git or Jujutsu.

Configure with Git

Configure with Git

Configure Git to use this plugin as a merge-tool:

git config --global merge.tool diffconflicts
git config --global mergetool.diffconflicts.cmd 'nvim -c DiffConflicts "$MERGED" "$BASE" "$LOCAL" "$REMOTE"'
git config --global mergetool.diffconflicts.trustExitCode true
git config --global mergetool.keepBackup false

or with history:

git config --global merge.tool diffconflicts
git config --global mergetool.diffconflicts.cmd 'nvim -c DiffConflictsWithHistory "$MERGED" "$BASE" "$LOCAL" "$REMOTE"'
git config --global mergetool.diffconflicts.trustExitCode true
git config --global mergetool.keepBackup false

Configure with Jujutsu

Configure with Jujutsu

Configure Jujutsu to use this plugin as a merge tool (requires the default "diff" conflict marker style):

[merge-tools.diffconflicts]
program = "nvim"
merge-args = [
  "-c", "let g:jj_diffconflicts_marker_length=$marker_length",
  "-c", "DiffConflicts", "$output", "$base", "$left", "$right",
]
merge-tool-edits-conflict-markers = true

or with history:

[merge-tools.diffconflicts]
program = "nvim"
merge-args = [
  "-c", "let g:jj_diffconflicts_marker_length=$marker_length",
  "-c", "DiffConflictsWithHistory", "$output", "$base", "$left", "$right",
]
merge-tool-edits-conflict-markers = true

Usage

To resolve merge conflicts, run:

git mergetool

Or for Jujutsu:

jj resolve --tool diffconflicts

This will open the conflicting file in Neovim with the diffconflicts.nvim plugin enabled. You can also manually open a file and then run the command:

:DiffConflicts

This will open the current file in diff mode with the conflicts highlighted.

The left side shows the resolution, the right side shows the differences between the branches.

diffconflicts screenshot

So all you need to do is edit the left side to resolve the conflicts.

By default, saving the file (:w) will automatically advance to the next conflicting file.

If there are no conflicts left it'll quit Neovim (so your merge tool can continue).

You can customize this behavior via qol.advance_on_save and qol.quit_on_done.

To abort the merge, simply :cquit.

Lua API

You can also use the Lua API to open the diff conflicts view:

require("diffconflicts").show()
require("diffconflicts").show_history()
require("diffconflicts").show_with_history()

Real world usage

You can use the ./scripts/make-conflicts.sh script to create a sample repository with merge conflicts to test the plugin.

Usage with Git

./scripts/make-conflicts.sh git twofiles

Usage with Jujutsu

./scripts/make-conflicts.sh jj twofiles

This will create a repository in ./tmp/testrepo, with two files containing merge conflicts.

cd ./tmp/testrepo

Then you can run git mergetool or jj resolve --tool diffconflicts to test the plugin.

About

Make resolving merge conflicts in Neovim a breeze.

Topics

Resources

License

Code of conduct

Contributing

Stars

Watchers

Forks

Contributors