[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
How to use emacs as a "diff3 -m" compatible merge tool?
From: |
Tassilo Horn |
Subject: |
How to use emacs as a "diff3 -m" compatible merge tool? |
Date: |
Thu, 09 Jun 2022 12:52:20 +0200 |
User-agent: |
mu4e 1.7.26; emacs 29.0.50 |
Hi all,
there are certain tools/scripts such as Arch GNU/Linux' pacdiff which
call a user-defined tool for doing a 3-way merge. For example, pacdiff
wants to merge the current config file with the current package-provided
config file and the package-provided config file of a previous version
as a base/ancestor.
pacdiff calls the user-defined mergeprog like so:
--8<---------------cut here---------------start------------->8---
if $mergeprog "$file" "$base" "$pacfile" >"$merged"; then
msg2 "Merged without conflicts."
fi
--8<---------------cut here---------------end--------------->8---
I'd like to use emacs as mergetool so need to support these calling
convention (which are the ones of "diff3 -m"), i.e.,
1. args are MY-VERSION BASE THEIR-VERSION
2. a successful merge exits zero, an aborted merge exits non-zero
3. the merge result is printed to stdout
I've come up with two versions (ediff-merge & emerge):
--8<---------------cut here---------------start------------->8---
(defun th/command-line-ediff-merge3 (_switch)
"Do a 3-way merge using `ediff-merge-files-with-ancestor'."
(let ((make-backup-files nil)
(my-version (pop command-line-args-left))
(base-version (pop command-line-args-left))
(their-version (pop command-line-args-left)))
(ediff-merge-files-with-ancestor
my-version their-version base-version)))
(add-to-list 'command-switch-alist
'("--ediff-merge3" . th/command-line-ediff-merge3))
(defun th/command-line-emerge3 (_switch)
"Do a 3-way merge using `emerge-files-with-ancestor'."
(let* ((make-backup-files nil)
(my-version (pop command-line-args-left))
(base-version (pop command-line-args-left))
(their-version (pop command-line-args-left))
(merged (make-temp-file (concat (file-name-nondirectory my-version)
".merged"))))
(emerge-files-with-ancestor
nil my-version their-version base-version merged)))
(add-to-list 'command-switch-alist
'("--emerge3" . th/command-line-emerge3))
--8<---------------cut here---------------end--------------->8---
So now I can call "emacs --ediff-merge3 my base theirs" or "emacs
--emerge3 my base theirs" and do the merge. However, points 2 and 3
are not yet addressed.
So how to address those? I guess I need to stick a function in
ediff-quit-merge-hook and emerge-quit-hook. But then? How do I print
the merge buffer's contents to stdout? And how can I influence the exit
code? (I could do (kill-emacs my-exit-code) but would be more happy if I
could also use the merge command with emacsclient where I obviously
don't want to kill emacs.)
Bye,
Tassilo