summaryrefslogtreecommitdiff
path: root/Command/PreCommit.hs
diff options
context:
space:
mode:
authorGravatar Joey Hess <joey@kitenet.net>2013-02-06 12:40:59 -0400
committerGravatar Joey Hess <joey@kitenet.net>2013-02-06 12:44:19 -0400
commit48d59dbad11a2f99a0003f5f3bd93734429be11d (patch)
treeef74a5cb149d78c8dc3e74732ae52f5afb73f274 /Command/PreCommit.hs
parent6be68947dcf80c99ed5135c1a968641dca199555 (diff)
pre-commit: Update direct mode mappings.
Making the pre-commit hook look at git diff-index to find changed direct mode files and update the mappings works pretty well. One case where it does not work is when a file is git annex added, and then git rmed, and then this is committed. That's a no-op commit, so the hook probably doesn't even run, and it certianly never notices that the file was deleted, so the mapping will still have the original filename in it. For this and other reasons, it's important that the mappings still be treated as possibly inconsistent. Also, the assistant now allows the pre-commit hook to run when in direct mode, so the mappings also get updated there.
Diffstat (limited to 'Command/PreCommit.hs')
-rw-r--r--Command/PreCommit.hs38
1 files changed, 29 insertions, 9 deletions
diff --git a/Command/PreCommit.hs b/Command/PreCommit.hs
index 7ecf496a9..23b6ecc0a 100644
--- a/Command/PreCommit.hs
+++ b/Command/PreCommit.hs
@@ -1,6 +1,6 @@
{- git-annex command
-
- - Copyright 2010 Joey Hess <joey@kitenet.net>
+ - Copyright 2010, 2013 Joey Hess <joey@kitenet.net>
-
- Licensed under the GNU GPL version 3 or higher.
-}
@@ -11,22 +11,42 @@ import Common.Annex
import Command
import qualified Command.Add
import qualified Command.Fix
+import qualified Git.DiffTree
+import Annex.CatFile
+import Annex.Content.Direct
+import Git.Sha
def :: [Command]
def = [command "pre-commit" paramPaths seek "run by git pre-commit hook"]
-{- The pre-commit hook needs to fix symlinks to all files being committed.
- - And, it needs to inject unlocked files into the annex. -}
seek :: [CommandSeek]
seek =
+ -- fix symlinks to files being committed
[ whenNotDirect $ withFilesToBeCommitted $ whenAnnexed $ Command.Fix.start
- , whenNotDirect $ withFilesUnlockedToBeCommitted start]
+ -- inject unlocked files into the annex
+ , whenNotDirect $ withFilesUnlockedToBeCommitted startIndirect
+ -- update direct mode mappings for committed files
+ , whenDirect $ withWords startDirect
+ ]
-start :: FilePath -> CommandStart
-start file = next $ perform file
-
-perform :: FilePath -> CommandPerform
-perform file = do
+startIndirect :: FilePath -> CommandStart
+startIndirect file = next $ do
unlessM (doCommand $ Command.Add.start file) $
error $ "failed to add " ++ file ++ "; canceling commit"
next $ return True
+
+startDirect :: [String] -> CommandStart
+startDirect _ = next $ do
+ (diffs, clean) <- inRepo $ Git.DiffTree.diffIndex
+ forM_ diffs go
+ next $ liftIO clean
+ where
+ go diff = do
+ withkey (Git.DiffTree.srcsha diff) removeAssociatedFile
+ withkey (Git.DiffTree.dstsha diff) addAssociatedFile
+ where
+ withkey sha a = when (sha /= nullSha) $ do
+ k <- catKey sha
+ case k of
+ Nothing -> noop
+ Just key -> void $ a key (Git.DiffTree.file diff)