3

So, I have two directory trees, one on my desktop computer and one on my laptop. They mostly contain text files. They are supposed to be equivalent, and I try to keep them vaguely in sync, manually. It’s an inefficient method, obviously, and lacks any kind of version control.

So, I want them to be a Git repository. The problem is, the two directories aren’t identical; each one has slightly drifted from the last time I synchronized things, and my synchronizations have always been sloppy and uneven. Also, neither one is a Git repositry. So this is what I’d like to do:

  1. Make a new Git repository, of which those two directories are clones, and
  2. Reconcile the differences between the two directories, so such that any files missing from one are copied to the other, and any files that conflict I can merge manually.

This isn’t a question about merging two Git repositories—neither directory is version-tracked at present—nor is it about moving one repository inside another. This is about merging two directories into one new Git repository, using the available Git tools. Thanks!

Tina Russell
  • 143
  • 3
  • 1
    Git is not much help here. The process you are describing is sometimes called a *two way merge*. What Git does for merge is a *three way* merge, from some common starting point (see https://stackoverflow.com/q/4129049/1256452). If you had the common starting point, you'd commit that, then make a side branch for one of the two end-points and use the main branch (or a second side branch) for the other of the two end-points. But you must have the common starting point. – torek Aug 11 '18 at 00:16
  • Merge first locally, then commit to the repo. – Rodrigo Murillo Aug 11 '18 at 00:24
  • @torek - not too hard to create an effectively blank directory as a starting point, create two branches from that, copy the appropriate directory into each branch, and then merge them both back into master with prompts. I'm not really aware of a better free tool for the job, not that there isn't one... – zzxyz Aug 11 '18 at 00:25
  • @zzxyz: unfortunately, using a blank start point gives you massive add/add conflicts... – torek Aug 11 '18 at 00:53
  • @torek - I got curious, and tested some somewhat hairy scenarios..Pretty smooth. It's not Beyond Compare, but pretty smooth. I did update my answer on the chance that some of my settings may have eased things. At the end of the day, it looks like git just assumes all files should be added together, and uses whatever mergetool you specify for anything else. – zzxyz Aug 11 '18 at 01:09
  • Interesting. I tried this once (admittedly a long time ago, perhaps Git 1.8 or 1.9 era) and just got the entire file content as one big add/add conflict. – torek Aug 11 '18 at 01:14
  • @torek - updated answer...my mergetool setting may have been important (although I think vimdiff looked ok too) – zzxyz Aug 11 '18 at 01:23

1 Answers1

2

This basic idea works...There are probably better approaches.

create new repository (start in new, empty directory):

git init
touch .gitignore #give git something to commit
git add .
git commit -m "blank directory"

create branch for directory 1:

git checkout -b dir1
touch a b c #<3 example files..replace this command by copying directory 1 in here
git add .
git commit -m "directory 1"

create branch for directory 2:

git checkout master # very important...start directory 2 from master
git checkout -b dir2
touch c d e #<3 example files..one of which overlaps..again, replace with appropriate directory
git add .
git commit -m "directory 2"

merge branches:

git checkout master
git merge dir1
git merge dir2

New master directory:

>ls -a
a  b  c  d  e  .gitignore

Note that I did try a more sophisticated merge (out of curiousity) after first post. Seemed to work quite well with subdirectories, files with different contents, etc. One important caveat may be that i have the following line in my .gitconfig file:

[diff]
        algorithm = minimal
[merge]
        tool = vimdiff
[mergetool "diffconflicts"]
        cmd = vim -c DiffConflicts \"$MERGED\" \"$BASE\" \"$LOCAL\" \"$REMOTE\"
        trustExitCode = true

I used the diffconflicts tool (a vim plugin) for this one git mergetool -t diffconflicts. It performs an at least mostly two-way merge based on diff markers. It does know about the base but I'm not sure to what degree it cares. Various other tools that are git compatible can perform two-way merges as well.

zzxyz
  • 2,953
  • 1
  • 16
  • 31
  • 1
    Thanks! This worked for me. I used “meld” as my merge tool, with the default Git three-way merges. When I needed to resolve a merge conflict, I just picked whatever I wanted from the left and right columns to add to the (initially blank) middle column. – Tina Russell Aug 11 '18 at 18:03