Why git is sometimes more gitty than any other git you are ever about to encounter…

So you work on a project which is version controlled and moreover it is version controlled by the almighty git himself. No matter whether you just got around all the teething problems and a steep learning curve of using git or you are a seasoned git professional – at one point or another you may find yourself in a situation where you want (or need) to:

No problem – you say? Sure – no problem as you can see if you follow the links above – nobody has ever got any problem with any of those operations. And no – using

$ git --follow

is not a solution either. Neither one knows when/where to try using some extra command line switches nor can one do it with non-command-line interfaces.. And no, unless you are a git geek, don’t even try to follow the discussions on those topics out there. The closest to something, which I felt could somehow work were a few discussions involving “filter-branch” command of git but God only knows what those dudes were really talking about. You know, this single big PITA alone can make one scream “GIVE ME MY SUBVERSION BACK!!!”

And you think there are no heroes anymore these days, don’t you? I tell you – There ARE! This awesome dude somehow made something out of this whole pile of conflicting, half-truth, semi-baked, scruffy-looking “advices” or just studied the matter on his own 😉 and came up with a shell script, which does the hardest part for you. I tried it. Sure I made a fresh pull to be up to date as action zero. Then backup of the whole directory first, then –dry-run second, then

$ git-mv-with-history myfile=mysubdirectory/

Rewrite cbb1a3111387949c0efde1540aa4565918f12f9b (1/117)

Rewrite ebb01ba7b2454a83f4e1b916384735a76cea15f9 (2/117)

[...]

Rewrite 18222fce98839724338fcdc833f3e307875eb6eb (115/117)

Rewrite 0b229d7fefa417f5b2e4975a87ea5ae69a2ebfe0 (116/117)

Rewrite e1ea07ce21b4a7ec6ba8e28dc1f5baba512bdbf2 (117/117)

Don’t forget the trailing slash if you want to move the file to a subdirectory or you may end up with your file being renamed into what you wanted a directory to be named!

I eyeballed all the files (checking them against the original clone of the repository) and the git status results..

silverdr$ git status

On branch master

Your branch and 'origin/master' have diverged,

and have 110 and 110 different commits each, respectively.

(use "git pull" to merge the remote branch into yours)

DON’T! DO! IT! I meant don’t “use git pull to merge the remote branch into yours”! Unless you want to ask for trouble, that is. Don’t try to simply push the changes either (but since your push will be most probably rejected anyway – it shouldn’t at least do much harm if you insist and try anyway). Now – what I did and it worked (but remember: YMMV!!) was:

silverdr$ git push --force origin master

Counting objects: 428, done.

Delta compression using up to 8 threads.

Compressing objects: 100% (398/398), done.

Writing objects: 100% (409/409), 562.33 KiB | 0 bytes/s, done.

Total 409 (delta 154), reused 0 (delta 0)

To https://github.com/yourowner/yourrepository.git

+ e1ea07c...8879fe2 master -> master (forced update)

silverdr$

YES – there are still heroes. Even these days…

This entry was posted in Coding, Git, Rants and tagged , . Bookmark the permalink.

5 Responses to Why git is sometimes more gitty than any other git you are ever about to encounter…

  1. This is a terrible suggestion for several reasons:

    TL;DR: Don’t do this.

    1. It rewrites commit history which will cause chaos and confusion across forks everywhere.
    2. Developers using shared branches will now not be able to pull latest of these branches, but will now have to git reset –hard or git rebase to get their work back to the new tip of the branch.
    3. Older commits that may have build scripts that depend on the file being at its ORIGINAL location will no longer work since you went back and time and moved the file since its inception. This is catastrophic for commercial products where there may be a need to go back in time and hotfix a release.

    • silverdrs says:

      Thank you for sharing, Robert. I believe that in a heavily distributed development, things like that would have to be thoroughly coordinated in order to avoid pitfalls like those you mentioned. I approved the comment so that people can see your points and be warned (!) but I am still wondering whether all the points are fully valid. While I certainly agree with point [3.], especially the fact that a certain release should remain accessible in its unchanged setup, I am not so sure about the extent of the problems mentioned in the other two. And – of course – I would very much prefer not having to do things like that. If only it was possible to move files without resorting to such methods. Unfortunately I don’t hold my breath waiting for git to allow this.

  2. Pingback: Merging Two Bitbucket Repositories | ALM Matters

  3. labmacambira says:

    git is fundamentally content-driven by design. It tells us: focus on the damn content. Don’t get emotionally attached to history. If you are often nostalgic, annotate your move commits so that you can know when to track stuff or when to use the (semi-baked) –follow when old commits don’t show in git log.

    • Jeffed says:

      One of the purposes of version control is to be able to see the history and the choices that have lead to certain content in code. Your interpretation of content-driven meaning simply that “Don’t get emotionally attached to history” is almost like saying that nothing but the present state matters. But if nothing but the present state was kept, that would quickly result in a plethora of problems especially in projects or products with lots of people and a long history.

Leave a comment