1 |
#!/usr/bin/env bash |
2 |
|
3 |
#### Remove const suffix |
4 |
v=abcd |
5 |
echo ${v%d} ${v%%cd} |
6 |
## stdout: abc ab |
7 |
|
8 |
#### Remove const prefix |
9 |
v=abcd |
10 |
echo ${v#a} ${v##ab} |
11 |
## stdout: bcd cd |
12 |
|
13 |
#### Remove const suffix is vectorized on user array |
14 |
a=(1a 2a 3a) |
15 |
argv.py ${a[@]%a} |
16 |
## stdout: ['1', '2', '3'] |
17 |
## status: 0 |
18 |
## N-I dash/mksh/ash stdout-json: "" |
19 |
## N-I dash/ash status: 2 |
20 |
## N-I mksh status: 1 |
21 |
|
22 |
#### Remove const suffix is vectorized on $@ array |
23 |
set -- 1a 2a 3a |
24 |
argv.py ${@%a} |
25 |
## stdout: ['1', '2', '3'] |
26 |
## status: 0 |
27 |
## N-I dash/ash stdout: ['1a', '2a', '3'] |
28 |
## N-I dash/ash status: 0 |
29 |
## N-I mksh stdout-json: "" |
30 |
## N-I mksh status: 1 |
31 |
|
32 |
#### Remove const suffix from undefined |
33 |
echo ${undef%suffix} |
34 |
## stdout: |
35 |
|
36 |
#### Remove shortest glob suffix |
37 |
v=aabbccdd |
38 |
echo ${v%c*} |
39 |
## stdout: aabbc |
40 |
|
41 |
#### Remove longest glob suffix |
42 |
v=aabbccdd |
43 |
echo ${v%%c*} |
44 |
## stdout: aabb |
45 |
|
46 |
#### Remove shortest glob prefix |
47 |
v=aabbccdd |
48 |
echo ${v#*b} |
49 |
## stdout: bccdd |
50 |
|
51 |
#### Remove longest glob prefix |
52 |
v=aabbccdd |
53 |
echo ${v##*b} |
54 |
## stdout: ccdd |
55 |
|
56 |
#### Strip char class |
57 |
v=abc |
58 |
echo ${v%[[:alpha:]]} |
59 |
## stdout: ab |
60 |
## N-I mksh stdout: abc |
61 |
|
62 |
#### Strip unicode prefix |
63 |
# NOTE: LANG is set to utf-8. |
64 |
v='μ-' |
65 |
echo ${v#?} # ? is a glob that stands for one character |
66 |
## stdout: - |
67 |
## BUG dash/mksh/ash stdout-repr: '\xbc-\n' |
68 |
## BUG zsh stdout-repr: '\n' |
69 |
|
70 |
#### Bug fix: Test that you can remove everything with glob |
71 |
s='--x--' |
72 |
argv.py "${s%%-*}" "${s%-*}" "${s#*-}" "${s##*-}" |
73 |
## STDOUT: |
74 |
['', '--x-', '-x--', ''] |
75 |
## END |
76 |
|
77 |
#### Test that you can remove everything with const |
78 |
s='abcd' |
79 |
argv.py "${s%%abcd}" "${s%abcd}" "${s#abcd}" "${s##abcd}" |
80 |
# failure case: |
81 |
argv.py "${s%%abcde}" "${s%abcde}" "${s#abcde}" "${s##abcde}" |
82 |
## STDOUT: |
83 |
['', '', '', ''] |
84 |
['abcd', 'abcd', 'abcd', 'abcd'] |
85 |
## END |
86 |
|
87 |
#### Prepend using replacement of # |
88 |
# This case was found in Kubernetes and others |
89 |
array=(aa bb '') |
90 |
argv.py ${array[@]/#/prefix-} |
91 |
## STDOUT: |
92 |
['prefix-aa', 'prefix-bb', 'prefix-'] |
93 |
## END |
94 |
## N-I dash/ash status: 2 |
95 |
## N-I dash/ash stdout-json: "" |
96 |
## N-I mksh status: 1 |
97 |
## N-I mksh stdout-json: "" |
98 |
|
99 |
#### Append using replacement of % |
100 |
array=(aa bb '') |
101 |
argv.py ${array[@]/%/-suffix} |
102 |
## STDOUT: |
103 |
['aa-suffix', 'bb-suffix', '-suffix'] |
104 |
## END |
105 |
## N-I dash/ash status: 2 |
106 |
## N-I dash/ash stdout-json: "" |
107 |
## N-I mksh status: 1 |
108 |
## N-I mksh stdout-json: "" |
109 |
|
110 |
#### strip unquoted and quoted [ |
111 |
# I guess dash and mksh treat unquoted [ as an invalid glob? |
112 |
var='[foo]' |
113 |
echo ${var#[} |
114 |
echo ${var#"["} |
115 |
echo "${var#[}" |
116 |
echo "${var#"["}" |
117 |
## STDOUT: |
118 |
foo] |
119 |
foo] |
120 |
foo] |
121 |
foo] |
122 |
## END |
123 |
## OK dash/mksh STDOUT: |
124 |
[foo] |
125 |
foo] |
126 |
[foo] |
127 |
foo] |
128 |
## END |
129 |
## BUG zsh stdout-json: "" |
130 |
## BUG zsh status: 1 |
131 |
|
132 |
#### strip unquoted and quoted [] |
133 |
# LooksLikeGlob('[]') is true |
134 |
# I guess dash, mksh, and zsh treat unquoted [ as an invalid glob? |
135 |
var='[]foo[]' |
136 |
echo ${var#[]} |
137 |
echo ${var#"[]"} |
138 |
echo "${var#[]}" |
139 |
echo "${var#"[]"}" |
140 |
## STDOUT: |
141 |
foo[] |
142 |
foo[] |
143 |
foo[] |
144 |
foo[] |
145 |
## END |
146 |
## OK dash/mksh/zsh STDOUT: |
147 |
[]foo[] |
148 |
foo[] |
149 |
[]foo[] |
150 |
foo[] |
151 |
## END |
152 |
|
153 |
#### strip unquoted and quoted ? |
154 |
var='[foo]' |
155 |
echo ${var#?} |
156 |
echo ${var#"?"} |
157 |
echo "${var#?}" |
158 |
echo "${var#"?"}" |
159 |
## STDOUT: |
160 |
foo] |
161 |
[foo] |
162 |
foo] |
163 |
[foo] |
164 |
## END |
165 |
|
166 |
#### strip unquoted and quoted [a] |
167 |
var='[a]foo[]' |
168 |
echo ${var#[a]} |
169 |
echo ${var#"[a]"} |
170 |
echo "${var#[a]}" |
171 |
echo "${var#"[a]"}" |
172 |
## STDOUT: |
173 |
[a]foo[] |
174 |
foo[] |
175 |
[a]foo[] |
176 |
foo[] |
177 |
## END |
178 |
|
179 |
#### Nested % and # operators (bug reported by Crestwave) |
180 |
var=$'\n' |
181 |
argv.py "${var#?}" |
182 |
argv.py "${var%''}" |
183 |
argv.py "${var%"${var#?}"}" |
184 |
var='a' |
185 |
argv.py "${var#?}" |
186 |
argv.py "${var%''}" |
187 |
argv.py "${var%"${var#?}"}" |
188 |
## STDOUT: |
189 |
[''] |
190 |
['\n'] |
191 |
['\n'] |
192 |
[''] |
193 |
['a'] |
194 |
['a'] |
195 |
## END |
196 |
## N-I dash STDOUT: |
197 |
['\\n'] |
198 |
['$\\n'] |
199 |
['$'] |
200 |
[''] |
201 |
['a'] |
202 |
['a'] |
203 |
## END |
204 |
|
205 |
#### strip * (bug regression) |
206 |
x=abc |
207 |
argv.py "${x#*}" |
208 |
argv.py "${x##*}" |
209 |
argv.py "${x%*}" |
210 |
argv.py "${x%%*}" |
211 |
## STDOUT: |
212 |
['abc'] |
213 |
[''] |
214 |
['abc'] |
215 |
[''] |
216 |
## END |
217 |
## BUG zsh STDOUT: |
218 |
['abc'] |
219 |
[''] |
220 |
['ab'] |
221 |
[''] |
222 |
## END |
223 |
|
224 |
#### strip ? |
225 |
x=abc |
226 |
argv.py "${x#?}" |
227 |
argv.py "${x##?}" |
228 |
argv.py "${x%?}" |
229 |
argv.py "${x%%?}" |
230 |
## STDOUT: |
231 |
['bc'] |
232 |
['bc'] |
233 |
['ab'] |
234 |
['ab'] |
235 |
## END |
236 |
|
237 |
#### strip all |
238 |
x=abc |
239 |
argv.py "${x#abc}" |
240 |
argv.py "${x##abc}" |
241 |
argv.py "${x%abc}" |
242 |
argv.py "${x%%abc}" |
243 |
## STDOUT: |
244 |
[''] |
245 |
[''] |
246 |
[''] |
247 |
[''] |
248 |
## END |
249 |
|
250 |
#### strip none |
251 |
x=abc |
252 |
argv.py "${x#}" |
253 |
argv.py "${x##}" |
254 |
argv.py "${x%}" |
255 |
argv.py "${x%%}" |
256 |
## STDOUT: |
257 |
['abc'] |
258 |
['abc'] |
259 |
['abc'] |
260 |
['abc'] |
261 |
## END |