package prox
Provides classes to work with system processes in a type safe way.
Overview
A system process to be started is represented by the Process case class, taking a command and optionally a list of arguments and a working directory:
import io.github.vigoo.prox._ import io.github.vigoo.prox.syntax._ val process = Process("echo", List("Hello world"))
To start the process, we can use the syntax.ProcessOps.start extension method, defined in syntax.ProcessOps, which creates a cats IO operation returning a RunningProcess instance.
Use the returned value to wait for the process to exit or to send a termination signal to it:
val program = Blocker[IO].use { blocker => for { echo <- Process("echo", List("Hello world")).start(blocker) result <- echo.waitForExit() } yield result.exitCode } val exitCode = program.unsafeRunSync()
Redirection
The syntax.ProcessNodeInputRedirect, syntax.ProcessNodeOutputRedirect and syntax.ProcessNodeErrorRedirect classes define extension methods for processes to redirect their inpout, output and error streams. The target of redirection can be anything that has the matching type class defined for: CanBeProcessInputSource, CanBeProcessOutputTarget and CanBeProcessErrorTarget.
The three extension methods are syntax.ProcessNodeInputRedirect.<, syntax.ProcessNodeOutputRedirect.> and syntax.ProcessNodeErrorRedirect.redirectErrorTo
The type system guarantees that each redirection can only happen once for a process.
Streams
The library provides type classes to redirect to/from fs2 streams: InputStreamingSource for feeding a stream as a process' input, and OutputStreamingTarget and ErrorStreamingTarget to feed a process' output and error to fs2 pipes.
Three special wrapper types can be used to modify how the streams are executed when the IO operation is composed:
- Drain to run the stream with fs2.Stream.CompileOps.drain, having a result of Unit
- ToVector to run the stream with fs2.Stream.CompileOps.toVector, having a result of Vector
- Fold to run the stream with fs2.Stream.CompileOps.fold, having a custom fold result
If none of the above wrappers is used, the default is to use fs2.Stream.CompileOps.drain for fs2.Sink, fs2.Stream.CompileOps.foldMonoid if the pipe's output is a cats.Monoid and fs2.Stream.CompileOps.toVector otherwise.
Piping
The syntax.ProcessNodeOutputRedirect class defined two extension methods for piping one process to another: syntax.ProcessNodeOutputRedirect.| for direct piping and syntax.ProcessNodeOutputRedirect.via for piping through a custom fs2 fs2.Pipe.
The result of the piping operators is a PipedProcess, which can be used exactly as a simple process, but its syntax.ProcessOps.start method returns a tuple of RunningProcess instances.
- Alphabetic
- By Inheritance
- prox
- AnyRef
- Any
- Hide All
- Show All
- Public
- All
Type Members
- trait CanBeProcessErrorTarget[F[_], To] extends AnyRef
Type class for creating error redirection handlers
Type class for creating error redirection handlers
- To
Type to be used as a target
- trait CanBeProcessInputSource[F[_], From] extends AnyRef
Type class for creating input redirection handlers
Type class for creating input redirection handlers
By providing an instance of this type class, a value of type From can be used to redirect the input channel of a process to.
- From
Type to be used as an input source
- trait CanBeProcessOutputTarget[F[_], To] extends AnyRef
Type class for creating output redirection handlers
Type class for creating output redirection handlers
- To
Type to be used as a target
- trait ContextOf[PN] extends AnyRef
- case class Drain[F[_], O](pipe: Pipe[F, Byte, O]) extends Product with Serializable
Wraps a pipe to modify how the stream is executed
Wraps a pipe to modify how the stream is executed
If a pipe used as an output or error target is wrapped by Drain, the stream will be executed by fs2.Stream.CompileOps.drain and the result type will be Unit.
- O
Stream element type
- pipe
The pipe to wrap
- abstract class ErrorStreamingTarget[F[_], Err] extends OutputStreamingTargetBase[[_]F[_], Err]
Error target implementation using a stream pipe as the target
Error target implementation using a stream pipe as the target
- Err
Stream output element type
- class FileSource[F[_]] extends ProcessInputSource[F]
Input source implementation of using a file as input
- class FileTarget[F[_]] extends ProcessOutputTarget[F, Byte, Unit] with ProcessErrorTarget[F, Byte, Unit]
Output/error target implementation for using a file as the target
- final case class FlushChunks[F[_]](stream: Stream[F, Byte]) extends Product with Serializable
Wrapper for input streams that enables flushing the process pipe stream after each chunk of bytes.
Wrapper for input streams that enables flushing the process pipe stream after each chunk of bytes.
This is useful for interactive processes, as the pipe stream has a 8K buffer on it.
- stream
The input stream for the process
- class FlushControlledInputStreamingSource[F[_]] extends ProcessInputSource[F]
Input source implementation that calls 'flush' after each chunk of bytes.
Input source implementation that calls 'flush' after each chunk of bytes. Useful for interactive communication with processes.
- case class Fold[F[_], O, R](pipe: Pipe[F, Byte, O], init: R, f: (R, O) => R) extends Product with Serializable
Wraps the pipe to modify how the stream is executed
Wraps the pipe to modify how the stream is executed
If a pipe used as an output or error target is wrapped by Fold, the stream will be executed by fs2.Stream.CompileOps.fold and the result type will be the result type of the provided fold function.
- O
Stream element type
- R
Fold result type
- pipe
The pipe to wrap
- init
Initial value for the fold
- f
The fold function
- class InputStreamingSource[F[_]] extends ProcessInputSource[F]
Input source implementation of using a byte stream as input
- trait LowPriorityCanBeProcessErrorTarget extends LowerPriorityCanBeProcessErrorTarget
- trait LowPriorityCanBeProcessOutputTarget extends LowerPriorityCanBeProcessOutputTarget
- trait LowerPriorityCanBeProcessErrorTarget extends AnyRef
- trait LowerPriorityCanBeProcessOutputTarget extends AnyRef
- trait NotRedirected extends RedirectionState
Indicates that the given channel is not redirected yet
- abstract class OutputStreamingTarget[F[_], Out] extends OutputStreamingTargetBase[[_]F[_], Out]
Output target implementation using a stream pipe as the target
Output target implementation using a stream pipe as the target
- Out
Stream output element type
- abstract class OutputStreamingTargetBase[F[_], Out] extends AnyRef
Base class for output/error target implementations using a stream pipe as the target
Base class for output/error target implementations using a stream pipe as the target
- Out
Stream output element type
- class PipeBuilder[F[_], PN <: ProcessNode[_, _, _, NotRedirected, _]] extends AnyRef
Helper class for customizing the pipe between two processes
Helper class for customizing the pipe between two processes
See the syntax object for an example.
- PN
Type of the first process
- case class PipeConstruction[F[_], Out](outStream: Stream[F, Out]) extends Product with Serializable
Holds information required to start a piped process
Holds information required to start a piped process
- Out
Element type of the piping stream
- outStream
Output stream of the first process, to be used as the input stream of the second one
- class PipedProcess[F[_], Out, Err, PN1Out, PN1 <: ProcessNode[_, _, _, _, _], PN2 <: ProcessNode[_, _, _, _, _], IRS <: RedirectionState, ORS <: RedirectionState, ERS <: RedirectionState] extends ProcessNode[Out, Err, IRS, ORS, ERS]
Represents two process piped together
Represents two process piped together
Do not construct PipedProcess directly. Use the syntax.ProcessNodeOutputRedirect.| or syntax.ProcessNodeOutputRedirect.via methods.
- Out
Output stream element type
- Err
Error stream element type
- PN1Out
Output stream element type of the first process
- PN1
Type of the first process
- PN2
Type of the second process
- IRS
Input channel redirection state
- ORS
Output channel redirection state
- ERS
Error channel redirection state
- trait Piping[F[_], PN1 <: ProcessNode[_, _, _, NotRedirected, _], PN2 <: ProcessNode[_, _, NotRedirected, _, _]] extends AnyRef
Type class for piping one process to another
Type class for piping one process to another
- PN1
First process type
- PN2
Second process type
- class Process[F[_], Out, Err, OutResult, ErrResult, IRS <: RedirectionState, ORS <: RedirectionState, ERS <: RedirectionState] extends ProcessNode[Out, Err, IRS, ORS, ERS]
Represents a single system process
Represents a single system process
Do not construct Process directly. Use the companion object instead.
- Out
Output stream element type
- Err
Error stream element type
- OutResult
Result type of running the output stream
- ErrResult
Result type of running the error stream
- IRS
Input channel redirection state
- ORS
Output channel redirection state
- ERS
Error channel redirection state
- trait ProcessErrorTarget[F[_], O, R] extends ProcessIO[F, O, R]
Base trait for error redirection handlers
Base trait for error redirection handlers
- O
The redirection stream element type
- R
Result type we get by running the redirection stream
- trait ProcessIO[F[_], O, R] extends AnyRef
Base trait for redirection handlers
Base trait for redirection handlers
- O
The redirection stream element type
- R
Result type we get by running the redirection stream
- trait ProcessInputSource[F[_]] extends ProcessIO[F, Byte, Unit]
Base trait for input redirection handlers
- sealed trait ProcessNode[Out, Err, IRS <: RedirectionState, ORS <: RedirectionState, ERS <: RedirectionState] extends AnyRef
Base trait for simple and piped processes
Base trait for simple and piped processes
To work with processes, use the extension methods defined in the syntax object.
- Out
Output stream element type
- Err
Error stream element type
- IRS
Input channel redirection state
- ORS
Output channel redirection state
- ERS
Error channel redirection state
- trait ProcessOutputTarget[F[_], O, R] extends ProcessIO[F, O, R]
Base trait for output redirection handlers
Base trait for output redirection handlers
- O
The redirection stream element type
- R
Result type we get by running the redirection stream
- case class ProcessResult[OutResult, ErrResult](exitCode: Int, fullOutput: OutResult, fullError: ErrResult) extends Product with Serializable
Holds information about a terminated process
Holds information about a terminated process
See OutputStreamingTarget and ErrorStreamingTarget for more information about the fullOutput and fullError fields.
- OutResult
Result type of running the redirected output stream. Unit if there is no such result.
- ErrResult
Result type of running the redirected error stream. Unit if there is no such result.
- exitCode
Exit code the process returned with
- fullOutput
Depending on the output redirection, the result of running the output stream
- fullError
Depending on the error redirection, the result of running the error stream
- trait RedirectError[F[_], PN <: ProcessNode[_, _, _, _, NotRedirected], To, NewErr, NewErrResult] extends AnyRef
Type class for redirecting the error channel of a process
Type class for redirecting the error channel of a process
The redirection is encoded in the process type and can be performed only once.
- PN
The process to modify
- To
Type of the output target to redirect to
- NewErr
Error stream element type
- NewErrResult
Result of running the error stream
- trait RedirectInput[F[_], PN <: ProcessNode[_, _, NotRedirected, _, _]] extends AnyRef
Type class for redirecting the input channel of a process
Type class for redirecting the input channel of a process
The redirection is encoded in the process type and can be performed only once.
- PN
The process to modify
- trait RedirectOutput[F[_], PN <: ProcessNode[_, _, _, NotRedirected, _], To, NewOut, NewOutResult] extends AnyRef
Type class for redirecting the output channel of a process
Type class for redirecting the output channel of a process
The redirection is encoded in the process type and can be performed only once.
- PN
The process to modify
- To
Type of the output target to redirect to
- NewOut
Output stream element type
- NewOutResult
Result of running the output stream
- trait Redirected extends RedirectionState
Indicates that the given channel has already been redirected
- sealed trait RedirectionState extends AnyRef
Phantom type representing the redirection state of a process
- trait RunningProcess[F[_], Out, OutResult, ErrResult] extends AnyRef
Interface to a running process
Interface to a running process
Always represents a single running system process, in case of process piping each participant of the pipe gets its own RunningProcess instance.
All the operations are running in the IO monad.
The result of the process can be acquied by either waiting for it to terminate or terminating it. The result will be contained by a ProcessResult object.
- F
Context
- Out
Output stream element type
- OutResult
Result type of running the redirected output stream. Unit if there is no such result.
- ErrResult
Result type of running the redirected error stream. Unit if there is no such result.
- trait Start[F[_], PN] extends AnyRef
Type class for starting processes
Type class for starting processes
- PN
Process type
- class StdError[F[_]] extends ProcessErrorTarget[F, Byte, Unit]
Default implementation of ProcessErrorTarget representing no redirection
- class StdIn[F[_]] extends ProcessInputSource[F]
Default input source representing no redirection
- class StdOut[F[_]] extends ProcessOutputTarget[F, Byte, Unit]
Default implementation of ProcessOutputTarget representing no redirection
- case class ToVector[F[_], O](pipe: Pipe[F, Byte, O]) extends Product with Serializable
Wraps a pipe to modify how the stream is executed
Wraps a pipe to modify how the stream is executed
If a pipe used as an output or error target is wrapped by ToVector, the stream will be executed by fs2.Stream.CompileOps.toVector and the result type will be a Vector of its element type.
- O
Stream element type
- pipe
The pipe to wrap
Value Members
- object CanBeProcessErrorTarget extends LowPriorityCanBeProcessErrorTarget
Instances of the CanBeProcessErrorTarget type class
Instances of the CanBeProcessErrorTarget type class
There are instances for the following types:
- java.nio.file.Path to redirect the error channel to a file
- fs2.Sink to redirect the error channel to a sink. The result type is Unit.
- fs2.Pipe if the pipe's output element type is a cats.Monoid. The result type is its element type.
- fs2.Pipe if the pipe's output element type is not a cats.Monoid. The result type is a Vector of its element type.
- Drain
- ToVector
- Fold
- object CanBeProcessInputSource
Instances of the CanBeProcessInputSource type class
Instances of the CanBeProcessInputSource type class
There are instances for the following types:
- java.nio.file.Path to use a file as input - fs2.Stream to use a byte stream as input
- object CanBeProcessOutputTarget extends LowPriorityCanBeProcessOutputTarget
Instances of the CanBeProcessOutputTarget type class
Instances of the CanBeProcessOutputTarget type class
There are instances for the following types:
- java.nio.file.Path to redirect the output to a file
- fs2.Sink to redirect the output to a sink. The result type is Unit.
- fs2.Pipe if the pipe's output element type is a cats.Monoid. The result type is its element type.
- fs2.Pipe if the pipe's output element type is not a cats.Monoid. The result type is a Vector of its element type.
- Drain
- ToVector
- Fold
- object ContextOf
- object Piping
- object Process
Factory object for Process
- object RedirectError
- object RedirectInput
- object RedirectOutput
- object Start
- object syntax
Implicit classes for working with simple and piped processes
Implicit classes for working with simple and piped processes
All the operations are implemented for both simple Process objects and PipedProcess objects as well. Most of the operations encode information in the types of the processes as well.
The operations are implemented by various type classes and exposed through extension methods defined in the implicit classes in this object.
Examples
Starting simple and piped processes:
val echoProcess = Process("echo", List("This is an output")) val wordCountProcess = Process("wc", List("-w")) val combined = echoProcess | wordCountProcess for { echo1 <- Process("echo", List("Hello world")).start runningProcs <- combined.start (echo2, wordCount) = runningProcs } yield ()
Redirecting input, output and error channels:
val p1 = Process("echo", List("Hello world")) > (home / "tmp" / "out.txt") val p2 = Process("cat") < (home / "something") val p3 = Process("make") errorTo (home / "errors.log")
Piping:
val echoProcess = Process("echo", List("This is an output")) val wordCountProcess = Process("wc", List("-w")) val combined1 = echoProcess | wordCountProcess val customPipe: Pipe[IO, Byte, Byte] = ??? val combined2 = echoProcess.via(customPipe).to(wordCountProcess)