OILS / spec / process-sub.test.sh View on Github | oilshell.org

204 lines, 111 significant
1## compare_shells: bash-4.4 zsh
2
3# mksh and dash don't support it
4
5#### Process sub input
6f=_tmp/process-sub.txt
7{ echo 1; echo 2; echo 3; } > $f
8cat <(head -n 2 $f) <(tail -n 2 $f)
9## STDOUT:
101
112
122
133
14## END
15
16#### Process sub from external process to stdin
17seq 3 > >(tac)
18## STDOUT:
193
202
211
22## END
23
24#### Process sub from shell to stdin
25{ echo 1; echo 2; echo 3; } > >(tac)
26## STDOUT:
273
282
291
30## END
31
32#### Non-linear pipeline with >()
33stdout_stderr() {
34 echo o1
35 echo o2
36
37 sleep 0.1 # Does not change order
38
39 { echo e1;
40 echo warning: e2
41 echo e3;
42 } >& 2
43}
44stdout_stderr 2> >(grep warning) | tac >$TMP/out.txt
45wait $! # this does nothing in bash 4.3, but probably does in bash 4.4.
46echo OUT
47cat $TMP/out.txt
48# PROBLEM -- OUT comes first, and then 'warning: e2', and then 'o2 o1'. It
49# looks like it's because nobody waits for the proc sub.
50# http://lists.gnu.org/archive/html/help-bash/2017-06/msg00018.html
51## STDOUT:
52OUT
53warning: e2
54o2
55o1
56## END
57
58#### $(<file) idiom with process sub
59echo FOO >foo
60
61# works in bash and zsh
62echo $(<foo)
63
64# this works in zsh, but not in bash
65tr A-Z a-z < <(<foo)
66
67cat < <(<foo; echo hi)
68
69## STDOUT:
70FOO
71hi
72## END
73## OK zsh STDOUT:
74FOO
75foo
76FOO
77hi
78## END
79
80#### status code is available
81
82shopt --set parse_at
83
84cat <(seq 2; exit 2) <(seq 3; exit 3)
85
86case $SH in bash*|zsh) exit ;; esac
87
88echo status @_process_sub_status
89echo done
90
91## STDOUT:
921
932
941
952
963
97status 2 3
98done
99## END
100## N-I bash/zsh STDOUT:
1011
1022
1031
1042
1053
106## END
107
108#### shopt -s process_sub_fail
109
110case $SH in bash*|zsh) exit ;; esac
111
112shopt --set parse_at
113
114cat <(echo a; exit 2) <(echo b; exit 3)
115echo status=$? ps @_process_sub_status
116
117echo __
118shopt -s process_sub_fail
119
120cat <(echo a; exit 2) <(echo b; exit 3)
121echo status=$? ps @_process_sub_status
122
123# Now exit because of it
124set -o errexit
125
126cat <(echo a; exit 2) <(echo b; exit 3)
127echo status=$? ps @_process_sub_status
128
129## status: 3
130## STDOUT:
131a
132b
133status=0 ps 2 3
134__
135a
136b
137status=3 ps 2 3
138a
139b
140## END
141## N-I bash/zsh status: 0
142## N-I bash/zsh STDOUT:
143## END
144
145#### process subs and pipelines together
146
147# zsh is very similar to bash, but don't bother with the assertions
148case $SH in bash*|zsh) exit ;; esac
149
150shopt --set parse_at
151
152f() {
153 cat <(seq 1; exit 1) | {
154 cat <(seq 2; exit 2) <(seq 3; exit 3)
155
156 # 2022-11 workaround for race condition: sometimes we get pipeline=141 4
157 # instead of pipeline=0 4, which means that the first 'cat' got SIGPIPE.
158 # If we make this part of the pipeline take longer, then 'cat' should have
159 # a chance to finish.
160
161 sleep 0.01
162
163 (exit 4)
164 }
165 echo status=$?
166 echo process_sub @_process_sub_status
167 echo pipeline @_pipeline_status
168 echo __
169}
170
171f
172
173## STDOUT:
1741
1752
1761
1772
1783
179status=4
180process_sub 2 3
181pipeline 0 4
182__
183## END
184## N-I bash/zsh STDOUT:
185## END
186
187#### process sub in background &
188
189cat <(seq 3; sleep 0.1) & wait
190
191echo sync
192
193# This one escapes, and the shell should still exit
194cat <(sleep 0.1) &
195
196echo fork
197
198## STDOUT:
1991
2002
2013
202sync
203fork
204## END