testpatches.sh - sites - public wiki contents of suckless.org | |
git clone git://git.suckless.org/sites | |
Log | |
Files | |
Refs | |
--- | |
testpatches.sh (7546B) | |
--- | |
1 #!/bin/sh | |
2 # TODO: | |
3 # ? build: | |
4 # - set flags per project? (per version too?). | |
5 # - add build status (OK, FAIL, unknown), must be secure though. | |
6 | |
7 projects() { | |
8 cat <<!__EOF__ | |
9 dmenu tools.suckless.org/dmenu/patches | |
10 dwm dwm.suckless.org/patches | |
11 ii tools.suckless.org/ii/patches | |
12 sent tools.suckless.org/sent/patches | |
13 sic tools.suckless.org/sic/patches | |
14 slock tools.suckless.org/slock/patches | |
15 st st.suckless.org/patches | |
16 surf surf.suckless.org/patches | |
17 tabbed tools.suckless.org/tabbed/patches | |
18 !__EOF__ | |
19 } | |
20 | |
21 wikidir="$(pwd)/sites" | |
22 repodir="$(pwd)/repos" | |
23 revdir="$(pwd)/rev" | |
24 resultsdir="$(pwd)/results" | |
25 builddir="$(pwd)/build" | |
26 | |
27 # dryrun patch command (OpenBSD). | |
28 # must be unified diff (-u, so no ed script), -t and -C are dryrun (non-… | |
29 dryrun="patch -u -p1 -t -C" | |
30 | |
31 # getdateutc() | |
32 getdateutc() { | |
33 # date as UTC+0 time. | |
34 TZ="UTC+0" date | |
35 } | |
36 | |
37 # log(s) | |
38 log() { | |
39 s="[$(date)] $1" | |
40 echo "$s" >&2 | |
41 } | |
42 | |
43 # getprojects() | |
44 getprojects() { | |
45 # allow commenting to disable. | |
46 projects | grep -v '^#' | |
47 } | |
48 | |
49 # clone() | |
50 clone() { | |
51 getprojects | while read -r -- project dir; do | |
52 test -d "$repodir/$project" && continue | |
53 | |
54 git clone --bare "git://git.suckless.org/$project" "$rep… | |
55 done | |
56 } | |
57 | |
58 # pull() | |
59 pull() { | |
60 getprojects | while read -r -- project dir; do | |
61 test -d "$repodir/$project" || continue | |
62 | |
63 GIT_DIR="$repodir/$project" git fetch "git://git.suckles… | |
64 done | |
65 } | |
66 | |
67 # listpatches() | |
68 listpatches() { | |
69 getprojects | while read -r -- project dir; do | |
70 find "$wikidir/$dir" -name "*.diff" | while read -r p; do | |
71 test -f "$p" || continue | |
72 | |
73 b=$(basename "$p") | |
74 bb="${b%.diff}" | |
75 bb="${bb#${project}-}" | |
76 | |
77 # NOTE: historical patches like "r1506" (mercuri… | |
78 v=$(echo "$bb" | sed -En 's@^([0-9a-f\.]+)-.*$@\… | |
79 if test -z "$v"; then | |
80 v=$(echo "$bb" | sed -En 's@^.*-([0-9a-f… | |
81 fi | |
82 | |
83 # version not found, skip. | |
84 if test -z "$v"; then | |
85 continue | |
86 fi | |
87 | |
88 name="${p%.diff}" | |
89 name="${name##*/patches/}" | |
90 name="${name%%/*}" | |
91 | |
92 printf '%s\t%s\t%s\t%s\t%s\n' "$project" "$v" "$… | |
93 done | |
94 done | |
95 } | |
96 | |
97 # checkoutrev(project, version) | |
98 checkoutrev() { | |
99 project="$1" | |
100 v="$2" | |
101 | |
102 test -f "$revdir/$project/$v/fail" && return 1 | |
103 test -d "$revdir/$project/$v" && return 0 | |
104 | |
105 cur=$(pwd) | |
106 d="$revdir/$project/$v" | |
107 mkdir -p "$d" | |
108 cd "$d" || return 1 | |
109 | |
110 GIT_DIR="$repodir/$project" \ | |
111 git archive "$v" 2> "$revdir/$project/$v/fail" | \ | |
112 tar xf - 2>/dev/null | |
113 status=$? | |
114 if test x"$status" != x"0"; then | |
115 status=1 | |
116 else | |
117 rm -f "$revdir/$project/$v/fail" | |
118 fi | |
119 cd "$cur" | |
120 | |
121 return $status | |
122 } | |
123 | |
124 # preparebuilds() | |
125 preparebuilds() { | |
126 listpatches | while read -r -- project v dir name p; do | |
127 test -f "$p" || continue | |
128 | |
129 # version quirks (wrong tagging). | |
130 if test x"$project" = x"sent"; then | |
131 if test x"$v" = x"1.0"; then | |
132 v="1" | |
133 test -e "$revdir/$project/1.0" || \ | |
134 ln -sf "$v" "$revdir/$project/1.… | |
135 fi | |
136 fi | |
137 if test x"$project" = x"ii"; then | |
138 if test x"$v" = x"1.7"; then | |
139 v="v1.7" | |
140 test -e "$revdir/$project/1.7" || \ | |
141 ln -sf "$v" "$revdir/$project/1.… | |
142 fi | |
143 fi | |
144 | |
145 # prepare clean build directory for patch. | |
146 b=$(basename "$p") | |
147 b="${b%.diff}" | |
148 | |
149 # cannot prepare revision for build: skip. | |
150 if ! checkoutrev "$project" "$v"; then | |
151 log "CANNOT CHECKOUT REVISION: $project v=$v, na… | |
152 continue | |
153 fi | |
154 | |
155 # already has clean builddir. | |
156 test -d "$builddir/$project/$b" && continue | |
157 cleanbuild "$project" "$v" "$b" | |
158 done | |
159 } | |
160 | |
161 # cleanbuild(project, version, build) | |
162 cleanbuild() { | |
163 project="$1" | |
164 v="$2" | |
165 b="$3" | |
166 | |
167 test -d "$builddir/$project/$b" && rm -rf "$builddir/$project/$b" | |
168 | |
169 mkdir -p "$builddir/$project" | |
170 cp -r "$revdir/$project/$v" "$builddir/$project/$b" | |
171 } | |
172 | |
173 # testpatches() | |
174 testpatches() { | |
175 # sort by project, name, version | |
176 listpatches | sort -k1,1 -k4,4 -k2,2 | \ | |
177 while read -r -- project v dir name p; do | |
178 test -f "$p" || continue | |
179 | |
180 # cannot prepare revision for build: skip. | |
181 checkoutrev "$project" "$v" || continue | |
182 | |
183 b=$(basename "$p") | |
184 b="${b%.diff}" | |
185 | |
186 test -d "$builddir/$project/$b" || continue | |
187 cd "$builddir/$project/$b" || continue | |
188 | |
189 # copy patch file for convenience / debugging. | |
190 cp "$p" "$builddir/$project/$b/p.diff" | |
191 | |
192 # lenient: copy config.def.h to config.h if config.h doe… | |
193 #rm -f "$builddir/$project/$b/config.h" # DEBUG | |
194 #if test -f "$builddir/$project/$b/config.def.h"; then | |
195 # if ! test -f "$builddir/$project/$b/config.h"; … | |
196 # cp "$builddir/$project/$b/config.def.h"… | |
197 # fi | |
198 #fi | |
199 | |
200 # patch (dryrun). | |
201 $dryrun < "$p" 2> "$builddir/$project/$b/patch.2.log" >"… | |
202 applystatus=$? | |
203 | |
204 # write results to metadata file (for creating views). | |
205 printf "%s\t%s\t%s\t%s\t%s\t%s\n" \ | |
206 "$project" "$v" "$dir" "$name" "$applystatus" "$… | |
207 | |
208 log "$p $applystatus" | |
209 done | |
210 } | |
211 | |
212 # outputhtml() | |
213 outputhtml() { | |
214 index="$resultsdir/index.html" | |
215 title="Last updated on $(getdateutc)" | |
216 | |
217 cat > "$index" <<!__EOF__ | |
218 <!DOCTYPE html> | |
219 <html> | |
220 <head> | |
221 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> | |
222 <title>$title - Patch applystatus</title> | |
223 <style type="text/css"> | |
224 table { border-collapse: collapse; } | |
225 td { padding: 2px; } | |
226 thead td { background-color: #eee; } | |
227 .s-0 td { background-color: #ccffcc; } | |
228 .s-1 td { background-color: #ffcccc; } | |
229 .s-2 td { background-color: #ff0000; color: #fff; } | |
230 </style> | |
231 </head> | |
232 <body> | |
233 <h1>$title</h1> | |
234 <table> | |
235 <thead> | |
236 <tr> | |
237 <td><b>Project</b></td> | |
238 <td><b>Version/revision</b></td> | |
239 <td><b>Patch</b></td> | |
240 <td><b>Patch</b></td> | |
241 <td><b>Patch file</b></td> | |
242 <td><b>Patch stdout</b></td> | |
243 <td><b>Patch stderr</b></td> | |
244 <td><b>Exitcode</b></td> | |
245 <td><b>Status</b></td> | |
246 </tr> | |
247 </thead> | |
248 <tbody> | |
249 !__EOF__ | |
250 | |
251 # sort by project, name, version | |
252 find "$builddir" -name "metadata" -type f -exec cat {} \; | \ | |
253 sort -k1,1 -k4,4 -k2,2 | \ | |
254 while read -r -- project v dir name applystatus b; do | |
255 test -d "$builddir/$project/$b" || continue | |
256 | |
257 # HTML output test | |
258 mkdir -p "$resultsdir/$b/" | |
259 cp \ | |
260 "$builddir/$project/$b/p.diff"\ | |
261 "$builddir/$project/$b/patch.2.log"\ | |
262 "$builddir/$project/$b/patch.1.log"\ | |
263 "$resultsdir/$b/" | |
264 | |
265 statustext="OK" | |
266 pageurl="https://$dir/$name/" | |
267 | |
268 case "$applystatus" in | |
269 0) statustext="OK";; | |
270 1) statustext="FAIL";; | |
271 2) statustext="CORRUPT";; | |
272 *) statustext="UNKNOWN";; | |
273 esac | |
274 | |
275 cat >> "$index" <<!__EOF__ | |
276 <tr class="s-$applystatus"> | |
277 <td><a href="https://git.suckless.org/$project/">$project</a></t… | |
278 <td>$v</td> | |
279 <td><a href="$pageurl">$name</a></td> | |
280 <td><a href="$pageurl">$b</a></td> | |
281 <td><a href="$b/p.diff">[patch]</a></td> | |
282 <td><a href="$b/patch.1.log">[stdout]</a></td> | |
283 <td><a href="$b/patch.2.log">[stderr]</a></td> | |
284 <td>$applystatus</td> | |
285 <td>$statustext</td> | |
286 </tr> | |
287 !__EOF__ | |
288 done | |
289 | |
290 echo "</tbody></table></body></html>" >> "$index" | |
291 } | |
292 | |
293 # outputcsv() | |
294 outputcsv() { | |
295 index="$resultsdir/index.csv" | |
296 | |
297 # sort by project, name, version | |
298 find "$builddir" -name "metadata" -type f -exec cat {} \; | \ | |
299 sort -k1,1 -k4,4 -k2,2 | \ | |
300 while read -r -- project v dir name applystatus b; do | |
301 test -d "$builddir/$project/$b" || continue | |
302 | |
303 printf '%s\n' "$project $v $name $b… | |
304 done | |
305 } | |
306 | |
307 case "$1" in | |
308 clone|pull) | |
309 mkdir -p "$repodir" | |
310 $1 | |
311 ;; | |
312 clean) | |
313 rm -rf "$revdir" "$builddir" | |
314 ;; | |
315 prepare) | |
316 mkdir -p "$builddir" "$revdir" | |
317 preparebuilds | |
318 ;; | |
319 test) | |
320 testpatches | |
321 ;; | |
322 results) | |
323 # output results | |
324 rm -rf "$resultsdir" | |
325 mkdir -p "$resultsdir" | |
326 outputhtml | |
327 outputcsv | |
328 ;; | |
329 *) | |
330 echo "usage: $0 <clone | pull | clean | prepare | test | results… | |
331 exit 1 | |
332 ;; | |
333 esac |