Create new Process instance to run specified program.
Set work directory for the process to be started
Set arguments for the process
Set process configuration
Set environment variable (specified by key) to provided value
Set configuration flag for process to be started
Set GID to run process with
Set UID to run process with
Add arguments to the process.
Execute the configured process and capture output.
Replace current process by executing program as configured by Process instance.
Pipe process
Set arguments for the process
Set process configuration
Set environemnt for the process to be started
Set environment variable (specified by key) to provided value
Set configuration flag for process to be started
Set GID to run process with
Set UID to run process with
Run process as specified user
Set work directory for the process to be started
Spawn process
Return string representation of process to be started
// It is possible to run process in following way: auto result = Process(y-program .withArgs("--verbose", "--help") .withEnv("MY_ENV_VAR", "MY_VALUE") .inWorkDir("my/working/directory") .execute() .ensureStatus!MyException("My error message on failure"); writeln(result.output);
// Also, in Posix system it is possible to run command as different user: auto result = Process(y-program .withUser("bob") .execute() .ensureStatus!MyException("My error message on failure"); writeln(result.output);
Test simple execution of the script
import std.string; import std.ascii : newline; import unit_threaded.assertions; auto temp_root = createTempPath(); scope(exit) temp_root.remove(); version(Posix) { import std.conv: octal; auto script_path = temp_root.join("test-script.sh"); script_path.writeFile( "#!" ~ nativeShell ~ newline ~ `echo "Test out: $1 $2"` ~ newline); // Add permission to run this script script_path.setAttributes(octal!755); } else version(Windows) { auto script_path = temp_root.join("test-script.cmd"); script_path.writeFile( "@echo off" ~ newline ~ "echo Test out: %1 %2" ~ newline); } // Test the case when process executes fine auto result = Process(script_path) .withArgs("Hello", "World", "test") .execute .ensureOk; result.status.should == 0; result.output.chomp.should == "Test out: Hello World"; result.isOk.shouldBeTrue; result.isNotOk.shouldBeFalse; // When we expect different successful exit-code result.isOk(42).shouldBeFalse; result.isNotOk(42).shouldBeTrue; result.ensureOk(42).shouldThrow!ProcessException;
Test simple execution of the script that handles environment variables
import std.string; import std.ascii : newline; import unit_threaded.assertions; auto temp_root = createTempPath(); scope(exit) temp_root.remove(); version(Posix) { import std.conv: octal; auto script_path = temp_root.join("test-script.sh"); script_path.writeFile( "#!" ~ nativeShell ~ newline ~ `echo "Test out: $1 $2, $MY_PARAM_1 $MY_PARAM_2"` ~ newline); // Add permission to run this script script_path.setAttributes(octal!755); } else version(Windows) { auto script_path = temp_root.join("test-script.cmd"); script_path.writeFile( "@echo off" ~ newline ~ "echo Test out: %1 %2, %MY_PARAM_1% %MY_PARAM_2%" ~ newline); } // Test the case when process executes fine auto result = Process(script_path) .withArgs("Hello") .addArgs("World") .withEnv("MY_PARAM_1", "the") .withEnv("MY_PARAM_2", "Void") .execute .ensureOk; result.status.should == 0; result.output.chomp.should == "Test out: Hello World, the Void"; result.isOk.shouldBeTrue; result.isNotOk.shouldBeFalse; // When we expect different successful exit-code result.isOk(42).shouldBeFalse; result.isNotOk(42).shouldBeTrue; result.ensureOk(42).shouldThrow!ProcessException;
This struct is used to prepare configuration for process and run it.
The following methods of running a process are supported:
- execute: run process and catch its output and exit code. - spawn: spawn the process in background, and optionally pipe its output. - pipe: spawn the process and attach configurable pipes to catch output.
The configuration of a process can be done like so:
1. Create the Process instance specifying the program to run. 2. Apply your desired configuration (args, env, workDir) via calls to one of the corresponding methods. 3. Run one of execute, spawn or pipe methods, that will actually start the process.
Configuration methods are usually prefixed with set word, but they may also have semantic aliases. For example, the method setArgs also has an alias withArgs, and the method setWorkDir has an alias inWorkDir. Additionally, configuration methods always return the reference to current instance of the Process being configured.