{- git-annex command - - Copyright 2010-2024 Joey Hess - - Licensed under the GNU AGPL version 3 or higher. -} {-# LANGUAGE CPP #-} module Command.PreCommit where import Command import qualified Command.Fix import qualified Command.Smudge import Annex.Hook import Annex.Link import Annex.View import Annex.View.ViewedFile import Logs.View import Logs.MetaData import Types.View import Types.MetaData import qualified Annex import qualified Annex.Branch import qualified Data.Set as S import qualified Data.Text as T cmd :: Command cmd = noCommit $ command "pre-commit" SectionPlumbing "run by git pre-commit hook" paramPaths (withParams seek) seek :: CmdParams -> CommandSeek seek ps = do let ww = WarnUnmatchWorkTreeItems "pre-commit" l <- workTreeItems ww ps -- fix symlinks to files being committed flip (withFilesToBeCommitted ww) l $ \(si, f) -> commandAction $ maybe stop (Command.Fix.start Command.Fix.FixSymlinks si f) =<< isAnnexLink f -- after a merge conflict or git cherry-pick or stash, pointer -- files in the worktree won't be populated, so populate them here Command.Smudge.updateSmudged (Restage False) runAnnexHook preCommitAnnexHook -- committing changes to a view updates metadata currentView >>= \case Nothing -> noop Just (v, _madj) -> do withViewChanges (addViewMetaData v) (removeViewMetaData v) -- Manually commit in this case, because -- noCommit prevents automatic commit. whenM (annexAlwaysCommit <$> Annex.getGitConfig) $ Annex.Branch.commit =<< Annex.Branch.commitMessage addViewMetaData :: View -> ViewedFile -> Key -> CommandStart addViewMetaData v f k = starting "metadata" ai si $ next $ changeMetaData k $ fromView v f where ai = mkActionItem (k, toRawFilePath f) si = SeekInput [] removeViewMetaData :: View -> ViewedFile -> Key -> CommandStart removeViewMetaData v f k = starting "metadata" ai si $ next $ changeMetaData k $ unsetMetaData $ fromView v f where ai = mkActionItem (k, toRawFilePath f) si = SeekInput [] changeMetaData :: Key -> MetaData -> CommandCleanup changeMetaData k metadata = do showMetaDataChange metadata addMetaData k metadata return True showMetaDataChange :: MetaData -> Annex () showMetaDataChange = showLongNote . UnquotedString . unlines . concatMap showmeta . fromMetaData where showmeta (f, vs) = map (showmetavalue f) $ S.toList vs showmetavalue f v = T.unpack (fromMetaField f) <> showset v <> "=" <> decodeBS (fromMetaValue v) showset v | isSet v = "+" | otherwise = "-"