1 # Oil Functions
2
3 #### Untyped func
4 func add(x, y) Int {
5 echo hi
6 return x + y
7 }
8 var result = add(42, 1)
9 echo $result
10 ## STDOUT:
11 hi
12 43
13 ## END
14
15 #### Typed func
16 func add(x Int, y Int) Int {
17 echo hi
18 return x+y
19 }
20 var result = add(42, 1)
21 echo $result
22 ## STDOUT:
23 hi
24 43
25 ## END
26
27 #### func: default values for positional params
28 shopt -s oil:all
29 func add(x Int, y=1, z=1+2*3) {
30 return x + y + z
31 }
32 echo $add(3)
33 echo $add(3,4)
34 ## STDOUT:
35 11
36 14
37 ## END
38
39 #### pass too many positional params to func (without spread)
40 shopt -s oil:all
41 func add(x, y) {
42 return x + y
43 }
44 var f = add(1,2)
45 echo f=$f
46 var f = add(1,2,3)
47 echo $f
48 ## status: 1
49 ## STDOUT:
50 f=3
51 ## END
52
53 #### Positional Spread
54 shopt -s oil:all
55 func add(x, y, ...args) {
56 write @args
57 return x + y
58 }
59 var args = @[5 6 7 8]
60 var y = add(...args)
61 echo y=$y
62 ## STDOUT:
63 7
64 8
65 y=11
66 ## END
67
68 #### pass named arg to func
69 func f(; x=42) {
70 echo $x
71 }
72 pass f()
73 pass f(x=99)
74 ## STDOUT:
75 42
76 99
77 ## END
78
79 #### Func with missing named param with no default
80 shopt -s oil:all
81 func add(x Int, y Int ; verbose Bool) {
82 if (verbose) {
83 echo 'verbose'
84 }
85 return x + y
86 }
87 var a = add(3, 2, verbose=true)
88 echo $a
89
90 # crashes
91 var a = add(3, 2)
92 echo "shouldn't get here"
93 ## status: 1
94 ## STDOUT:
95 verbose
96 5
97 ## END
98
99 #### Func passed wrong named param
100 shopt -s oil:all
101 func add(x, y) {
102 return x + y
103 }
104 var x = add(2, 3)
105 echo x=$x
106 var y = add(2, 3, verbose=true)
107
108 ## status: 1
109 ## STDOUT:
110 x=5
111 ## END
112
113
114 #### Named Spread
115 shopt -s oil:all
116 func add(x, y; verbose=true, ...named) {
117 if (verbose) { echo 'verbose' }
118 write @named | sort
119 return x + y
120 }
121 var args = {verbose: false, a: 1, b: 2}
122 var args2 = {f: 3}
123 var ret = add(2, 3; ...args, ...args2)
124 echo ret=$ret
125 ## STDOUT:
126 a
127 b
128 f
129 ret=5
130 ## END
131
132 #### Func with varargs
133 shopt -s oil:all
134 func printf(fmt, ...args) {
135 = fmt
136 # Should be a LIST
137 = args
138 }
139 pass printf('foo', 'a', 42, null)
140
141 ## STDOUT:
142 (Str) 'foo'
143 (Tuple) ('a', 42, None)
144 ## END
145
146 #### return expression then return builtin
147 func f(x) {
148 return x + 2*3
149 }
150 # this goes in proc
151 f() {
152 local x=42
153 return $x
154 }
155 var x = f(36)
156 echo x=$x
157 f
158 echo status=$?
159 ## STDOUT:
160 x=42
161 status=42
162 ## END
163
164 #### Open proc (any number of args)
165 proc f {
166 var x = 42
167 return x
168 }
169 # this gets called with 3 args then?
170 f a b c
171 echo status=$?
172 ## STDOUT:
173 status=42
174 ## END
175
176 #### Closed proc with no args, passed too many
177 proc f() {
178 return 42
179 }
180 f
181 echo status=$?
182
183 # TODO: This should abort, or have status 1
184 f a b
185 echo status=$?
186
187 ## status: 1
188 ## STDOUT:
189 status=42
190 ## END
191
192 #### Open proc has "$@"
193 shopt -s oil:all
194 proc foo {
195 write ARGV "$@"
196 }
197 builtin set -- a b c
198 foo x y z
199 ## STDOUT:
200 ARGV
201 x
202 y
203 z
204 ## END
205
206 #### Closed proc doesn't have "$@"
207 shopt -s oil:all
208 proc foo(d, e, f) {
209 write params $d $e $f
210 write ARGV "$@"
211 }
212 builtin set -- a b c
213 foo x y z
214 ## STDOUT:
215 params
216 x
217 y
218 z
219 ARGV
220 ## END
221
222
223 #### Proc with default args
224 proc f(x='foo') {
225 echo x=$x
226 }
227 f
228 ## STDOUT:
229 x=foo
230 ## END
231
232 #### Proc with explicit args
233
234 # doesn't require oil:all
235 proc f(x, y, z) {
236 echo $x $y $z
237 var ret = 42
238 return ret # expression mode
239 }
240 # this gets called with 3 args then?
241 f a b c
242 echo status=$?
243 ## STDOUT:
244 a b c
245 status=42
246 ## END
247
248 #### Proc with varargs
249
250 # TODO: opts goes with this
251 # var opt = grep_opts.parse(ARGV)
252 #
253 # func(**opt) # Assumes keyword args match?
254 # parse :grep_opts :opt @ARGV
255
256 shopt -s oil:all
257
258 proc f(@names) {
259 write names: @names
260 }
261 # this gets called with 3 args then?
262 f a b c
263 echo status=$?
264 ## STDOUT:
265 names:
266 a
267 b
268 c
269 status=0
270 ## END
271
272 #### Proc name-with-hyphen
273 proc name-with-hyphen {
274 echo "$@"
275 }
276 name-with-hyphen x y z
277 ## STDOUT:
278 x y z
279 ## END
280
281 #### Proc with block arg
282
283 # TODO: Test more of this
284 proc f(x, y, &block) {
285 echo hi
286 }
287 f a b
288 ## STDOUT:
289 hi
290 ## END
291
292 #### inline function calls with spread, named args, etc.
293 shopt -s oil:all
294
295 func f(a, b=0, ...args; c, d=0, ...named) {
296 write __ args: @args
297 write __ named:
298 write @named | sort
299 if (named) {
300 return [a, b, c, d]
301 } else {
302 return a + b + c + d
303 }
304 }
305 var a = [42, 43]
306 var n = {x: 99, y: 100}
307
308 echo ____
309 write string $f(0, 1, ...a, c=2, d=3)
310
311 # Now get a list back
312 echo ____
313 write array @f(5, 6, ...a, c=7, d=8; ...n)
314
315 ## STDOUT:
316 ____
317 __
318 args:
319 42
320 43
321 __
322 named:
323
324 string
325 6
326 ____
327 __
328 args:
329 42
330 43
331 __
332 named:
333 x
334 y
335 array
336 5
337 6
338 7
339 8
340 ## END
341
342 #### basic lambda
343 var f = |x| x+1
344 var y = f(0)
345 echo $y
346 echo $f(42)
347 ## STDOUT:
348 1
349 43
350 ## END
351