-}
module Annex.Action (
+ action,
+ verifiedAction,
startup,
shutdown,
stopCoProcesses,
import Annex.HashObject
import Annex.CheckIgnore
+{- Runs an action that may throw exceptions, catching and displaying them. -}
+action :: Annex () -> Annex Bool
+action a = tryNonAsync a >>= \case
+ Right () -> return True
+ Left e -> do
+ warning (show e)
+ return False
+
+verifiedAction :: Annex Verification -> Annex (Bool, Verification)
+verifiedAction a = tryNonAsync a >>= \case
+ Right v -> return (True, v)
+ Left e -> do
+ warning (show e)
+ return (False, UnVerified)
+
+
{- Actions to perform each time ran. -}
startup :: Annex ()
startup = return ()
return (Just (k', ok))
checkDiskSpaceToGet k Nothing $
notifyTransfer Download af $
- download (Remote.uuid remote) k af stdRetry $ \p' ->
+ download' (Remote.uuid remote) k af stdRetry $ \p' ->
withTmp k $ downloader p'
-- The file is small, so is added to git, so while importing
return Nothing
checkDiskSpaceToGet tmpkey Nothing $
notifyTransfer Download af $
- download (Remote.uuid remote) tmpkey af stdRetry $ \p ->
+ download' (Remote.uuid remote) tmpkey af stdRetry $ \p ->
withTmp tmpkey $ \tmpfile ->
metered (Just p) tmpkey $
const (rundownload tmpfile)
module Annex.Transfer (
module X,
upload,
+ upload',
alwaysUpload,
download,
+ download',
runTransfer,
alwaysRunTransfer,
noRetry,
import Logs.Transfer as X
import Types.Transfer as X
import Annex.Notification as X
+import Annex.Content
import Annex.Perms
+import Annex.Action
import Utility.Metered
import Utility.ThreadScheduler
import Annex.LockPool
import qualified System.FilePath.ByteString as P
import Data.Ord
-upload :: Observable v => UUID -> Key -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> NotifyWitness -> Annex v
-upload u key f d a _witness = guardHaveUUID u $
+upload :: Remote -> Key -> AssociatedFile -> RetryDecider -> NotifyWitness -> Annex Bool
+upload r key f d = upload' (Remote.uuid r) key f d $
+ action . Remote.storeKey r key f
+
+upload' :: Observable v => UUID -> Key -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> NotifyWitness -> Annex v
+upload' u key f d a _witness = guardHaveUUID u $
runTransfer (Transfer Upload u (fromKey id key)) f d a
alwaysUpload :: Observable v => UUID -> Key -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> NotifyWitness -> Annex v
alwaysUpload u key f d a _witness = guardHaveUUID u $
alwaysRunTransfer (Transfer Upload u (fromKey id key)) f d a
-download :: Observable v => UUID -> Key -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> NotifyWitness -> Annex v
-download u key f d a _witness = guardHaveUUID u $
+download :: Remote -> Key -> AssociatedFile -> RetryDecider -> NotifyWitness -> Annex Bool
+download r key f d witness =
+ getViaTmp (Remote.retrievalSecurityPolicy r) (RemoteVerify r) key f $ \dest ->
+ download' (Remote.uuid r) key f d (go dest) witness
+ where
+ go dest p = verifiedAction $
+ Remote.retrieveKeyFile r key f (fromRawFilePath dest) p
+
+download' :: Observable v => UUID -> Key -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> NotifyWitness -> Annex v
+download' u key f d a _witness = guardHaveUUID u $
runTransfer (Transfer Download u (fromKey id key)) f d a
guardHaveUUID :: Observable v => UUID -> Annex v -> Annex v
alwaysRunTransfer = runTransfer' True
runTransfer' :: Observable v => Bool -> Transfer -> AssociatedFile -> RetryDecider -> (MeterUpdate -> Annex v) -> Annex v
-runTransfer' ignorelock t afile retrydecider transferaction = enteringStage TransferStage $ debugLocks $ checkSecureHashes t $ do
+runTransfer' ignorelock t afile retrydecider transferaction = enteringStage TransferStage $ debugLocks $ preCheckSecureHashes t $ do
info <- liftIO $ startTransferInfo afile
(meter, tfile, createtfile, metervar) <- mkProgressUpdater t info
mode <- annexFileMode
- still contains content using an insecure hash, remotes will likewise
- tend to be configured to reject it, so Upload is also prevented.
-}
-checkSecureHashes :: Observable v => Transfer -> Annex v -> Annex v
-checkSecureHashes t a = ifM (isCryptographicallySecure (transferKey t))
+preCheckSecureHashes :: Observable v => Transfer -> Annex v -> Annex v
+preCheckSecureHashes t a = ifM (isCryptographicallySecure (transferKey t))
( a
, ifM (annexSecureHashesOnly <$> Annex.getGitConfig)
( do
let cleanuptmp = pruneTmpWorkDirBefore tmp (liftIO . removeWhenExistsWith R.removeLink)
showNote "using youtube-dl"
Transfer.notifyTransfer Transfer.Download url $
- Transfer.download webUUID mediakey (AssociatedFile Nothing) Transfer.noRetry $ \p ->
+ Transfer.download' webUUID mediakey (AssociatedFile Nothing) Transfer.noRetry $ \p ->
youtubeDl url (fromRawFilePath workdir) p >>= \case
Right (Just mediafile) -> do
cleanuptmp
checkDiskSpaceToGet dummykey Nothing $ do
tmp <- fromRepo $ gitAnnexTmpObjectLocation dummykey
ok <- Transfer.notifyTransfer Transfer.Download url $
- Transfer.download u dummykey afile Transfer.stdRetry $ \p -> do
+ Transfer.download' u dummykey afile Transfer.stdRetry $ \p -> do
createAnnexDirectory (parentDir tmp)
downloader (fromRawFilePath tmp) p
if ok
sent <- tryNonAsync $ case ek of
AnnexKey k -> ifM (inAnnex k)
( notifyTransfer Upload af $
- upload (uuid r) k af stdRetry $ \pm -> do
+ upload' (uuid r) k af stdRetry $ \pm -> do
let rollback = void $
performUnexport r db [ek] loc
sendAnnex k rollback $ \f ->
import Command
import qualified Remote
-import Annex.Content
import Annex.Transfer
import Annex.NumCopies
import Annex.Wanted
| Remote.hasKeyCheap r =
either (const False) id <$> Remote.hasKey r key
| otherwise = return True
- docopy r witness = getViaTmp (Remote.retrievalSecurityPolicy r) (RemoteVerify r) key afile $ \dest ->
- download (Remote.uuid r) key afile stdRetry
- (\p -> do
- showAction $ "from " ++ Remote.name r
- Remote.verifiedAction $
- Remote.retrieveKeyFile r key afile (fromRawFilePath dest) p
- ) witness
+ docopy r witness = do
+ showAction $ "from " ++ Remote.name r
+ download r key afile stdRetry witness
Right False -> logMove srcuuid destuuid False key $ \deststartedwithcopy -> do
showAction $ "to " ++ Remote.name dest
ok <- notifyTransfer Upload afile $
- upload (Remote.uuid dest) key afile stdRetry $
- Remote.action . Remote.storeKey dest key afile
+ upload dest key afile stdRetry
if ok
then finish deststartedwithcopy $
Remote.logStatus dest key InfoPresent
then dispatch removewhen deststartedwithcopy True
else dispatch removewhen deststartedwithcopy =<< get
where
- get = notifyTransfer Download afile $
- download (Remote.uuid src) key afile stdRetry $ \p ->
- getViaTmp (Remote.retrievalSecurityPolicy src) (RemoteVerify src) key afile $ \t ->
- Remote.verifiedAction $ Remote.retrieveKeyFile src key afile (fromRawFilePath t) p
+ get = notifyTransfer Download afile $
+ download src key afile stdRetry
dispatch _ _ False = stop -- failed
dispatch RemoveNever _ True = next $ return True -- copy complete
toPerform :: Key -> AssociatedFile -> Remote -> CommandPerform
toPerform key file remote = go Upload file $
- upload (uuid remote) key file stdRetry $ \p -> do
+ upload' (uuid remote) key file stdRetry $ \p -> do
tryNonAsync (Remote.storeKey remote key file p) >>= \case
Right () -> do
Remote.logStatus remote key InfoPresent
fromPerform :: Key -> AssociatedFile -> Remote -> CommandPerform
fromPerform key file remote = go Upload file $
- download (uuid remote) key file stdRetry $ \p ->
+ download' (uuid remote) key file stdRetry $ \p ->
getViaTmp (retrievalSecurityPolicy remote) (RemoteVerify remote) key file $ \t ->
tryNonAsync (Remote.retrieveKeyFile remote key file (fromRawFilePath t) p) >>= \case
Right v -> return (True, v)
where
runner (TransferRequest direction _ keydata file) remote
| direction == Upload = notifyTransfer direction file $
- upload (Remote.uuid remote) key file stdRetry $ \p -> do
+ upload' (Remote.uuid remote) key file stdRetry $ \p -> do
tryNonAsync (Remote.storeKey remote key file p) >>= \case
Left e -> do
warning (show e)
Remote.logStatus remote key InfoPresent
return True
| otherwise = notifyTransfer direction file $
- download (Remote.uuid remote) key file stdRetry $ \p ->
+ download' (Remote.uuid remote) key file stdRetry $ \p ->
getViaTmp (Remote.retrievalSecurityPolicy remote) (RemoteVerify remote) key file $ \t -> do
r <- tryNonAsync (Remote.retrieveKeyFile remote key file (fromRawFilePath t) p) >>= \case
Left e -> do
let rsp = RetrievalAllKeysSecure
v <- tryNonAsync $ do
let runtransfer ti =
- Right <$> transfer download k af (\p ->
+ Right <$> transfer download' k af (\p ->
getViaTmp rsp DefaultVerify k af $ \tmp ->
storefile (fromRawFilePath tmp) o l getb validitycheck p ti)
let fallback = return $ Left $
import Types.Remote
import qualified Annex
import Annex.UUID
+import Annex.Action
import Logs.UUID
import Logs.Trust
import Logs.Location hiding (logStatus)
import Git.Types (RemoteName, ConfigKey(..), fromConfigValue)
import Utility.Aeson
-{- Runs an action that may throw exceptions, catching and displaying them. -}
-action :: Annex () -> Annex Bool
-action a = tryNonAsync a >>= \case
- Right () -> return True
- Left e -> do
- warning (show e)
- return False
-
-verifiedAction :: Annex Verification -> Annex (Bool, Verification)
-verifiedAction a = tryNonAsync a >>= \case
- Right v -> return (True, v)
- Left e -> do
- warning (show e)
- return (False, UnVerified)
-
{- Map from UUIDs of Remotes to a calculated value. -}
remoteMap :: (Remote -> v) -> Annex (M.Map UUID v)
remoteMap mkv = remoteMap' mkv (pure . mkk)