NAME
git-annex undo - undo last change to a file or directory
SYNOPSIS
git annex [filename|directory] ...
DESCRIPTION
When passed a filename, undoes the last change that was made to that file.
When passed a directory, undoes the last change that was made to the contents of that directory.
Running undo a second time will undo the undo, returning the working tree to the same state it had before. To support undoing an undo of staged changes, any staged changes are first committed by the undo command.
Note that this does not undo get/drop of a file's content; it only operates on the file tree committed to git.
OPTIONS
--json
Enable JSON output. This is intended to be parsed by programs that use git-annex. Each line of output is a JSON object.
--json-error-messages
Messages that would normally be output to standard error are included in the JSON instead.
The git-annex-common-options(1) can also be used.
SEE ALSO
git-annex(1)
AUTHOR
Joey Hess id@joeyh.name
Warning: Automatically converted into a man page by mdwn2man. Edit with care.
Hello,
Context
Thank you for git-annex. I'm progressing in learning how to use it. Seems to work as intended with only annexed files.
I actually need mixed content repository and like the idea of
annex.largefiles
deciding which files go into the annex.While experimenting with mixed content repository, I had
git-annex-undo
destroy information twice. Or perhaps I did something wrong?What happened
Here's my .gitattributes
I had a directory (say,
newdir
) with some jpg and some other files, not known by git or git-annex so far.Based on https://git-annex.branchable.com/tips/largefiles/ I expected both
git add
andgit annex add
to add NEF JPG jpg to the annex, and other files as regular git files.In case of problem, I expected
git annex undo
to revert state to the one just before the last command (which is: full of my regular files, not symlinks or empty).git add newdir
added them all as regular files, not partly in the annex as expected. Surprised, I wanted to undo and try another command.git annex undo
emptiednewdir
completely. Wow! Fortunately these were copies, else they would have been gone forever! To be fair I have not checked at that point if files had been copied in annex, which as only copy would still be a mess because file names would have been lost anyway.I used
git reset <hash>
to revert state git-style, checked withgit status
that state was indeed back to pre-add (newdir empty, not known to git), then copied the files again from their source.git annex add newdir
added them all as annexed files, replacing with links, not partly as regular files as expected.git annex undo
emptiednewdir
completely. I expected my regular files back in place.I had the intended result by using
git add
on regular files andgit annex add
to add files to be annexed. As if.gitattributes
were absent.git-annex compiled on Debian unstable as of 2016-10-13 from git source, commit 3135d35094aa5453ef7a5f12762e00e0139a6dbb.
Questions
git annex add
behave as intended by you? Wasn't it supposed to automatically decide which files go to the annex?git annex undo
behave as intended by you? Wasn't it supposed to revert working directory to the state just before the wrong "add"?.gitattributes
,add
commands correctly?Thank you.
Adding this to
.gitattributes
:Causes
git-annex add
to behave as expected. Questions aboutgit annex undo
behavior remain.git annex undo
undoes the last change that was committed to the file. If the file has staged changes,git annex undo
first commits those changes (to avoid losing data) and then undoes that commit.The reason that
git annex undo
deleted the files from your working tree is that the previous commit did not have those files in it, and it undid to the state at that commit.So, you will never lose the content of a file by running
git annex undo
. Ifgit annex undo
deletes a file, you can always get it back by checking out a previous version of the branch. Or even by runninggit annex undo
a second time, to undo the undo.Hello Joey.
Thank you for your answer. It makes things clearer. I believe the documentation should reflect it.
Where the bug (1) is: not defining the level of operation
Ah, committed. That's an important information. It's not at all what I expected from reading the page.
I was expecting tree-level undo, not commit-level undo. I've found the bug: The documentation for git-annex undo does not define "undo" or the level at which it operates.
Suggestion (1): define the level of operation
What if the documentation included something like this?
Case (2) of staged changes
This sounds strange.
So, if I call git-annex-undo to undo a commit A, but there are staged changes, git-annex-undo will add a commit B then add another commit C to undo B?
This will not undo A.
What use case where you thinking of?
Case of staged changes: suggestion (2)
Perhaps in case when file has staged changes, it would be better to display a warning message, perhaps with a
--commit-staged
option to bypass it.Internal rationale: got it
Ok I understand the data was not lost. But this kind of reasoning is only reachable when one knows what git-annex-undo really does. So, this command is still dangerous to the unsavvy. Perhaps document that?
Issue (3): What was actually needed (all this time)
It seems that what I really needed was git-annex-unannex.
Suggested changes to documentation (3)
Perhaps in case when file has staged changes, it would be better to display a warning message and suggest using git-annex-unannex instead?
Conclusion
What do you think about the 3 issues and fix suggestions?
Thanks again.
git-annex
has started to become useful here.