module EDSL:sig
..end
type'a
t ='a Language.t
val string : string -> string t
val int : int -> int t
val bool : bool -> bool t
val call : string t list -> unit t
Note that UNIX does not allow strings passed as arguments to
executables to contain NUL-characters ('\x00'
).
The function Language.to_many_lines
raises an exception
if an argument is a literal and contains a NUL, but if the
argument is the result of some other expression the behavior is
for now undefined.
val exec : string list -> unit t
EDSL.call
but with string literals; i.e. exec ["a"; "b"]
is
actually call [string "a"; string "b"]
which is the usual shell command
"a b"
(with proper escaping).val getenv : string t -> string t
val setenv : var:string t -> string t -> unit t
If the ~var
argument is not a valid variable name or if the value does
not fit in a shell variable (newlines, '\000'
), behavior is undefined.
val (&&&) : bool t -> bool t -> bool t
val (|||) : bool t -> bool t -> bool t
val not : bool t -> bool t
val (=$=) : string t -> string t -> bool t
val (<$>) : string t -> string t -> bool t
val returns : 'a t -> value:int -> bool t
module Bool:sig
..end
val succeeds : 'a t -> bool t
succeeds expr
is a equivalent to returns expr ~value:0
.val file_exists : string t -> bool t
module Integer:sig
..end
val list : 'a t list -> 'a list t
val list_append : 'a list t -> 'a list t -> 'a list t
val list_iter : 'a list t -> f:((unit -> 'a t) -> unit t) -> unit t
val list_to_string : 'a list t -> f:('a t -> string t) -> string t
val list_of_string : string t -> f:(string t -> 'a t) -> 'a list t
val output_as_string : unit t -> string t
val feed : string:string t -> unit t -> unit t
~string
) into the "stdin"
filedescriptor of
a unit t
expression.val (>>) : string t -> unit t -> unit t
str >> cmd
is feed ~string:str cmd
.val string_concat : string t list -> string t
string t
values.val string_concat_list : string list t -> string t
string list t
.val nop : unit t
val if_then_else : bool t -> unit t -> unit t -> unit t
val if_then : bool t -> unit t -> unit t
val seq : unit t list -> unit t
val loop_while : bool t -> body:unit t -> unit t
val if_seq : t:unit t list -> ?e:unit t list -> bool t -> unit t
if_seq c ~t ~e
is an alternate API for EDSL.if_then_else
(when
?e
is provided) or EDSL.if_then
(otherwise) that assumes “then”
and “else” bodies to be lists for EDSL.seq
construct.val switch : [ `Case of bool t * unit t | `Default of unit t ] list ->
unit t
EDSL.case
and optionally a
EDSL.default
(the function raises an exception if there are more
than one default cases).val case : bool t -> unit t list -> [> `Case of bool t * unit t ]
EDSL.switch
statement.val default : unit t list -> [> `Default of unit t ]
EDSL.switch
statement.type
fd_redirection
val to_fd : int t -> int t -> fd_redirection
val to_file : int t -> string t -> fd_redirection
val with_redirections : unit t -> fd_redirection list -> unit t
unit t
expression after applying a list of file-descriptor
redirections.
The redirections are applied in the list's order.
Cf. the example:
with_redirections (exec ["printf"; "%s"; "hello"]) [
to_file (int 3) (string "/path/to/one");
to_file (int 3) (string "/path/to/two");
to_fd (int 2) (int 3);
to_fd (int 1) (int 2);
];
"printf '%s' 'hello'"
will output to the file "/path/to/two"
,
because redirections are set in that order:
3
is set to output to "/path/to/one"
,3
is set to output to "/path/to/two"
(overriding the previous redirection),2
is redirected to file-descriptor 3
,1
is redirected to file-descriptor 2
,"printf"
outputs to 1
.with_redirections expr redirs
exits and its return value is in [1, 125]
; if the shell is
"bash"
or "zsh"
, the failing redirection is just ignored and expr
is
executed with the remaining redirections if any.val write_output : ?stdout:string t ->
?stderr:string t ->
?return_value:string t -> unit t -> unit t
stdout
,
stderr
, return_value
are paths).val write_stdout : path:string t -> unit t -> unit t
write_stdout ~path expr
is write_output expr ~stdout:path
.val pipe : unit t list -> unit t
"stdout"
into "stdin"
exactly like the
" | "
operator).val (||>) : unit t -> unit t -> unit t
a ||> b
is a shortcut for pipe [a; b]
.val printf : string t -> string t list -> unit t
printf fmt l
is call (string "printf" :: string "--" :: fmt :: l)
.val eprintf : string t -> string t list -> unit t
val fail : unit t
val with_signal : ?signal_name:string ->
catch:unit t -> (unit t -> unit t) -> unit t
"USR2"
) to create a “jump.”
with_signal ~catch (fun signal -> (* more_code *))
executes (* more_code *)
but if it uses signal
, the code behaves like
a raised exception, and the catch
argument is executed.
See the example:
let tmp = tmp_file "appender" in
seq [
tmp#set (string "start");
with_signal ~signal_name:"USR1" (fun signal ->
seq [
tmp#append (string "-signal");
signal;
tmp#append (string "-WRONG");
])
~catch:(seq [
tmp#append (string "-caught")
]);
call [string "printf"; string "tmp: %s\\n"; tmp#get];
assert_or_fail "Timeline-of-tmp"
(tmp#get =$= string "start-signal-caught");
]
Note that by default, the compiler functions use the signal "USR1"
and
having 2 calls to trap
with the same signal in the same script
does not play well, so use ~signal_name:"USR1"
at your own risk.
Moreover, for now this feature makes use of "sh -c <>"
sub-shells; it
does not play well with arbitrary redirections.
val with_failwith : ((message:string Language.t -> return:int Language.t -> unit Language.t) ->
unit Language.t) ->
unit Language.t
with_failwith f
uses ! and EDSL.with_signal
to call f
with a function that exits the flow of execution and displays
~message
and returns ~return
(a bit like Pervasives.failwith
).type
file = <
|
append : |
|
delete : |
|
get : |
|
path : |
|
set : |
EDSL.tmp_file
.val tmp_file : ?tmp_dir:string t -> string -> file
string t
values).
tmp_file (string "foo")
points to a path that is a function
of the string "foo"
; it does not try to make temporary-files
unique, on the contrary two calls to tmp_file (string "foo")
ensure that
it is the same file.
module Command_line:sig
..end
Prtinf.scanf
.
module Magic:sig
..end
EDSL.Magic
module is like OCaml's Obj.magic
function for the
EDSL; it allows one to bypass typing.