module Git.Repository where

import Control.Monad
import Control.Monad.IO.Class
import Control.Monad.IO.Unlift
import Git.Types
import System.Directory
import UnliftIO.Exception

withNewRepository :: (MonadGit r n, MonadUnliftIO n, MonadUnliftIO m)
                  => RepositoryFactory n m r
                  -> FilePath -> n a -> m a
withNewRepository :: RepositoryFactory n m r -> FilePath -> n a -> m a
withNewRepository RepositoryFactory n m r
factory FilePath
path n a
action = do
    IO () -> m ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> IO () -> m ()
forall a b. (a -> b) -> a -> b
$ do
        Bool
exists <- FilePath -> IO Bool
doesDirectoryExist FilePath
path
        Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
exists (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ FilePath -> IO ()
removeDirectoryRecursive FilePath
path

    -- we want exceptions to leave the repo behind
    a
a <- RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
forall r (n :: * -> *) (m :: * -> *) a.
(MonadGit r n, MonadUnliftIO n, MonadUnliftIO m) =>
RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
withRepository' RepositoryFactory n m r
factory RepositoryOptions :: FilePath -> Maybe FilePath -> Bool -> Bool -> RepositoryOptions
RepositoryOptions
        { repoPath :: FilePath
repoPath       = FilePath
path
        , repoWorkingDir :: Maybe FilePath
repoWorkingDir = Maybe FilePath
forall a. Maybe a
Nothing
        , repoIsBare :: Bool
repoIsBare     = Bool
True
        , repoAutoCreate :: Bool
repoAutoCreate = Bool
True
        } n a
action

    IO () -> m ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> IO () -> m ()
forall a b. (a -> b) -> a -> b
$ do
        Bool
exists <- FilePath -> IO Bool
doesDirectoryExist FilePath
path
        Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
exists (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ FilePath -> IO ()
removeDirectoryRecursive FilePath
path

    a -> m a
forall (m :: * -> *) a. Monad m => a -> m a
return a
a

withNewRepository' :: (MonadGit r n, MonadUnliftIO n, MonadUnliftIO m)
                   => RepositoryFactory n m r -> FilePath -> n a -> m a
withNewRepository' :: RepositoryFactory n m r -> FilePath -> n a -> m a
withNewRepository' RepositoryFactory n m r
factory FilePath
path n a
action =
    m () -> m () -> m a -> m a
forall (m :: * -> *) a b c.
MonadUnliftIO m =>
m a -> m b -> m c -> m c
bracket_ m ()
recover m ()
recover (m a -> m a) -> m a -> m a
forall a b. (a -> b) -> a -> b
$
        RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
forall r (n :: * -> *) (m :: * -> *) a.
(MonadGit r n, MonadUnliftIO n, MonadUnliftIO m) =>
RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
withRepository' RepositoryFactory n m r
factory RepositoryOptions :: FilePath -> Maybe FilePath -> Bool -> Bool -> RepositoryOptions
RepositoryOptions
            { repoPath :: FilePath
repoPath       = FilePath
path
            , repoWorkingDir :: Maybe FilePath
repoWorkingDir = Maybe FilePath
forall a. Maybe a
Nothing
            , repoIsBare :: Bool
repoIsBare     = Bool
True
            , repoAutoCreate :: Bool
repoAutoCreate = Bool
True
            } n a
action
  where
    recover :: m ()
recover = IO () -> m ()
forall (m :: * -> *) a. MonadIO m => IO a -> m a
liftIO (IO () -> m ()) -> IO () -> m ()
forall a b. (a -> b) -> a -> b
$ do
        Bool
exists <- FilePath -> IO Bool
doesDirectoryExist FilePath
path
        Bool -> IO () -> IO ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when Bool
exists (IO () -> IO ()) -> IO () -> IO ()
forall a b. (a -> b) -> a -> b
$ FilePath -> IO ()
removeDirectoryRecursive FilePath
path

withRepository' :: (MonadGit r n, MonadUnliftIO n, MonadUnliftIO m)
                => RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
withRepository' :: RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
withRepository' RepositoryFactory n m r
factory RepositoryOptions
opts n a
action = do
    r
repo <- RepositoryFactory n m r -> RepositoryOptions -> m r
forall (n :: * -> *) (m :: * -> *) r.
RepositoryFactory n m r -> RepositoryOptions -> m r
openRepository RepositoryFactory n m r
factory RepositoryOptions
opts
    RepositoryFactory n m r -> r -> n a -> m a
forall (n :: * -> *) (m :: * -> *) r.
RepositoryFactory n m r -> forall a. r -> n a -> m a
runRepository RepositoryFactory n m r
factory r
repo (n a -> m a) -> n a -> m a
forall a b. (a -> b) -> a -> b
$ n a
action n a -> n () -> n a
forall (m :: * -> *) a b. MonadUnliftIO m => m a -> m b -> m a
`finally` n ()
forall r (m :: * -> *). MonadGit r m => m ()
closeRepository

withRepository :: (MonadGit r n, MonadUnliftIO n, MonadUnliftIO m)
               => RepositoryFactory n m r -> FilePath -> n a -> m a
withRepository :: RepositoryFactory n m r -> FilePath -> n a -> m a
withRepository RepositoryFactory n m r
factory FilePath
path =
    RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
forall r (n :: * -> *) (m :: * -> *) a.
(MonadGit r n, MonadUnliftIO n, MonadUnliftIO m) =>
RepositoryFactory n m r -> RepositoryOptions -> n a -> m a
withRepository' RepositoryFactory n m r
factory RepositoryOptions
defaultRepositoryOptions { repoPath :: FilePath
repoPath = FilePath
path }