summaryrefslogtreecommitdiff
path: root/Annex/ReplaceFile.hs
diff options
context:
space:
mode:
Diffstat (limited to 'Annex/ReplaceFile.hs')
-rw-r--r--Annex/ReplaceFile.hs35
1 files changed, 35 insertions, 0 deletions
diff --git a/Annex/ReplaceFile.hs b/Annex/ReplaceFile.hs
new file mode 100644
index 000000000..f0dfa5b27
--- /dev/null
+++ b/Annex/ReplaceFile.hs
@@ -0,0 +1,35 @@
+{- git-annex file replacing
+ -
+ - Copyright 2013 Joey Hess <joey@kitenet.net>
+ -
+ - Licensed under the GNU GPL version 3 or higher.
+ -}
+
+module Annex.ReplaceFile where
+
+import Common.Annex
+import Annex.Perms
+
+{- Replaces a possibly already existing file with a new version,
+ - atomically, by running an action.
+ -
+ - The action is passed a temp file, which it can write to, and once
+ - done the temp file is moved into place.
+ -}
+replaceFile :: FilePath -> (FilePath -> Annex ()) -> Annex ()
+replaceFile file a = do
+ tmpdir <- fromRepo gitAnnexTmpDir
+ createAnnexDirectory tmpdir
+ tmpfile <- liftIO $ do
+ (tmpfile, h) <- openTempFileWithDefaultPermissions tmpdir $
+ takeFileName file
+ hClose h
+ return tmpfile
+ a tmpfile
+ liftIO $ do
+ r <- tryIO $ rename tmpfile file
+ case r of
+ Left _ -> do
+ createDirectoryIfMissing True $ parentDir file
+ rename tmpfile file
+ _ -> noop