*** empty log message ***
[bpt/guile.git] / doc / ref / expect.texi
CommitLineData
a0e07ba4
NJ
1@page
2@node Expect
3@chapter Expect
4
5The macros in this section are made available with:
6
7@smalllisp
8(use-modules (ice-9 expect))
9@end smalllisp
10
11@code{expect} is a macro for selecting actions based on the output from
12a port. The name comes from a tool of similar functionality by Don Libes.
13Actions can be taken when a particular string is matched, when a timeout
14occurs, or when end-of-file is seen on the port. The @code{expect} macro
15is described below; @code{expect-strings} is a front-end to @code{expect}
16based on regexec (see the regular expression documentation).
17
18@defmac expect-strings clause @dots{}
19By default, @code{expect-strings} will read from the current input port.
20The first term in each clause consists of an expression evaluating to
21a string pattern (regular expression). As characters
22are read one-by-one from the port, they are accumulated in a buffer string
23which is matched against each of the patterns. When a
24pattern matches, the remaining expression(s) in
25the clause are evaluated and the value of the last is returned. For example:
26
27@smalllisp
28(with-input-from-file "/etc/passwd"
29 (lambda ()
30 (expect-strings
31 ("^nobody" (display "Got a nobody user.\n")
32 (display "That's no problem.\n"))
33 ("^daemon" (display "Got a daemon user.\n")))))
34@end smalllisp
35
36The regular expression is compiled with the @code{REG_NEWLINE} flag, so
37that the ^ and $ anchors will match at any newline, not just at the start
38and end of the string.
39
40There are two other ways to write a clause:
41
42The expression(s) to evaluate
43can be omitted, in which case the result of the regular expression match
44(converted to strings, as obtained from regexec with match-pick set to "")
45will be returned if the pattern matches.
46
47The symbol @code{=>} can be used to indicate that the expression is a
48procedure which will accept the result of a successful regular expression
49match. E.g.,
50
51@smalllisp
52("^daemon" => write)
53("^d\\(aemon\\)" => (lambda args (for-each write args)))
54("^da\\(em\\)on" => (lambda (all sub)
55 (write all) (newline)
56 (write sub) (newline)))
57@end smalllisp
58
59The order of the substrings corresponds to the order in which the
60opening brackets occur.
61
62A number of variables can be used to control the behaviour
63of @code{expect} (and @code{expect-strings}).
64Most have default top-level bindings to the value @code{#f},
65which produces the default behaviour.
66They can be redefined at the
67top level or locally bound in a form enclosing the expect expression.
68
69@table @code
70@item expect-port
71A port to read characters from, instead of the current input port.
72@item expect-timeout
73@code{expect} will terminate after this number of
74seconds, returning @code{#f} or the value returned by expect-timeout-proc.
75@item expect-timeout-proc
76A procedure called if timeout occurs. The procedure takes a single argument:
77the accumulated string.
78@item expect-eof-proc
79A procedure called if end-of-file is detected on the input port. The
80procedure takes a single argument: the accumulated string.
81@item expect-char-proc
82A procedure to be called every time a character is read from the
83port. The procedure takes a single argument: the character which was read.
84@item expect-strings-compile-flags
85Flags to be used when compiling a regular expression, which are passed
86to @code{make-regexp} @xref{Regexp Functions}. The default value
87is @code{regexp/newline}.
88@item expect-strings-exec-flags
89Flags to be used when executing a regular expression, which are
90passed to regexp-exec @xref{Regexp Functions}.
91The default value is @code{regexp/noteol}, which prevents @code{$}
92from matching the end of the string while it is still accumulating,
93but still allows it to match after a line break or at the end of file.
94@end table
95
96Here's an example using all of the variables:
97
98@smalllisp
99(let ((expect-port (open-input-file "/etc/passwd"))
100 (expect-timeout 1)
101 (expect-timeout-proc
102 (lambda (s) (display "Times up!\n")))
103 (expect-eof-proc
104 (lambda (s) (display "Reached the end of the file!\n")))
105 (expect-char-proc display)
106 (expect-strings-compile-flags (logior regexp/newline regexp/icase))
107 (expect-strings-exec-flags 0))
108 (expect-strings
109 ("^nobody" (display "Got a nobody user\n"))))
110@end smalllisp
111@end defmac
112
113@defmac expect clause @dots{}
114@code{expect} is used in the same way as @code{expect-strings},
115but tests are specified not as patterns, but as procedures. The
116procedures are called in turn after each character is read from the
117port, with two arguments: the value of the accumulated string and
118a flag to indicate whether end-of-file has been reached. The flag
119will usually be @code{#f}, but if end-of-file is reached, the procedures
120are called an additional time with the final accumulated string and
121@code{#t}.
122
123The test is successful if the procedure returns a non-false value.
124
125If the @code{=>} syntax is used, then if the test succeeds it must return
126a list containing the arguments to be provided to the corresponding
127expression.
128
129In the following example, a string will only be matched at the beginning
130of the file:
131
132@smalllisp
133(let ((expect-port (open-input-file "/etc/passwd")))
134 (expect
135 ((lambda (s eof?) (string=? s "fnord!"))
136 (display "Got a nobody user!\n"))))
137@end smalllisp
138
139The control variables described for @code{expect-strings} also
140influence the behaviour of @code{expect}, with the exception of
141variables whose names begin with @code{expect-strings-}.
142@end defmac