{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE ConstraintKinds #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE DeriveDataTypeable #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE StandaloneDeriving #-}
{-# LANGUAGE CPP #-}

-- | All types.
module Data.Conduit.Shell.Types where

import Control.Applicative
import UnliftIO.Exception
import Control.Monad
import Control.Monad.IO.Class
import Control.Monad.Trans.Class
import Control.Monad.Trans.Resource
import Data.Conduit
import Data.Typeable

-- | Shell transformer.
newtype ShellT m a = ShellT
  { ShellT m a -> ResourceT m a
runShellT :: ResourceT m a
  } deriving (Functor (ShellT m)
a -> ShellT m a
Functor (ShellT m) =>
(forall a. a -> ShellT m a)
-> (forall a b. ShellT m (a -> b) -> ShellT m a -> ShellT m b)
-> (forall a b c.
    (a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c)
-> (forall a b. ShellT m a -> ShellT m b -> ShellT m b)
-> (forall a b. ShellT m a -> ShellT m b -> ShellT m a)
-> Applicative (ShellT m)
ShellT m a -> ShellT m b -> ShellT m b
ShellT m a -> ShellT m b -> ShellT m a
ShellT m (a -> b) -> ShellT m a -> ShellT m b
(a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c
forall a. a -> ShellT m a
forall a b. ShellT m a -> ShellT m b -> ShellT m a
forall a b. ShellT m a -> ShellT m b -> ShellT m b
forall a b. ShellT m (a -> b) -> ShellT m a -> ShellT m b
forall a b c.
(a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c
forall (f :: * -> *).
Functor f =>
(forall a. a -> f a)
-> (forall a b. f (a -> b) -> f a -> f b)
-> (forall a b c. (a -> b -> c) -> f a -> f b -> f c)
-> (forall a b. f a -> f b -> f b)
-> (forall a b. f a -> f b -> f a)
-> Applicative f
forall (m :: * -> *). Applicative m => Functor (ShellT m)
forall (m :: * -> *) a. Applicative m => a -> ShellT m a
forall (m :: * -> *) a b.
Applicative m =>
ShellT m a -> ShellT m b -> ShellT m a
forall (m :: * -> *) a b.
Applicative m =>
ShellT m a -> ShellT m b -> ShellT m b
forall (m :: * -> *) a b.
Applicative m =>
ShellT m (a -> b) -> ShellT m a -> ShellT m b
forall (m :: * -> *) a b c.
Applicative m =>
(a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c
<* :: ShellT m a -> ShellT m b -> ShellT m a
$c<* :: forall (m :: * -> *) a b.
Applicative m =>
ShellT m a -> ShellT m b -> ShellT m a
*> :: ShellT m a -> ShellT m b -> ShellT m b
$c*> :: forall (m :: * -> *) a b.
Applicative m =>
ShellT m a -> ShellT m b -> ShellT m b
liftA2 :: (a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c
$cliftA2 :: forall (m :: * -> *) a b c.
Applicative m =>
(a -> b -> c) -> ShellT m a -> ShellT m b -> ShellT m c
<*> :: ShellT m (a -> b) -> ShellT m a -> ShellT m b
$c<*> :: forall (m :: * -> *) a b.
Applicative m =>
ShellT m (a -> b) -> ShellT m a -> ShellT m b
pure :: a -> ShellT m a
$cpure :: forall (m :: * -> *) a. Applicative m => a -> ShellT m a
$cp1Applicative :: forall (m :: * -> *). Applicative m => Functor (ShellT m)
Applicative, Applicative (ShellT m)
a -> ShellT m a
Applicative (ShellT m) =>
(forall a b. ShellT m a -> (a -> ShellT m b) -> ShellT m b)
-> (forall a b. ShellT m a -> ShellT m b -> ShellT m b)
-> (forall a. a -> ShellT m a)
-> Monad (ShellT m)
ShellT m a -> (a -> ShellT m b) -> ShellT m b
ShellT m a -> ShellT m b -> ShellT m b
forall a. a -> ShellT m a
forall a b. ShellT m a -> ShellT m b -> ShellT m b
forall a b. ShellT m a -> (a -> ShellT m b) -> ShellT m b
forall (m :: * -> *). Monad m => Applicative (ShellT m)
forall (m :: * -> *) a. Monad m => a -> ShellT m a
forall (m :: * -> *) a b.
Monad m =>
ShellT m a -> ShellT m b -> ShellT m b
forall (m :: * -> *) a b.
Monad m =>
ShellT m a -> (a -> ShellT m b) -> ShellT m b
forall (m :: * -> *).
Applicative m =>
(forall a b. m a -> (a -> m b) -> m b)
-> (forall a b. m a -> m b -> m b)
-> (forall a. a -> m a)
-> Monad m
return :: a -> ShellT m a
$creturn :: forall (m :: * -> *) a. Monad m => a -> ShellT m a
>> :: ShellT m a -> ShellT m b -> ShellT m b
$c>> :: forall (m :: * -> *) a b.
Monad m =>
ShellT m a -> ShellT m b -> ShellT m b
>>= :: ShellT m a -> (a -> ShellT m b) -> ShellT m b
$c>>= :: forall (m :: * -> *) a b.
Monad m =>
ShellT m a -> (a -> ShellT m b) -> ShellT m b
$cp1Monad :: forall (m :: * -> *). Monad m => Applicative (ShellT m)
Monad, a -> ShellT m b -> ShellT m a
(a -> b) -> ShellT m a -> ShellT m b
(forall a b. (a -> b) -> ShellT m a -> ShellT m b)
-> (forall a b. a -> ShellT m b -> ShellT m a)
-> Functor (ShellT m)
forall a b. a -> ShellT m b -> ShellT m a
forall a b. (a -> b) -> ShellT m a -> ShellT m b
forall (m :: * -> *) a b.
Functor m =>
a -> ShellT m b -> ShellT m a
forall (m :: * -> *) a b.
Functor m =>
(a -> b) -> ShellT m a -> ShellT m b
forall (f :: * -> *).
(forall a b. (a -> b) -> f a -> f b)
-> (forall a b. a -> f b -> f a) -> Functor f
<$ :: a -> ShellT m b -> ShellT m a
$c<$ :: forall (m :: * -> *) a b.
Functor m =>
a -> ShellT m b -> ShellT m a
fmap :: (a -> b) -> ShellT m a -> ShellT m b
$cfmap :: forall (m :: * -> *) a b.
Functor m =>
(a -> b) -> ShellT m a -> ShellT m b
Functor, Monad (ShellT m)
e -> ShellT m a
Monad (ShellT m) =>
(forall e a. Exception e => e -> ShellT m a)
-> MonadThrow (ShellT m)
forall e a. Exception e => e -> ShellT m a
forall (m :: * -> *).
Monad m =>
(forall e a. Exception e => e -> m a) -> MonadThrow m
forall (m :: * -> *). MonadThrow m => Monad (ShellT m)
forall (m :: * -> *) e a.
(MonadThrow m, Exception e) =>
e -> ShellT m a
throwM :: e -> ShellT m a
$cthrowM :: forall (m :: * -> *) e a.
(MonadThrow m, Exception e) =>
e -> ShellT m a
$cp1MonadThrow :: forall (m :: * -> *). MonadThrow m => Monad (ShellT m)
MonadThrow, Monad (ShellT m)
Monad (ShellT m) =>
(forall a. IO a -> ShellT m a) -> MonadIO (ShellT m)
IO a -> ShellT m a
forall a. IO a -> ShellT m a
forall (m :: * -> *).
Monad m =>
(forall a. IO a -> m a) -> MonadIO m
forall (m :: * -> *). MonadIO m => Monad (ShellT m)
forall (m :: * -> *) a. MonadIO m => IO a -> ShellT m a
liftIO :: IO a -> ShellT m a
$cliftIO :: forall (m :: * -> *) a. MonadIO m => IO a -> ShellT m a
$cp1MonadIO :: forall (m :: * -> *). MonadIO m => Monad (ShellT m)
MonadIO, m a -> ShellT m a
(forall (m :: * -> *) a. Monad m => m a -> ShellT m a)
-> MonadTrans ShellT
forall (m :: * -> *) a. Monad m => m a -> ShellT m a
forall (t :: (* -> *) -> * -> *).
(forall (m :: * -> *) a. Monad m => m a -> t m a) -> MonadTrans t
lift :: m a -> ShellT m a
$clift :: forall (m :: * -> *) a. Monad m => m a -> ShellT m a
MonadTrans)

deriving instance (MonadUnliftIO m) => MonadResource (ShellT m)

-- | Intentionally only handles 'ShellException'. Use normal exception
-- handling to handle usual exceptions.
instance (MonadUnliftIO (ShellT m), Applicative m, MonadThrow m) =>
         Alternative (ConduitT i o (ShellT m)) where
  empty :: ConduitT i o (ShellT m) a
empty = ShellException -> ConduitT i o (ShellT m) a
forall (m :: * -> *) e a. (MonadIO m, Exception e) => e -> m a
throwIO ShellException
ShellEmpty
  x :: ConduitT i o (ShellT m) a
x <|> :: ConduitT i o (ShellT m) a
-> ConduitT i o (ShellT m) a -> ConduitT i o (ShellT m) a
<|> y :: ConduitT i o (ShellT m) a
y = do
    Either ShellException a
r <- ConduitT i o (ShellT m) a
-> ConduitT i o (ShellT m) (Either ShellException a)
forall (m :: * -> *) e i o r.
(MonadUnliftIO m, Exception e) =>
ConduitT i o m r -> ConduitT i o m (Either e r)
tryC ConduitT i o (ShellT m) a
x
    case Either ShellException a
r of
      Left (ShellException
_ :: ShellException) -> ConduitT i o (ShellT m) a
y
      Right rr :: a
rr -> a -> ConduitT i o (ShellT m) a
forall (m :: * -> *) a. Monad m => a -> m a
return a
rr

-- | An exception resulting from a shell command.
data ShellException
  = ShellEmpty -- ^ For 'mempty'.
  | ShellExitFailure !Int -- ^ Process exited with failure.
  deriving (Typeable, Int -> ShellException -> ShowS
[ShellException] -> ShowS
ShellException -> String
(Int -> ShellException -> ShowS)
-> (ShellException -> String)
-> ([ShellException] -> ShowS)
-> Show ShellException
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [ShellException] -> ShowS
$cshowList :: [ShellException] -> ShowS
show :: ShellException -> String
$cshow :: ShellException -> String
showsPrec :: Int -> ShellException -> ShowS
$cshowsPrec :: Int -> ShellException -> ShowS
Show)

instance Exception ShellException