6 ms·
To my knowledge, reflog won't help you get back uncommitted work that you nuked with git-reset --hard. Of course --hard is not on by default so... there is no
by jlgreco 13y ago
To my knowledge, reflog won't help you get back uncommitted work that you nuked with git-reset --hard.
Of course --hard is not on by default so... there is no issue here with git's default behaviour.
> "Git's model is remarkably simple, and that simplicity is the source of many of its benefits. Every other VCS out there is more complex."
Yup, exactly. The simplicity of git's model is hugely important. It allows me to not only know what git will or will not allow me to do (knowledge that in other systems is acquired by studying the docs for each particular command to see what all the flags do) but also lets me figure out what sort of novel operations are possible if I am willing to write a little code of my own.
Example: Update hook that only allows a push if two or more colleagues of the committer have pushed annotations for that commit already? With little more than my knowledge of git's data model, and what update hooks are in the first place, I know that can be done and I know how I could do it.
- tednaleid 13y agoThat's not correct, you can get back to any ref in the reflog, including those that you moved away from with git-reset --hard. Those commits are just dangling but are easy to get back to. I've got a presentation [1] that goes into how to use the reflog and how the various flags in reset work (among other things) that could explain more. [1]: http://tednaleid.github.io/showoff-git-core-concepts/ http://tednaleid.github.io/showoff-git-core-concepts/
- jlgreco 13y agoMy point is that git-reset --hard can remove data from the working tree filesystem that never hit the DAG in the first place: $ git init Initialized empty Git repository in /home/john/tmp2/.git/ $ echo "foo" > foo $ git add foo $ git commit -m 'init' [master (root-commit) 84fb5d1] init ... $ echo "bar" >>foo $ cat foo foo bar $ git reset --hard HEAD HEAD is now at 84fb5d1 init $ git reflog 84fb5d1 HEAD@{0}: commit (initial): init $ git status # On branch master nothing to commit (working directory clean)
- tednaleid 13y agoOk, yes, I agree with that clarification (and I missed that you specified in your original comment "uncommitted work", my mistake). If you git reset --hard and you have a dirty working directory, you can absolutely blow work away. That's one of the main reasons to use git reset --hard, but I agree that it needs to be used with intention. The easiest way to protect against it is to never use it if you have a dirty working directory, always commit first and then reset --hard after you've committed.
- acjohnson55 13y agoI guess maybe the counterargument is that perhaps this should happen invisibly and automatically.
- skriticos2 13y agoYou just ran a script that scattered production / sensitive information in your source files. You definitely don't want to get that into history and get the last head state back.. Yes, you can delete the working tree and check out head again, but than again, git reset --hard pretty much does that and it's welcome at times.
- Skinney 13y agoWell, there is to my knowledge no other vcs that does this. Mercurial will hapily blow your changes away if you do a hg update -C. If you want your changes to stick around, you do a git stash first.
- ajross 13y agoThis is true, but seems specious. By this definition (development tools that can irrecoverably destroy data in the working directory) you should be flaming against vim too, not to mention rm or the dreaded "clean" target to make. It just seems silly, sorry. And while I know little about hg I suspect it's not even true: hg will never delete a file it doesn't understand? What about the equivalent of git clean (which I use daily -- it's loss would be a minor hardship and definitely not an advantage for mercurial)?
- fennecfoxen 13y agoI'd recommend learning "git reset --keep" instead of --hard because of this reason.
- jlgreco 13y agoCertainly. --hard should only be used if you actually want what --hard provides.
- sampo 13y ago> To my knowledge, reflog won't help you get back uncommitted work that you nuked with git-reset --hard. Every version control system has a way to overwrite a dirty (modified) work directory, so git is hardly any more dangerous than any other tool. It also won't help you get back uncommitted files that you destroy with `rm`. No other tool does, either.
- jlgreco 13y agoTo be clear, I think that the behaviour of git-reset --hard is absolutely appropriate. I am just correcting the overly strong statement: "No matter if you rebase, reset --hard, or any other "destructive" operation, you can always get back to your prior state with nothing but a quick look in the reflog." There are situations that reflog won't get you back from, but those situations are perfectly logical and appropriate exceptions.
- rocky1138 13y agoYou can actually get back files that you rm. I've seen it done. Apparently it has something to do with unmounting the drive, restarting in single-user mode, then finding/knowing where it is on the drive before the OS overwrites it (hence the unmount).
- TylerE 13y agoDoesn't generally work with modern FS's that use more "clever" allocation schemes.
- willvarfar 13y agoYeah there's not a lot of tooling for it. I recall writing my own to analyse a disk image to find traces of an intrusion, so its possible if you put in the leg work even for modern complex FS that do stuff like store small files inline in inodes.
- Dylan16807 13y agoI'm not sure what you mean. The 'clever' filesystems I'm aware of are copy-on-write, which makes it much easier to recover deleted files. Unclever filesystems, like NTFS, are also quite easy to recover files on. I've had to do so multiple times.
- nbouscal 13y agoYou're completely right, I should have clarified that I was only talking about committed data. My mistake.