module HaskellWorks.Polysemy.System.Process
  ( IO.CreateProcess(..),
    IO.CmdSpec(..),
    IO.StdStream(..),
    Handle,
    ProcessHandle,
    ExitCode(..),
    FD,
    Pid,
    createProcess,
    createProcess_,
    IO.shell,
    IO.proc,
    callProcess,
    callCommand,
    spawnProcess,
    spawnCommand,
    readCreateProcess,
    readProcess,
    readCreateProcessWithExitCode,
    readProcessWithExitCode,
    cleanupProcess,
    getPid,
    getCurrentPid,
    interruptProcessGroupOf,
    createPipe,
    createPipeFd,
    runProcess,
    runCommand,
    runInteractiveProcess,
    runInteractiveCommand,
    system,
    rawSystem,

    waitSecondsForProcess,

  ) where

import qualified Control.Exception             as CE
import           HaskellWorks.Error
import           HaskellWorks.Error.Types
import qualified HaskellWorks.IO.Process       as IO
import           HaskellWorks.Polysemy.Prelude
import           Polysemy
import           Polysemy.Error
import           Polysemy.Log
import           System.Exit                   (ExitCode (..))
import           System.IO                     (Handle)
import           System.Posix.Internals        (FD)
import qualified System.Process                as IO
import           System.Process                (Pid, ProcessHandle)

createProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => IO.CreateProcess
  -> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
createProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
CreateProcess
-> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
createProcess CreateProcess
cp = do
  Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
r <- IO
  (Either
     IOException
     (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
-> Sem
     r
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO
   (Either
      IOException
      (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
 -> Sem
      r
      (Either
         IOException
         (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)))
-> IO
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
-> Sem
     r
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
 -> IO
      (Either
         IOException
         (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)))
-> IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
-> IO
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ CreateProcess
-> IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
IO.createProcess CreateProcess
cp
  Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
-> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
r

createProcess_ :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> IO.CreateProcess
  -> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
createProcess_ :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String
-> CreateProcess
-> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
createProcess_ String
cmd CreateProcess
cp = do
  Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
r <- IO
  (Either
     IOException
     (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
-> Sem
     r
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO
   (Either
      IOException
      (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
 -> Sem
      r
      (Either
         IOException
         (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)))
-> IO
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
-> Sem
     r
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
 -> IO
      (Either
         IOException
         (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)))
-> IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
-> IO
     (Either
        IOException
        (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ String
-> CreateProcess
-> IO (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
IO.createProcess_ String
cmd CreateProcess
cp
  Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
-> Sem r (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either
  IOException
  (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
r

callProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> [String]
  -> Sem r ()
callProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> [String] -> Sem r ()
callProcess String
cmd [String]
args = do
  Either IOException ()
r <- IO (Either IOException ()) -> Sem r (Either IOException ())
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ()) -> Sem r (Either IOException ()))
-> IO (Either IOException ()) -> Sem r (Either IOException ())
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO () -> IO (Either IOException ()))
-> IO () -> IO (Either IOException ())
forall a b. (a -> b) -> a -> b
$ String -> [String] -> IO ()
IO.callProcess String
cmd [String]
args
  Either IOException () -> Sem r ()
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ()
r

callCommand :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> Sem r ()
callCommand :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> Sem r ()
callCommand String
cmd = do
  Either IOException ()
r <- IO (Either IOException ()) -> Sem r (Either IOException ())
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ()) -> Sem r (Either IOException ()))
-> IO (Either IOException ()) -> Sem r (Either IOException ())
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO () -> IO (Either IOException ()))
-> IO () -> IO (Either IOException ())
forall a b. (a -> b) -> a -> b
$ String -> IO ()
IO.callCommand String
cmd
  Either IOException () -> Sem r ()
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ()
r

spawnProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> [String]
  -> Sem r ProcessHandle
spawnProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> [String] -> Sem r ProcessHandle
spawnProcess String
cmd [String]
args = do
  Either IOException ProcessHandle
r <- IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ProcessHandle)
 -> Sem r (Either IOException ProcessHandle))
-> IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ProcessHandle -> IO (Either IOException ProcessHandle))
-> IO ProcessHandle -> IO (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ String -> [String] -> IO ProcessHandle
IO.spawnProcess String
cmd [String]
args
  Either IOException ProcessHandle -> Sem r ProcessHandle
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ProcessHandle
r

spawnCommand :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> Sem r ProcessHandle
spawnCommand :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> Sem r ProcessHandle
spawnCommand String
cmd = do
  Either IOException ProcessHandle
r <- IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ProcessHandle)
 -> Sem r (Either IOException ProcessHandle))
-> IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ProcessHandle -> IO (Either IOException ProcessHandle))
-> IO ProcessHandle -> IO (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ String -> IO ProcessHandle
IO.spawnCommand String
cmd
  Either IOException ProcessHandle -> Sem r ProcessHandle
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ProcessHandle
r

readCreateProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => IO.CreateProcess
  -> String
  -> Sem r String
readCreateProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
CreateProcess -> String -> Sem r String
readCreateProcess CreateProcess
cp String
input = do
  Either IOException String
r <- IO (Either IOException String) -> Sem r (Either IOException String)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException String)
 -> Sem r (Either IOException String))
-> IO (Either IOException String)
-> Sem r (Either IOException String)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO String -> IO (Either IOException String))
-> IO String -> IO (Either IOException String)
forall a b. (a -> b) -> a -> b
$ CreateProcess -> String -> IO String
IO.readCreateProcess CreateProcess
cp String
input
  Either IOException String -> Sem r String
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException String
r

readProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> [String]
  -> String
  -> Sem r String
readProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> [String] -> String -> Sem r String
readProcess String
cmd [String]
args String
input = do
  Either IOException String
r <- IO (Either IOException String) -> Sem r (Either IOException String)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException String)
 -> Sem r (Either IOException String))
-> IO (Either IOException String)
-> Sem r (Either IOException String)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO String -> IO (Either IOException String))
-> IO String -> IO (Either IOException String)
forall a b. (a -> b) -> a -> b
$ String -> [String] -> String -> IO String
IO.readProcess String
cmd [String]
args String
input
  Either IOException String -> Sem r String
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException String
r

readCreateProcessWithExitCode :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => IO.CreateProcess
  -> String
  -> Sem r (ExitCode, String, String)
readCreateProcessWithExitCode :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
CreateProcess -> String -> Sem r (ExitCode, String, String)
readCreateProcessWithExitCode CreateProcess
cp String
input = do
  Either IOException (ExitCode, String, String)
r <- IO (Either IOException (ExitCode, String, String))
-> Sem r (Either IOException (ExitCode, String, String))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (ExitCode, String, String))
 -> Sem r (Either IOException (ExitCode, String, String)))
-> IO (Either IOException (ExitCode, String, String))
-> Sem r (Either IOException (ExitCode, String, String))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (ExitCode, String, String)
 -> IO (Either IOException (ExitCode, String, String)))
-> IO (ExitCode, String, String)
-> IO (Either IOException (ExitCode, String, String))
forall a b. (a -> b) -> a -> b
$ CreateProcess -> String -> IO (ExitCode, String, String)
IO.readCreateProcessWithExitCode CreateProcess
cp String
input
  Either IOException (ExitCode, String, String)
-> Sem r (ExitCode, String, String)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (ExitCode, String, String)
r

readProcessWithExitCode :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> [String]
  -> String
  -> Sem r (ExitCode, String, String)
readProcessWithExitCode :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> [String] -> String -> Sem r (ExitCode, String, String)
readProcessWithExitCode String
cmd [String]
args String
input = do
  Either IOException (ExitCode, String, String)
r <- IO (Either IOException (ExitCode, String, String))
-> Sem r (Either IOException (ExitCode, String, String))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (ExitCode, String, String))
 -> Sem r (Either IOException (ExitCode, String, String)))
-> IO (Either IOException (ExitCode, String, String))
-> Sem r (Either IOException (ExitCode, String, String))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (ExitCode, String, String)
 -> IO (Either IOException (ExitCode, String, String)))
-> IO (ExitCode, String, String)
-> IO (Either IOException (ExitCode, String, String))
forall a b. (a -> b) -> a -> b
$ String -> [String] -> String -> IO (ExitCode, String, String)
IO.readProcessWithExitCode String
cmd [String]
args String
input
  Either IOException (ExitCode, String, String)
-> Sem r (ExitCode, String, String)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (ExitCode, String, String)
r

cleanupProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
  -> Sem r ()
cleanupProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
(Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle)
-> Sem r ()
cleanupProcess (Maybe Handle
mIn, Maybe Handle
mOut, Maybe Handle
mErr, ProcessHandle
ph) = do
  Either IOException ()
r <- IO (Either IOException ()) -> Sem r (Either IOException ())
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ()) -> Sem r (Either IOException ()))
-> IO (Either IOException ()) -> Sem r (Either IOException ())
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO () -> IO (Either IOException ()))
-> IO () -> IO (Either IOException ())
forall a b. (a -> b) -> a -> b
$ (Maybe Handle, Maybe Handle, Maybe Handle, ProcessHandle) -> IO ()
IO.cleanupProcess (Maybe Handle
mIn, Maybe Handle
mOut, Maybe Handle
mErr, ProcessHandle
ph)
  Either IOException () -> Sem r ()
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ()
r

getPid :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => ProcessHandle
  -> Sem r (Maybe Pid)
getPid :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
ProcessHandle -> Sem r (Maybe Pid)
getPid ProcessHandle
ph = do
  Either IOException (Maybe Pid)
r <- IO (Either IOException (Maybe Pid))
-> Sem r (Either IOException (Maybe Pid))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (Maybe Pid))
 -> Sem r (Either IOException (Maybe Pid)))
-> IO (Either IOException (Maybe Pid))
-> Sem r (Either IOException (Maybe Pid))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Maybe Pid) -> IO (Either IOException (Maybe Pid)))
-> IO (Maybe Pid) -> IO (Either IOException (Maybe Pid))
forall a b. (a -> b) -> a -> b
$ ProcessHandle -> IO (Maybe Pid)
IO.getPid ProcessHandle
ph
  Either IOException (Maybe Pid) -> Sem r (Maybe Pid)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (Maybe Pid)
r

getCurrentPid :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => Sem r Pid
getCurrentPid :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
Sem r Pid
getCurrentPid = do
  Either IOException Pid
r <- IO (Either IOException Pid) -> Sem r (Either IOException Pid)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException Pid) -> Sem r (Either IOException Pid))
-> IO (Either IOException Pid) -> Sem r (Either IOException Pid)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO Pid -> IO (Either IOException Pid))
-> IO Pid -> IO (Either IOException Pid)
forall a b. (a -> b) -> a -> b
$ IO Pid
IO.getCurrentPid
  Either IOException Pid -> Sem r Pid
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException Pid
r

interruptProcessGroupOf :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => ProcessHandle
  -> Sem r ()
interruptProcessGroupOf :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
ProcessHandle -> Sem r ()
interruptProcessGroupOf ProcessHandle
ph = do
  Either IOException ()
r <- IO (Either IOException ()) -> Sem r (Either IOException ())
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ()) -> Sem r (Either IOException ()))
-> IO (Either IOException ()) -> Sem r (Either IOException ())
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO () -> IO (Either IOException ()))
-> IO () -> IO (Either IOException ())
forall a b. (a -> b) -> a -> b
$ ProcessHandle -> IO ()
IO.interruptProcessGroupOf ProcessHandle
ph
  Either IOException () -> Sem r ()
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ()
r

createPipe :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => Sem r (Handle, Handle)
createPipe :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
Sem r (Handle, Handle)
createPipe = do
  Either IOException (Handle, Handle)
r <- IO (Either IOException (Handle, Handle))
-> Sem r (Either IOException (Handle, Handle))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (Handle, Handle))
 -> Sem r (Either IOException (Handle, Handle)))
-> IO (Either IOException (Handle, Handle))
-> Sem r (Either IOException (Handle, Handle))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Handle, Handle) -> IO (Either IOException (Handle, Handle)))
-> IO (Handle, Handle) -> IO (Either IOException (Handle, Handle))
forall a b. (a -> b) -> a -> b
$ IO (Handle, Handle)
IO.createPipe
  Either IOException (Handle, Handle) -> Sem r (Handle, Handle)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (Handle, Handle)
r

createPipeFd :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => Sem r (FD, FD)
createPipeFd :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
Sem r (FD, FD)
createPipeFd = do
  Either IOException (FD, FD)
r <- IO (Either IOException (FD, FD))
-> Sem r (Either IOException (FD, FD))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (FD, FD))
 -> Sem r (Either IOException (FD, FD)))
-> IO (Either IOException (FD, FD))
-> Sem r (Either IOException (FD, FD))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (FD, FD) -> IO (Either IOException (FD, FD)))
-> IO (FD, FD) -> IO (Either IOException (FD, FD))
forall a b. (a -> b) -> a -> b
$ IO (FD, FD)
IO.createPipeFd
  Either IOException (FD, FD) -> Sem r (FD, FD)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (FD, FD)
r

runProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => FilePath
  -> [String]
  -> Maybe FilePath
  -> Maybe [(String, String)]
  -> Maybe Handle
  -> Maybe Handle
  -> Maybe Handle
  -> Sem r ProcessHandle
runProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String
-> [String]
-> Maybe String
-> Maybe [(String, String)]
-> Maybe Handle
-> Maybe Handle
-> Maybe Handle
-> Sem r ProcessHandle
runProcess String
cmd [String]
args Maybe String
mbStdIn Maybe [(String, String)]
mbEnv Maybe Handle
mbCwd Maybe Handle
mbStdOut Maybe Handle
mbStdErr = do
  Either IOException ProcessHandle
r <- IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ProcessHandle)
 -> Sem r (Either IOException ProcessHandle))
-> IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ProcessHandle -> IO (Either IOException ProcessHandle))
-> IO ProcessHandle -> IO (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ String
-> [String]
-> Maybe String
-> Maybe [(String, String)]
-> Maybe Handle
-> Maybe Handle
-> Maybe Handle
-> IO ProcessHandle
IO.runProcess String
cmd [String]
args Maybe String
mbStdIn Maybe [(String, String)]
mbEnv Maybe Handle
mbCwd Maybe Handle
mbStdOut Maybe Handle
mbStdErr
  Either IOException ProcessHandle -> Sem r ProcessHandle
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ProcessHandle
r

runCommand :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> Sem r ProcessHandle
runCommand :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> Sem r ProcessHandle
runCommand String
cmd = do
  Either IOException ProcessHandle
r <- IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ProcessHandle)
 -> Sem r (Either IOException ProcessHandle))
-> IO (Either IOException ProcessHandle)
-> Sem r (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ProcessHandle -> IO (Either IOException ProcessHandle))
-> IO ProcessHandle -> IO (Either IOException ProcessHandle)
forall a b. (a -> b) -> a -> b
$ String -> IO ProcessHandle
IO.runCommand String
cmd
  Either IOException ProcessHandle -> Sem r ProcessHandle
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ProcessHandle
r

runInteractiveProcess :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => FilePath
  -> [String]
  -> Maybe FilePath
  -> Maybe [(String, String)]
  -> Sem r (Handle, Handle, Handle, ProcessHandle)
runInteractiveProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String
-> [String]
-> Maybe String
-> Maybe [(String, String)]
-> Sem r (Handle, Handle, Handle, ProcessHandle)
runInteractiveProcess String
cmd [String]
args Maybe String
mbCwd Maybe [(String, String)]
mbEnv = do
  Either IOException (Handle, Handle, Handle, ProcessHandle)
r <- IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
-> Sem
     r (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
 -> Sem
      r (Either IOException (Handle, Handle, Handle, ProcessHandle)))
-> IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
-> Sem
     r (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Handle, Handle, Handle, ProcessHandle)
 -> IO (Either IOException (Handle, Handle, Handle, ProcessHandle)))
-> IO (Handle, Handle, Handle, ProcessHandle)
-> IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ String
-> [String]
-> Maybe String
-> Maybe [(String, String)]
-> IO (Handle, Handle, Handle, ProcessHandle)
IO.runInteractiveProcess String
cmd [String]
args Maybe String
mbCwd Maybe [(String, String)]
mbEnv
  Either IOException (Handle, Handle, Handle, ProcessHandle)
-> Sem r (Handle, Handle, Handle, ProcessHandle)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (Handle, Handle, Handle, ProcessHandle)
r

runInteractiveCommand :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> Sem r (Handle, Handle, Handle, ProcessHandle)
runInteractiveCommand :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> Sem r (Handle, Handle, Handle, ProcessHandle)
runInteractiveCommand String
cmd = do
  Either IOException (Handle, Handle, Handle, ProcessHandle)
r <- IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
-> Sem
     r (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
 -> Sem
      r (Either IOException (Handle, Handle, Handle, ProcessHandle)))
-> IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
-> Sem
     r (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO (Handle, Handle, Handle, ProcessHandle)
 -> IO (Either IOException (Handle, Handle, Handle, ProcessHandle)))
-> IO (Handle, Handle, Handle, ProcessHandle)
-> IO (Either IOException (Handle, Handle, Handle, ProcessHandle))
forall a b. (a -> b) -> a -> b
$ String -> IO (Handle, Handle, Handle, ProcessHandle)
IO.runInteractiveCommand String
cmd
  Either IOException (Handle, Handle, Handle, ProcessHandle)
-> Sem r (Handle, Handle, Handle, ProcessHandle)
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException (Handle, Handle, Handle, ProcessHandle)
r

system :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> Sem r ExitCode
system :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> Sem r ExitCode
system String
cmd = do
  Either IOException ExitCode
r <- IO (Either IOException ExitCode)
-> Sem r (Either IOException ExitCode)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ExitCode)
 -> Sem r (Either IOException ExitCode))
-> IO (Either IOException ExitCode)
-> Sem r (Either IOException ExitCode)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ExitCode -> IO (Either IOException ExitCode))
-> IO ExitCode -> IO (Either IOException ExitCode)
forall a b. (a -> b) -> a -> b
$ String -> IO ExitCode
IO.system String
cmd
  Either IOException ExitCode -> Sem r ExitCode
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ExitCode
r

rawSystem :: ()
  => Member (Embed IO) r
  => Member (Error IOException) r
  => String
  -> [String]
  -> Sem r ExitCode
rawSystem :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error IOException) r) =>
String -> [String] -> Sem r ExitCode
rawSystem String
cmd [String]
args = do
  Either IOException ExitCode
r <- IO (Either IOException ExitCode)
-> Sem r (Either IOException ExitCode)
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (IO (Either IOException ExitCode)
 -> Sem r (Either IOException ExitCode))
-> IO (Either IOException ExitCode)
-> Sem r (Either IOException ExitCode)
forall a b. (a -> b) -> a -> b
$ forall e a. Exception e => IO a -> IO (Either e a)
CE.try @IOException (IO ExitCode -> IO (Either IOException ExitCode))
-> IO ExitCode -> IO (Either IOException ExitCode)
forall a b. (a -> b) -> a -> b
$ String -> [String] -> IO ExitCode
IO.rawSystem String
cmd [String]
args
  Either IOException ExitCode -> Sem r ExitCode
forall e (r :: EffectRow) a.
Member (Error e) r =>
Either e a -> Sem r a
fromEither Either IOException ExitCode
r

waitSecondsForProcess :: ()
  => Member (Embed IO) r
  => Member (Error GenericError) r
  => Member (Error IOException) r
  => Member (Error TimedOut) r
  => Member Log r
  => Int
  -> ProcessHandle
  -> Sem r (Maybe ExitCode)
waitSecondsForProcess :: forall (r :: EffectRow).
(Member (Embed IO) r, Member (Error GenericError) r,
 Member (Error IOException) r, Member (Error TimedOut) r,
 Member Log r) =>
Int -> ProcessHandle -> Sem r (Maybe ExitCode)
waitSecondsForProcess Int
seconds ProcessHandle
hProcess =
  IO (Either TimedOut (Maybe ExitCode))
-> Sem r (Either TimedOut (Maybe ExitCode))
forall (m :: * -> *) (r :: EffectRow) a.
Member (Embed m) r =>
m a -> Sem r a
embed (Int -> ProcessHandle -> IO (Either TimedOut (Maybe ExitCode))
IO.waitSecondsForProcess Int
seconds ProcessHandle
hProcess)
    Sem r (Either TimedOut (Maybe ExitCode))
-> (Sem r (Either TimedOut (Maybe ExitCode))
    -> Sem r (Maybe ExitCode))
-> Sem r (Maybe ExitCode)
forall a b. a -> (a -> b) -> b
& forall e a (m :: * -> *).
Monad m =>
(e -> m a) -> m (Either e a) -> m a
onLeftM @TimedOut TimedOut -> Sem r (Maybe ExitCode)
forall e (r :: EffectRow) a. Member (Error e) r => e -> Sem r a
throw