]> git.decadent.org.uk Git - dak.git/blob - config/debian/cron.dinstall
make mkfilesindices a function
[dak.git] / config / debian / cron.dinstall
1 #!/bin/bash
2 # No way I try to deal with a crippled sh just for POSIX foo.
3
4 # Copyright (C) 2009 Joerg Jaspert <joerg@debian.org>
5 #
6 # This program is free software; you can redistribute it and/or
7 # modify it under the terms of the GNU General Public License as
8 # published by the Free Software Foundation; version 2.
9 #
10 # This program is distributed in the hope that it will be useful, but
11 # WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13 # General Public License for more details.
14 #
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18
19 # Homer: Are you saying you're never going to eat any animal again? What
20 #        about bacon?
21 # Lisa: No.
22 # Homer: Ham?
23 # Lisa: No.
24 # Homer: Pork chops?
25 # Lisa: Dad, those all come from the same animal.
26 # Homer: Heh heh heh. Ooh, yeah, right, Lisa. A wonderful, magical animal.
27
28 # exit on errors
29 set -e
30 # make sure to only use defined variables
31 set -u
32 # ERR traps should be inherited from functions too. (And command
33 # substitutions and subshells and whatnot, but for us the functions is
34 # the important part here)
35 set -E
36
37 # import the general variable set.
38 export SCRIPTVARS=/srv/ftp.debian.org/dak/config/debian/vars
39 . $SCRIPTVARS
40
41 ########################################################################
42 # Functions                                                            #
43 ########################################################################
44 # common functions are "outsourced"
45 . "${configdir}/common"
46
47 # Timestamp. Used for dinstall stat graphs
48 function ts() {
49         echo "Archive maintenance timestamp ($1): $(date +%H:%M:%S)"
50 }
51
52 # Cleanup actions
53 function cleanup() {
54         rm -f ${LOCK_DAILY}
55         rm -f ${LOCK_ACCEPTED}
56 }
57
58 # If we error out this one is called, *FOLLOWED* by cleanup above
59 function onerror() {
60     ERRDATE=$(date "+%Y.%m.%d-%H:%M:%S")
61
62     subject="ATTENTION ATTENTION!"
63     if [ "${error}" = "false" ]; then
64         subject="${subject} (continued)"
65     else
66         subject="${subject} (interrupted)"
67     fi
68     subject="${subject} dinstall error at ${ERRDATE} in ${STAGEFILE} - (Be quiet, Brain, or I'll stab you with a Q-tip)"
69
70     cat "${STAGEFILE}.log" | mail -s "${subject}" -a "X-Debian: DAK" cron@ftp-master.debian.org
71 }
72
73 ########################################################################
74 # the actual dinstall functions follow                                 #
75 ########################################################################
76
77 # pushing merkels QA user, part one
78 function merkel1() {
79     log "Telling merkels QA user that we start dinstall"
80     ssh -2 -i ~dak/.ssh/push_merkel_qa  -o BatchMode=yes -o SetupTimeOut=90 -o ConnectTimeout=90 qa@merkel.debian.org sleep 1
81 }
82
83 # Create the postgres dump files
84 function pgdump_pre() {
85     log "Creating pre-daily-cron-job backup of projectb database..."
86     pg_dump projectb > $base/backup/dump_pre_$(date +%Y.%m.%d-%H:%M:%S)
87 }
88
89 function pgdump_post() {
90     log "Creating post-daily-cron-job backup of projectb database..."
91     cd $base/backup
92     POSTDUMP=$(date +%Y.%m.%d-%H:%M:%S)
93     pg_dump projectb > $base/backup/dump_$POSTDUMP
94     pg_dumpall --globals-only > $base/backup/dumpall_$POSTDUMP
95     ln -sf $base/backup/dump_$POSTDUMP current
96     ln -sf $base/backup/dumpall_$POSTDUMP currentall
97 }
98
99 # Load the dak-dev projectb
100 function pgdakdev() {
101     cd $base/backup
102     echo "drop database projectb" | psql -p 5433 template1
103         cat currentall | psql -p 5433 template1
104     createdb -p 5433 -T template0 projectb
105     fgrep -v '\connect' current | psql -p 5433 projectb
106 }
107
108 # Updating various files
109 function updates() {
110     log "Updating Bugs docu, Mirror list and mailing-lists.txt"
111     cd $configdir
112     $scriptsdir/update-bugdoctxt
113     $scriptsdir/update-mirrorlists
114     $scriptsdir/update-mailingliststxt
115     $scriptsdir/update-pseudopackages.sh
116 }
117
118 # Process (oldstable)-proposed-updates "NEW" queue
119 function punew_do() {
120     cd "${queuedir}/${1}"
121     date -u -R >> REPORT
122     dak process-new -a -C COMMENTS >> REPORT || true
123     echo >> REPORT
124 }
125 function punew() {
126     log "Doing automated p-u-new processing"
127     punew_do "$1"
128 }
129 function opunew() {
130     log "Doing automated o-p-u-new processing"
131     punew_do "$1"
132 }
133
134 # The first i18n one, syncing new descriptions
135 function i18n1() {
136     log "Synchronizing i18n package descriptions"
137     # First sync their newest data
138     cd ${scriptdir}/i18nsync
139     rsync -aq --delete --delete-after ddtp-sync:/does/not/matter . || true
140
141     # Now check if we still know about the packages for which they created the files
142     # is the timestamp signed by us?
143     if $(gpgv --keyring /srv/ftp.debian.org/s3kr1t/dot-gnupg/pubring.gpg timestamp.gpg timestamp); then
144         # now read it. As its signed by us we are sure the content is what we expect, no need
145         # to do more here. And we only test -d a directory on it anyway.
146         TSTAMP=$(cat timestamp)
147         # do we have the dir still?
148         if [ -d ${scriptdir}/i18n/${TSTAMP} ]; then
149             # Lets check!
150             if ${scriptsdir}/ddtp-i18n-check.sh . ${scriptdir}/i18n/${TSTAMP}; then
151                 # Yay, worked, lets copy around
152                 for dir in squeeze sid; do
153                     if [ -d dists/${dir}/ ]; then
154                         cd dists/${dir}/main/i18n
155                         rsync -aq --delete --delete-after  . ${ftpdir}/dists/${dir}/main/i18n/.
156                     fi
157                     cd ${scriptdir}/i18nsync
158                 done
159             else
160                 echo "ARRRR, bad guys, wrong files, ARRR"
161                 echo "Arf, Arf, Arf, bad guys, wrong files, arf, arf, arf" | mail -s "Don't you kids take anything. I'm watching you. I've got eye implants in the back of my head." debian-l10n-devel@lists.alioth.debian.org
162             fi
163         else
164             echo "ARRRR, missing the timestamp ${TSTAMP} directory, not updating i18n, ARRR"
165             echo "Arf, Arf, Arf, missing the timestamp ${TSTAMP} directory, not updating i18n, arf, arf, arf" | mail -s "Lisa, if you don't like your job you don't strike. You just go in every day and do it really half-assed. That's the American way." debian-l10n-devel@lists.alioth.debian.org
166         fi
167     else
168         echo "ARRRRRRR, could not verify our timestamp signature, ARRR. Don't mess with our files, i18n guys, ARRRRR."
169         echo "Arf, Arf, Arf, could not verify our timestamp signature, arf. Don't mess with our files, i18n guys, arf, arf, arf" | mail -s "You can't keep blaming yourself. Just blame yourself once, and move on." debian-l10n-devel@lists.alioth.debian.org
170     fi
171 }
172
173 # Process the accepted queue
174 function accepted() {
175     log "Processing queue/accepted"
176     rm -f "$accepted/REPORT"
177     dak process-accepted -pa -d "$accepted" > "$accepted/REPORT"
178     cat "$accepted/REPORT" | mail -s "Install for $(date +"%D - %R")" ftpmaster@ftp-master.debian.org
179     chgrp debadmin "$accepted/REPORT"
180     chmod 664 "$accepted/REPORT"
181 }
182
183 function cruft() {
184     log "Checking for cruft in overrides"
185     dak check-overrides
186 }
187
188 function msfl() {
189     log "Generating suite file lists for apt-ftparchive"
190     dak make-suite-file-list
191 }
192
193 function fingerprints() {
194     log "Updating fingerprints"
195     dak import-keyring -L /srv/keyring.debian.org/keyrings/debian-keyring.gpg
196
197     OUTFILE=$(mktemp)
198     dak import-keyring --generate-users "%s" /srv/keyring.debian.org/keyrings/debian-maintainers.gpg >"${OUTFILE}"
199
200     if [ -s "${OUTFILE}" ]; then
201         /usr/sbin/sendmail -odq -oi -t -f envelope@ftp-master.debian.org <<EOF
202 From: Debian FTP Masters <ftpmaster@ftp-master.debian.org>
203 To: <debian-project@lists.debian.org>
204 Subject: Debian Maintainers Keyring changes
205 Content-Type: text/plain; charset=utf-8
206 MIME-Version: 1.0
207
208 The following changes to the debian-maintainers keyring have just been activated:
209
210 $(cat $OUTFILE)
211
212 Debian distribution maintenance software,
213 on behalf of the Keyring maintainers
214
215 EOF
216     fi
217     rm -f "$OUTFILE"
218 }
219
220 function overrides() {
221     log "Writing overrides into text files"
222     cd $overridedir
223     dak make-overrides
224
225     # FIXME
226     rm -f override.sid.all3
227     for i in main contrib non-free main.debian-installer; do cat override.sid.$i >> override.sid.all3; done
228 }
229
230 function mpfm() {
231     log "Generating package / file mapping"
232     dak make-pkg-file-mapping | bzip2 -9 > $base/ftp/indices/package-file.map.bz2
233 }
234
235 function packages() {
236     log "Generating Packages and Sources files"
237     cd $configdir
238     GZIP='--rsyncable' ; export GZIP
239     apt-ftparchive generate apt.conf
240 }
241
242 function pdiff() {
243     log "Generating pdiff files"
244     dak generate-index-diffs
245 }
246
247 function release() {
248     log "Generating Release files"
249     dak generate-releases
250 }
251
252 function dakcleanup() {
253     log "Cleanup old packages/files"
254     dak clean-suites -m 10000
255     dak clean-queues
256 }
257
258 function buildd() {
259     # Needs to be rebuilt, as files have moved.  Due to unaccepts, we need to
260     # update this before wanna-build is updated.
261     log "Regenerating wanna-build/buildd information"
262     psql projectb -A -t -q -c "SELECT filename FROM queue_build WHERE suite = 5 AND queue = 0 AND in_queue = true AND filename ~ 'd(sc|eb)$'" > $dbdir/dists/unstable_accepted.list
263     symlinks -d /srv/incoming.debian.org/buildd > /dev/null
264     apt-ftparchive generate apt.conf.buildd
265 }
266
267 function buildd_dir() {
268     # Rebuilt the buildd dir to avoid long times of 403
269     log "Regenerating the buildd incoming dir"
270     STAMP=$(date "+%Y%m%d%H%M")
271     make_buildd_dir
272 }
273
274 function mklslar() {
275     cd $ftpdir
276
277     FILENAME=ls-lR
278
279     log "Removing any core files ..."
280     find -type f -name core -print0 | xargs -0r rm -v
281
282     log "Checking permissions on files in the FTP tree ..."
283     find -type f \( \! -perm -444 -o -perm +002 \) -ls
284     find -type d \( \! -perm -555 -o -perm +002 \) -ls
285
286     log "Checking symlinks ..."
287     symlinks -rd .
288
289     log "Creating recursive directory listing ... "
290     rm -f .${FILENAME}.new
291     TZ=UTC ls -lR > .${FILENAME}.new
292
293     if [ -r ${FILENAME}.gz ] ; then
294         mv -f ${FILENAME}.gz ${FILENAME}.old.gz
295         mv -f .${FILENAME}.new ${FILENAME}
296         rm -f ${FILENAME}.patch.gz
297         zcat ${FILENAME}.old.gz | diff -u - ${FILENAME} | gzip --rsyncable -9cfn - >${FILENAME}.patch.gz
298         rm -f ${FILENAME}.old.gz
299     else
300         mv -f .${FILENAME}.new ${FILENAME}
301     fi
302
303     gzip --rsyncable -9cfN ${FILENAME} >${FILENAME}.gz
304     rm -f ${FILENAME}
305 }
306
307 function mkmaintainers() {
308     log -n 'Creating Maintainers index ... '
309
310     cd $indices
311     dak make-maintainers ${scriptdir}/masterfiles/pseudo-packages.maintainers | \
312         sed -e "s/~[^  ]*\([   ]\)/\1/"  | awk '{printf "%-20s ", $1; for (i=2; i<=NF; i++) printf "%s ", $i; printf "\n";}' > .new-maintainers
313
314     set +e
315     cmp .new-maintainers Maintainers >/dev/null
316     rc=$?
317     set -e
318     if [ $rc = 1 ] || [ ! -f Maintainers ] ; then
319             log -n "installing Maintainers ... "
320             mv -f .new-maintainers Maintainers
321             gzip --rsyncable -9v <Maintainers >.new-maintainers.gz
322             mv -f .new-maintainers.gz Maintainers.gz
323     elif [ $rc = 0 ] ; then
324             log '(same as before)'
325             rm -f .new-maintainers
326     else
327             log cmp returned $rc
328             false
329     fi
330 }
331
332 function copyoverrides() {
333     log 'Copying override files into public view ...'
334
335     for f in $copyoverrides ; do
336             cd $overridedir
337             chmod g+w override.$f
338
339             cd $indices
340             rm -f .newover-$f.gz
341             pc="`gzip 2>&1 -9nv <$overridedir/override.$f >.newover-$f.gz`"
342             set +e
343             nf=override.$f.gz
344             cmp -s .newover-$f.gz $nf
345             rc=$?
346             set -e
347         if [ $rc = 0 ]; then
348                     rm -f .newover-$f.gz
349             elif [ $rc = 1 -o ! -f $nf ]; then
350                     echo "   installing new $nf $pc"
351                     mv -f .newover-$f.gz $nf
352                     chmod g+w $nf
353             else
354                     echo $? $pc
355                     exit 1
356             fi
357     done
358 }
359
360 function mkfilesindices() {
361     umask 002
362     cd $base/ftp/indices/files/components
363
364     ARCHLIST=$(tempfile)
365
366     echo "Querying projectb..."
367     echo 'SELECT l.path, f.filename, a.arch_string FROM location l JOIN files f ON (f.location = l.id) LEFT OUTER JOIN (binaries b JOIN architecture a ON (b.architecture = a.id)) ON (f.id = b.file)' | psql projectb -At | sed 's/|//;s,^/srv/ftp.debian.org/ftp,.,' | sort >$ARCHLIST
368
369     includedirs () {
370         perl -ne 'print; while (m,/[^/]+$,) { $_=$`; print $_ . "\n" unless $d{$_}++; }'
371     }
372     poolfirst () {
373         perl -e '@nonpool=(); while (<>) { if (m,^\./pool/,) { print; } else { push @nonpool, $_; } } print for (@nonpool);'
374     }
375
376     echo "Generating sources list..."
377     (
378         sed -n 's/|$//p' $ARCHLIST
379         cd $base/ftp
380         find ./dists -maxdepth 1 \! -type d
381         find ./dists \! -type d | grep "/source/"
382     ) | sort -u | gzip --rsyncable -9 > source.list.gz
383
384     echo "Generating arch lists..."
385
386     ARCHES=$( (<$ARCHLIST sed -n 's/^.*|//p'; echo amd64) | grep . | grep -v all | sort -u)
387     for a in $ARCHES; do
388         (sed -n "s/|$a$//p" $ARCHLIST
389             sed -n 's/|all$//p' $ARCHLIST
390
391             cd $base/ftp
392             find ./dists -maxdepth 1 \! -type d
393             find ./dists \! -type d | grep -E "(proposed-updates.*_$a.changes$|/main/disks-$a/|/main/installer-$a/|/Contents-$a|/binary-$a/)"
394         ) | sort -u | gzip --rsyncable -9 > arch-$a.list.gz
395     done
396
397     echo "Generating suite lists..."
398
399     suite_list () {
400         printf 'SELECT DISTINCT l.path, f.filename FROM (SELECT sa.source AS source FROM src_associations sa WHERE sa.suite = %d UNION SELECT b.source AS source FROM bin_associations ba JOIN binaries b ON (ba.bin = b.id) WHERE ba.suite = %d) s JOIN dsc_files df ON (s.source = df.source) JOIN files f ON (df.file = f.id) JOIN location l ON (f.location = l.id)\n' $1 $1 | psql -F' ' -A -t projectb
401
402         printf 'SELECT l.path, f.filename FROM bin_associations ba JOIN binaries b ON (ba.bin = b.id) JOIN files f ON (b.file = f.id) JOIN location l ON (f.location = l.id) WHERE ba.suite = %d\n' $1 | psql -F' ' -A -t projectb
403     }
404
405     printf 'SELECT id, suite_name FROM suite\n' | psql -F' ' -At projectb |
406     while read id suite; do
407         [ -e $base/ftp/dists/$suite ] || continue
408         (
409             (cd $base/ftp
410                 distname=$(cd dists; readlink $suite || echo $suite)
411                 find ./dists/$distname \! -type d
412                 for distdir in ./dists/*; do
413                     [ "$(readlink $distdir)" != "$distname" ] || echo $distdir
414                 done
415             )
416             suite_list $id | tr -d ' ' | sed 's,^/srv/ftp.debian.org/ftp,.,'
417         ) | sort -u | gzip --rsyncable -9 > suite-${suite}.list.gz
418     done
419
420     echo "Finding everything on the ftp site to generate sundries $(date +"%X")..."
421
422     (cd $base/ftp; find . \! -type d \! -name 'Archive_Maintenance_In_Progress' | sort) >$ARCHLIST
423
424     rm -f sundries.list
425     zcat *.list.gz | cat - *.list | sort -u |
426     diff - $ARCHLIST | sed -n 's/^> //p' > sundries.list
427
428     echo "Generating files list $(date +"%X")..."
429
430     for a in $ARCHES; do
431         (echo ./project/trace; zcat arch-$a.list.gz source.list.gz) |
432         cat - sundries.list dists.list project.list docs.list indices.list |
433         sort -u | poolfirst > ../arch-$a.files
434     done
435
436     (cd $base/ftp/
437             for dist in sid squeeze; do
438                     find ./dists/$dist/main/i18n/ \! -type d | sort -u | gzip --rsyncable -9 > $base/ftp/indices/files/components/translation-$dist.list.gz
439             done
440     )
441
442     (cat ../arch-i386.files ../arch-amd64.files; zcat suite-oldstable.list.gz suite-proposed-updates.list.gz ; zcat translation-sid.list.gz ; zcat translation-squeeze.list.gz) |
443     sort -u | poolfirst > ../typical.files
444
445     rm -f $ARCHLIST
446     echo "Done!"
447 }
448 function scripts() {
449     log "Running various scripts from $scriptsdir"
450     cd $scriptsdir
451     mkmaintainers
452     copyoverrides
453     mklslar
454     mkfilesindices
455     ./mkchecksums
456 }
457
458 function mirror() {
459     echo "Regenerating \"public\" mirror/ hardlink fun"
460     cd ${mirrordir}
461     rsync -aH --link-dest ${ftpdir} --delete --delete-after --ignore-errors ${ftpdir}/. .
462 }
463
464 function wb() {
465     log "Trigger daily wanna-build run"
466     ssh -o BatchMode=yes -o SetupTimeOut=90 -o ConnectTimeout=90 wbadm@buildd /org/wanna-build/trigger.daily || echo "W-B trigger.daily failed" | mail -s "W-B Daily trigger failed" ftpmaster@ftp-master.debian.org
467 }
468
469 function expire() {
470     log "Expiring old database dumps..."
471     cd $base/backup
472     $scriptsdir/expire_dumps -d . -p -f "dump_*"
473 }
474
475 function transitionsclean() {
476     log "Removing out of date transitions..."
477     cd $base
478     dak transitions -c -a
479 }
480
481 function reports() {
482     # Send a report on NEW/BYHAND packages
483     log "Nagging ftpteam about NEW/BYHAND packages"
484     dak queue-report | mail -e -s "NEW and BYHAND on $(date +%D)" ftpmaster@ftp-master.debian.org
485     # and one on crufty packages
486     log "Sending information about crufty packages"
487     dak cruft-report > $webdir/cruft-report-daily.txt
488     dak cruft-report -s experimental >> $webdir/cruft-report-daily.txt
489     cat $webdir/cruft-report-daily.txt | mail -e -s "Debian archive cruft report for $(date +%D)" ftpmaster@ftp-master.debian.org
490 }
491
492 function dm() {
493     log "Updating DM html page"
494     $scriptsdir/dm-monitor >$webdir/dm-uploaders.html
495 }
496
497 function bts() {
498     log "Categorizing uncategorized bugs filed against ftp.debian.org"
499     dak bts-categorize
500 }
501
502 function merkel2() {
503     # Push dak@merkel so it syncs the projectb there. Returns immediately, the sync runs detached
504     log "Trigger merkel/flotows projectb sync"
505     ssh -2 -o BatchMode=yes -o SetupTimeOut=30 -o ConnectTimeout=30 -i ~/.ssh/push_merkel_projectb dak@merkel.debian.org sleep 1
506     # Also trigger flotow, the ftpmaster test box
507     ssh -2 -o BatchMode=yes -o SetupTimeOut=30 -o ConnectTimeout=30 -i ~/.ssh/push_flotow_projectb dak@flotow.debconf.org sleep 1
508 }
509
510 function merkel3() {
511     # Push dak@merkel to tell it to sync the dd accessible parts. Returns immediately, the sync runs detached
512     log "Trigger merkels dd accessible parts sync"
513     ssh -2 -o BatchMode=yes -o SetupTimeOut=30 -o ConnectTimeout=30 -i ~/.ssh/push_merkel_ddaccess dak@merkel.debian.org sleep 1
514 }
515
516 function mirrorpush() {
517     log "Starting the mirrorpush"
518     date -u > /srv/ftp.debian.org/web/mirrorstart
519     echo "Using dak v1" >> /srv/ftp.debian.org/web/mirrorstart
520     echo "Running on host $(hostname -f)" >> /srv/ftp.debian.org/web/mirrorstart
521     sudo -H -u archvsync /home/archvsync/runmirrors > ~dak/runmirrors.log 2>&1 &
522 }
523
524 function i18n2() {
525     log "Exporting package data foo for i18n project"
526     STAMP=$(date "+%Y%m%d%H%M")
527     mkdir -p ${scriptdir}/i18n/${STAMP}
528     cd ${scriptdir}/i18n/${STAMP}
529     dak control-suite -l stable > lenny
530     dak control-suite -l testing > squeeze
531     dak control-suite -l unstable > sid
532     echo "${STAMP}" > timestamp
533     gpg --secret-keyring /srv/ftp.debian.org/s3kr1t/dot-gnupg/secring.gpg --keyring /srv/ftp.debian.org/s3kr1t/dot-gnupg/pubring.gpg --no-options --batch --no-tty --armour --default-key 55BE302B --detach-sign -o timestamp.gpg timestamp
534     rm -f md5sum
535     md5sum * > md5sum
536     cd ${webdir}/
537     ln -sfT ${scriptdir}/i18n/${STAMP} i18n
538
539     cd ${scriptdir}
540     find ./i18n -mindepth 1 -maxdepth 1 -mtime +2 -not -name "${STAMP}" -type d -print0 | xargs --no-run-if-empty -0 rm -rf
541 }
542
543 function stats() {
544     log "Updating stats data"
545     cd $configdir
546     $scriptsdir/update-ftpstats $base/log/* > $base/misc/ftpstats.data
547     R --slave --vanilla < $base/misc/ftpstats.R
548     dak stats arch-space > $webdir/arch-space
549     dak stats pkg-nums > $webdir/pkg-nums
550 }
551
552 function aptftpcleanup() {
553     log "Clean up apt-ftparchive's databases"
554     cd $configdir
555     apt-ftparchive -q clean apt.conf
556 }
557
558 function compress() {
559     log "Compress old psql backups"
560     cd $base/backup/
561     find -maxdepth 1 -mindepth 1 -type f -name 'dump_pre_*' -mtime +2 -print0 | xargs -0 --no-run-if-empty rm
562
563     find -maxdepth 1 -mindepth 1 -type f -name 'dump_*' \! -name '*.bz2' \! -name '*.gz' -mmin +720 |
564     while read dumpname; do
565         echo "Compressing $dumpname"
566         bzip2 -9fv "$dumpname"
567     done
568     find -maxdepth 1 -mindepth 1 -type f -name "dumpall_*" \! -name '*.bz2' \! -name '*.gz' -mmin +720 |
569     while read dumpname; do
570         echo "Compressing $dumpname"
571         bzip2 -9fv "$dumpname"
572     done
573     finddup -l -d $base/backup
574 }
575
576 function logstats() {
577     $masterdir/tools/logs.py "$1"
578 }
579
580 # save timestamp when we start
581 function savetimestamp() {
582         NOW=`date "+%Y.%m.%d-%H:%M:%S"`
583         echo ${NOW} > "${dbdir}/dinstallstart"
584 }
585
586 function maillogfile() {
587     cat "$LOGFILE" | mail -s "Log for dinstall run of ${NOW}" cron@ftp-master.debian.org
588 }
589
590 function renamelogfile() {
591     if [ -f "${dbdir}/dinstallstart" ]; then
592         NOW=$(cat "${dbdir}/dinstallstart")
593 #        maillogfile
594         mv "$LOGFILE" "$logdir/dinstall_${NOW}.log"
595         logstats "$logdir/dinstall_${NOW}.log"
596         bzip2 -9 "$logdir/dinstall_${NOW}.log"
597     else
598         error "Problem, I don't know when dinstall started, unable to do log statistics."
599         NOW=`date "+%Y.%m.%d-%H:%M:%S"`
600 #        maillogfile
601         mv "$LOGFILE" "$logdir/dinstall_${NOW}.log"
602         bzip2 -9 "$logdir/dinstall_${NOW}.log"
603     fi
604 }
605
606 function testingsourcelist() {
607     dak ls -s testing -f heidi -r .| egrep 'source$' > ${webdir}/testing.list
608 }
609
610 # do a last run of process-unchecked before dinstall is on.
611 function process_unchecked() {
612     log "Processing the unchecked queue"
613     acceptnew
614     UNCHECKED_WITHOUT_LOCK="-p"
615     do_unchecked
616     sync_debbugs
617 }
618
619 ########################################################################
620 ########################################################################
621
622 # Function to save which stage we are in, so we can restart an interrupted
623 # dinstall. Or even run actions in parallel, if we dare to, by simply
624 # backgrounding the call to this function. But that should only really be
625 # done for things we don't care much about.
626 #
627 # This should be called with the first argument being an array, with the
628 # members
629 #  - FUNC - the function name to call
630 #  - ARGS - Possible arguments to hand to the function. Can be the empty string
631 #  - TIME - The timestamp name. Can be the empty string
632 #  - ERR  - if this is the string false, then the call will be surrounded by
633 #           set +e ... set -e calls, so errors in the function do not exit
634 #           dinstall. Can be the empty string, meaning true.
635 #
636 # MAKE SURE TO KEEP THIS THE LAST FUNCTION, AFTER ALL THE VARIOUS ONES
637 # ADDED FOR DINSTALL FEATURES!
638 function stage() {
639     ARGS='GO[@]'
640     local "${!ARGS}"
641
642     error=${ERR:-"true"}
643
644     STAGEFILE="${stagedir}/${FUNC}"
645     if [ -f "${STAGEFILE}" ]; then
646         stamptime=$(/usr/bin/stat -c %Z "${STAGEFILE}")
647         unixtime=$(date +%s)
648         difference=$(( $unixtime - $stamptime ))
649         if [ ${difference} -ge 14400 ]; then
650             log_error "Did already run ${FUNC}, stagefile exists, but that was ${difference} seconds ago. Please check."
651         else
652             log "Did already run ${FUNC}, not calling again..."
653         fi
654         return
655     fi
656
657     debug "Now calling function ${FUNC}. Arguments: ${ARGS}. Timestamp: ${TIME}"
658
659     # Make sure we are always at the same place. If a function wants to be elsewhere,
660     # it has to cd first!
661     cd ${configdir}
662
663     # Now redirect the output into $STAGEFILE.log. In case it errors out somewhere our
664     # errorhandler trap can then mail the contents of $STAGEFILE.log only, instead of a whole
665     # dinstall logfile. Short error mails ftw!
666     exec >> "${STAGEFILE}.log" 2>&1
667
668     if [ -f "${LOCK_STOP}" ]; then
669         log "${LOCK_STOP} exists, exiting immediately"
670         exit 42
671     fi
672
673     if [ "${error}" = "false" ]; then
674         set +e
675     fi
676     ${FUNC} ${ARGS}
677
678     # No matter what happened in the function, we make sure we have set -e default state back
679     set -e
680
681     # Make sure we are always at the same place.
682     cd ${configdir}
683
684     # We always use the same umask. If a function wants to do different, fine, but we reset.
685     umask 022
686
687     touch "${STAGEFILE}"
688
689     if [ -n "${TIME}" ]; then
690         ts "${TIME}"
691     fi
692
693     # And the output goes back to the normal logfile
694     exec >> "$LOGFILE" 2>&1
695
696     # Now we should make sure that we have a usable dinstall.log, so append the $STAGEFILE.log
697     # to it.
698     cat "${STAGEFILE}.log" >> "${LOGFILE}"
699     rm -f "${STAGEFILE}.log"
700
701     if [ -f "${LOCK_STOP}" ]; then
702         log "${LOCK_STOP} exists, exiting immediately"
703         exit 42
704     fi
705 }
706
707 ########################################################################
708
709 # We need logs.
710 LOGFILE="$logdir/dinstall.log"
711
712 exec >> "$LOGFILE" 2>&1
713
714 # usually we are not using debug logs. Set to 1 if you want them.
715 DEBUG=0
716
717 # our name
718 PROGRAM="dinstall"
719
720 # where do we want mails to go? For example log entries made with error()
721 if [ "x$(hostname -s)x" != "xriesx" ]; then
722     # Not our ftpmaster host
723     MAILTO=${MAILTO:-"root"}
724 else
725     # Yay, ftpmaster
726     MAILTO=${MAILTO:-"ftpmaster@debian.org"}
727 fi
728
729 # Make sure we start out with a sane umask setting
730 umask 022
731
732 # And use one locale, no matter what the caller has set
733 export LANG=C
734 export LC_ALL=C
735
736 # How many logfiles to keep
737 LOGROTATE=${LOGROTATE:-400}
738
739 # Marker for dinstall start
740 DINSTALLSTART="${lockdir}/dinstallstart"
741 # Marker for dinstall end
742 DINSTALLEND="${lockdir}/dinstallend"
743
744 touch "${DINSTALLSTART}"
745 ts "startup"
746
747 # lock cron.unchecked (it immediately exits when this exists)
748 LOCK_DAILY="$lockdir/daily.lock"
749
750 # Lock cron.unchecked from doing work
751 LOCK_ACCEPTED="$lockdir/unchecked.lock"
752
753 # Lock process-new from doing work
754 LOCK_NEW="$lockdir/processnew.lock"
755
756 # This file is simply used to indicate to britney whether or not
757 # the Packages file updates completed sucessfully.  It's not a lock
758 # from our point of view
759 LOCK_BRITNEY="$lockdir/britney.lock"
760
761 # If this file exists we exit immediately after the currently running
762 # function is done
763 LOCK_STOP="$lockdir/archive.stop"
764
765 lockfile -l 3600 "${LOCK_DAILY}"
766 trap onerror ERR
767 trap cleanup EXIT TERM HUP INT QUIT
768
769 touch "${LOCK_BRITNEY}"
770
771 GO=(
772     FUNC="savetimestamp"
773     TIME=""
774     ARGS=""
775     ERR="false"
776 )
777 stage $GO
778
779 GO=(
780     FUNC="notice"
781     TIME=""
782     ARGS=""
783     ERR="false"
784 )
785 stage $GO
786
787 GO=(
788     FUNC="merkel1"
789     TIME="init"
790     ARGS=""
791     ERR="false"
792 )
793 stage $GO &
794
795 GO=(
796     FUNC="pgdump_pre"
797     TIME="pg_dump1"
798     ARGS=""
799     ERR=""
800 )
801 stage $GO
802
803 GO=(
804     FUNC="updates"
805     TIME="External Updates"
806     ARGS=""
807     ERR="false"
808 )
809 stage $GO &
810
811 GO=(
812     FUNC="punew"
813     TIME="p-u-new"
814     ARGS="p-u-new"
815     ERR=""
816 )
817 stage $GO
818
819 GO=(
820     FUNC="opunew"
821     TIME="o-p-u-new"
822     ARGS="o-p-u-new"
823     ERR=""
824 )
825 stage $GO
826
827 GO=(
828     FUNC="i18n1"
829     TIME="i18n 1"
830     ARGS=""
831     ERR="false"
832 )
833 stage $GO &
834
835 lockfile "$LOCK_ACCEPTED"
836 lockfile "$LOCK_NEW"
837
838 GO=(
839     FUNC="process_unchecked"
840     TIME=""
841     ARGS=""
842     ERR=""
843 )
844 stage $GO
845
846
847 GO=(
848     FUNC="accepted"
849     TIME="accepted"
850     ARGS=""
851     ERR=""
852 )
853 stage $GO
854
855 GO=(
856     FUNC="buildd_dir"
857     TIME="buildd_dir"
858     ARGS=""
859     ERR="false"
860 )
861 stage $GO
862
863 GO=(
864     FUNC="cruft"
865     TIME="cruft"
866     ARGS=""
867     ERR=""
868 )
869 stage $GO
870
871 rm -f "$LOCK_ACCEPTED"
872 rm -f "$LOCK_NEW"
873
874 GO=(
875     FUNC="msfl"
876     TIME="make-suite-file-list"
877     ARGS=""
878     ERR=""
879 )
880 stage $GO
881
882 GO=(
883     FUNC="fingerprints"
884     TIME="import-keyring"
885     ARGS=""
886     ERR="false"
887 )
888 stage $GO &
889
890 GO=(
891     FUNC="overrides"
892     TIME="overrides"
893     ARGS=""
894     ERR=""
895 )
896 stage $GO
897
898 GO=(
899     FUNC="mpfm"
900     TIME="pkg-file-mapping"
901     ARGS=""
902     ERR="false"
903 )
904 stage $GO
905
906 GO=(
907     FUNC="packages"
908     TIME="apt-ftparchive"
909     ARGS=""
910     ERR=""
911 )
912 stage $GO
913
914 GO=(
915     FUNC="pdiff"
916     TIME="pdiff"
917     ARGS=""
918     ERR=""
919 )
920 stage $GO
921
922 GO=(
923     FUNC="release"
924     TIME="release files"
925     ARGS=""
926     ERR=""
927 )
928 stage $GO
929
930 GO=(
931     FUNC="dakcleanup"
932     TIME="cleanup"
933     ARGS=""
934     ERR=""
935 )
936 stage $GO
937
938 GO=(
939     FUNC="buildd"
940     TIME="buildd"
941     ARGS=""
942     ERR=""
943 )
944 stage $GO
945
946 GO=(
947     FUNC="scripts"
948     TIME="scripts"
949     ARGS=""
950     ERR=""
951 )
952 stage $GO
953
954 GO=(
955     FUNC="mirror"
956     TIME="mirror hardlinks"
957     ARGS=""
958     ERR=""
959 )
960 stage $GO
961
962 GO=(
963     FUNC="wb"
964     TIME="w-b"
965     ARGS=""
966     ERR=""
967 )
968 stage $GO &
969
970 rm -f "${LOCK_DAILY}"
971
972 ts "locked part finished"
973
974 GO=(
975     FUNC="pgdump_post"
976     TIME="pg_dump2"
977     ARGS=""
978     ERR=""
979 )
980 stage $GO &
981
982 GO=(
983     FUNC="expire"
984     TIME="expire_dumps"
985     ARGS=""
986     ERR=""
987 )
988 stage $GO &
989
990 GO=(
991     FUNC="transitionsclean"
992     TIME="transitionsclean"
993     ARGS=""
994     ERR=""
995 )
996 stage $GO &
997
998 GO=(
999     FUNC="reports"
1000     TIME="reports"
1001     ARGS=""
1002     ERR=""
1003 )
1004 stage $GO &
1005
1006 GO=(
1007     FUNC="dm"
1008     TIME=""
1009     ARGS=""
1010     ERR=""
1011 )
1012 stage $GO &
1013
1014 GO=(
1015     FUNC="bts"
1016     TIME=""
1017     ARGS=""
1018     ERR="false"
1019 )
1020 stage $GO &
1021
1022 GO=(
1023     FUNC="merkel2"
1024     TIME="merkel projectb push"
1025     ARGS=""
1026     ERR="false"
1027 )
1028 stage $GO &
1029
1030 GO=(
1031     FUNC="mirrorpush"
1032     TIME="mirrorpush"
1033     ARGS=""
1034     ERR="false"
1035 )
1036 stage $GO
1037
1038 GO=(
1039     FUNC="i18n2"
1040     TIME="i18n 2"
1041     ARGS=""
1042     ERR="false"
1043 )
1044 stage $GO
1045
1046 GO=(
1047     FUNC="stats"
1048     TIME="stats"
1049     ARGS=""
1050     ERR="false"
1051 )
1052 stage $GO &
1053
1054 GO=(
1055     FUNC="testingsourcelist"
1056     TIME=""
1057     ARGS=""
1058     ERR="false"
1059 )
1060 stage $GO
1061
1062 rm -f ${LOCK_BRITNEY}
1063
1064 GO=(
1065     FUNC="pgdakdev"
1066     TIME="dak-dev db"
1067     ARGS=""
1068     ERR="false"
1069 )
1070 stage $GO &
1071
1072 GO=(
1073     FUNC="merkel3"
1074     TIME="merkel ddaccessible sync"
1075     ARGS=""
1076     ERR="false"
1077 )
1078 stage $GO &
1079
1080 GO=(
1081     FUNC="compress"
1082     TIME="compress"
1083     ARGS=""
1084     ERR=""
1085 )
1086 stage $GO &
1087
1088 GO=(
1089     FUNC="aptftpcleanup"
1090     TIME="apt-ftparchive cleanup"
1091     ARGS=""
1092     ERR="false"
1093 )
1094 stage $GO
1095
1096 log "Daily cron scripts successful, all done"
1097
1098 exec > "$logdir/afterdinstall.log" 2>&1
1099
1100 GO=(
1101     FUNC="renamelogfile"
1102     TIME=""
1103     ARGS=""
1104     ERR="false"
1105 )
1106 stage $GO
1107
1108
1109 # Now, at the very (successful) end of dinstall, make sure we remove
1110 # our stage files, so the next dinstall run will do it all again.
1111 rm -f ${stagedir}/*
1112 touch "${DINSTALLEND}"