This tutorial connects os to an Eiffel application, runs a process, handles
its result, and performs a small file-system operation.
Add os at a stable path inside the application repository:
git submodule add https://github.com/samedit66/os.git vendor/os
git submodule update --initReference it from the application ECF file:
<library name="os" location="./vendor/os/os.ecf" readonly="true"/>The process API uses Eiffel threads, so the consuming target must enable them:
<capability>
<concurrency support="thread" use="thread"/>
<void_safety support="all" use="all"/>
</capability>Build the native backends before compiling the Eiffel application:
make -C vendor/os nativeOn Windows, run the equivalent build from a regular Command Prompt:
vendor\os\build-native.cmdOS_COMMAND accepts an executable name and an argument vector. It does not
join the arguments into a shell command:
local
command: OS_COMMAND
do
create command.make ("git", <<"--version">>)
command.run
endThe bare name git is resolved through the command's environment snapshot.
run starts the child and waits until process supervision, stream I/O, and
result publication have all completed.
Use make_shell only when shell syntax is actually required. Never concatenate
untrusted input into a shell command.
After run, read the result directly from the command:
if command.successful then
io.put_string (command.stdout)
else
if command.stderr_was_captured then
io.error.put_string (command.stderr)
end
across command.failures as failure loop
io.error.put_string (failure.description)
io.error.put_new_line
end
endAll result queries require finished. In addition, exit_code requires
has_exit_code, while stdout and stderr require their corresponding
*_was_captured query. run establishes finished; asynchronous clients can
wait with wait_for_exit or observe autonomous completion through finished.
successful means all of the following:
- the child was launched;
- it produced an exit code of zero;
- it was neither terminated by the client nor timed out;
- the library recorded no failures.
A nonzero exit code is a normal child-process result, not a library failure.
Check was_launched and has_exit_code when the distinction matters.
Add an overall deadline before starting the command:
command.set_timeout_milliseconds (5_000)
command.run
if command.was_timed_out then
io.error.put_string ("git did not finish within five seconds%N")
endThe deadline includes process execution and completion of captured streams.
On expiration, os terminates the managed process tree. Use clear_timeout
before a later run when no limit is required.
An OS_COMMAND retains its configuration and can be run again after
can_start becomes true. Executions on the same command cannot overlap.
Configuration changes apply to subsequent executions:
command.set_working_directory ("/path/to/repository")
command.set_environment_variable ("CI", "true")
command.unset_environment_variable ("GIT_DIR")
command.prepend_to_path ("/path/to/toolchain/bin")
command.set_input ("input bytes%N")The command owns a copied environment snapshot. These calls do not change the current Eiffel application's environment.
Standard output and error are captured and standard input is an empty pipe by default. Stream destinations can be changed before starting:
command.inherit_stdin
command.inherit_stdout
command.discard_stderrUse capture_stdout or capture_stderr to restore capture. set_input
restores piped stdin. merge_stderr redirects stderr to the selected stdout
destination.
OS_FILE_PATH is a path value with portable file-system operations:
local
directory: OS_FILE_PATH
file: OS_FILE_PATH
do
create directory.make ("build/quick-start")
directory.create_directory
file := directory / "message.txt"
file.write_text ("Hello from os%N")
io.put_string_32 (file.text)
endcreate_directory creates missing parents. write_text writes strict UTF-8
without a byte-order mark, while text decodes strict UTF-8. Use bytes and
write_bytes for non-text data, or the explicit encoding features for another
character set.
Before calling an operation, use status queries such as exists,
is_directory, is_plain_file, and is_symbolic_link. Eiffel contracts make
invalid combinations visible during development.
The complete quick-start program and its standalone ECF file live in
examples/quick_start. From the os repository:
make gobo
make iseEach command builds the native archives, compiles the same example with the
selected compiler, and runs it. The program prints the installed Git version
and writes build/quick-start/message.txt.
Continue with the reference guide for asynchronous execution, streaming callbacks, executable lookup, termination guarantees, path traversal, and replacement semantics.