An Unusual Git Error I Got, And How to Fix it

Posted on Sun 16 April 2023 in Technology

Note: This article was originally written on Feburary 21, 2021.

I was working on this game I've been programming for a while when I decided to add a little feature to let the player check how good the armor that they're wearing actually is. I commit, check the 'git status' to see if there was anything that I was missing, found nothing, and pushed to my Github repo. All in all, a pretty normal experience, until I noticed an extremely abnormal bug. Instead of pushing my code, Git said "fatal: unable to read 'messed_up_hash'". For some reason I still don't understand, Git expected the commit to be under a different hash than the one it was actually under. A bit unusual, so I look up solutions. I find several solutions to fix corrupted objects, but none of them worked for me, since they assume that the hash is actually there (I checked my .git directory, there really wasn't a hash there). This brought me to what looked like the only solution I hadn't tried: delete the repo, pull from Github, and accept losing your unpushed commits. This isn't exactly a bad solution, since it works and it's easy to do, but it assumes best practice. I have (or at least had, now that this scare has fixed me up) a habit where I let commits pile up before pushing. This is not best practice. I had 8 commits piled up, one of which was extremely important and took a considerable amount of time to figure out. Dumping it wasn't an option as far as I'm concerned.

Here I decided to keep looking for solutions to my problem. Thankfully, I found one other person who had my exact same problem: Jim Schubert. In a 2012 post on his website, almost down to the exact same day that I had the problem, Jim outlines a way to fix the problem by writing the hash to Git. It's a reasonable fix, but with one problem: it didn't work on my repo. Again, no idea why, since there's no reason why it wouldn't work, but computers don't always act in logical ways. Yet again, I had to search for answers.

Suddenly, it hit me: why not just get rid of the commit? I use 'git reset' to remove it, only to find out that it needs the non-existent hash in order to remove it. Great. At this point, I'm trying to find out how to remove a commit without directly interacting with the commit when I finally find my solution: backup the problematic file, use 'git rm' to get rid of it, use your text editor of choice on the copy to undo whatever changes you made, rename the copy as the original file, use 'git add', and then run 'git commit --amend --allow-empty'. Your commit still stays, and will probably always stay, but now Git won't give you any problems about missing hashes. After running those commands, I was finally able to push to my Github repo. Here's hoping I never have to do this again.