]> git.uio.no Git - u/mrichter/AliRoot.git/blob - PWGLF/FORWARD/analysis2/qa/RunQAMT.sh
Smal fixes
[u/mrichter/AliRoot.git] / PWGLF / FORWARD / analysis2 / qa / RunQAMT.sh
1 #!/bin/bash
2 #
3 # This script runs the Forward QA for the specified production number
4 #
5 # The scripts downloads and runs the single run QA in parallel 
6 #
7
8 # --- Some aux files -------------------------------------------------
9 style=$ALICE_ROOT/PWGLF/FORWARD/analysis2/qa/style.css 
10 favicon=$ALICE_ROOT/PWGLF/FORWARD/analysis2/qa/fmd_favicon.png
11 logo=$ALICE_ROOT/PWGLF/FORWARD/analysis2/qa/fmd_logo.png
12
13 # --- Help output ----------------------------------------------
14 usage()
15 {
16     cat <<EOF
17 Usage: $0 [OPTIONS] -j [JOBID]
18        $0 [OPTIONS] -p PRODUCTION -P PASS 
19
20 Options:
21         -h,--help                  This help 
22         -j,--jobid      NUMBER     The master job id of the production [$jobid]
23         -v,--verbose               Increase verbosity [$verb]
24         -m,--max-files  NUMBER     Max number of files to get [$maxf]
25         -M,--max-jobs   NUMBER     Max number of consequtive jobs [$maxjobs]
26         -t,--top        DIRECTORY  Output directory [$top]
27         -R,--also-results          Also get QAresults.root for each run
28         -Q,--qa-number  NUMBER     Custom QA id [$qanumber]
29         -p,--production IDENTIFIER Production identifier [$prodfull]
30         -P,--pass       IDENTIFIER Pass identifier [$passfull]
31         -l,--log-file              Log file output [$redir]
32         -b,--barrel     MODE       Fetch barrel data  [$barrel]
33         -f,--force                 Force re-run analysis [$force]
34
35 Note the option -j and the options -p and -P are mutually exclusive,
36 The option -Q is only used if the options -p and -P are given.
37 Production identifiers are of the form LHC11h, LHC11h3, or LHC11h_2. 
38 Pass identifers are of the form pass2, pass1_HLT, or cpass1.  If barrel mode
39 is >0, then do not assume ESD directory.  If mode>1, then get 
40 trending_barrel.root and QAresults_barrel.root
41 EOF
42 }
43
44 # --- Check AliEn token ----------------------------------------------
45 check_token()
46 {
47     uid=`id -u`
48     genv_file=/tmp/gclient_env_${uid}
49     
50     if test ! -f ${genv_file} ; then 
51         echo "No such file: ${genv_file}, please do alien-token-init" \
52             >/dev/stderr
53         exit 1
54     fi
55     . ${genv_file}
56     alien-token-info | grep -q "Token is still valid"
57     if test $? -ne 0 ; then 
58         echo "Token not valid, please re-new" > /dev/stderr 
59         exit 1
60     fi
61 }
62
63 # --- Diagnostics output ---------------------------------------------
64 verb=0
65 mess()
66 {
67     if test $1 -gt $verb ; then return ; fi 
68     shift
69     echo $*
70 }
71
72 # --- Handling of exit -----------------------------------------------
73 lock=
74 handle_exit()
75 {
76     if test "x$lock" = "x" ; then return ; fi 
77     rm -rf $lock 
78 }
79 trap handle_exit EXIT
80
81 # --- Handling of errors ---------------------------------------------
82 last=
83 handle_err()
84 {
85     echo "Error: $last" 
86     exit 1
87 }
88 enable_trap()
89 {
90     trap handle_err ERR
91 }
92 disable_trap()
93 {
94     trap - ERR
95 }
96
97 # --- Check the lock -------------------------------------------------
98 check_lock()
99 {
100     local loc=$1 
101     lock=$loc/.lock
102
103     if test -f $lock ; then 
104         echo "Another QA process is already running:" > /dev/stderr 
105         echo "Content of ${lock}:" > /dev/stderr 
106         cat $lock > /dev/stderr 
107         trap - EXIT
108     exit 1
109     local now=`date` 
110     cat <<EOF > $lock
111 Process: $$
112 User:    $USER
113 Start:   $now
114 EOF
115     fi
116 }
117
118 # --- Parse production information -----------------------------------
119 parse_prod()
120 {
121     prodyear=`echo $prodfull | sed 's/LHC\(..\).*/\1/'` 
122     prodletter=`echo $prodfull | sed "s/LHC${prodyear}\(.\).*/\1/"` 
123     prodpost=`echo $prodfull | sed "s/LHC${prodyear}${prodletter}//"` 
124 }
125
126 parse_pass()
127 {
128     passno=`echo $passfull | sed 's/.*pass\([0-9]*\).*/\1/'`  
129     passpost=`echo $passfull | sed -n "s/.*pass${passno}_//p"` 
130     passpre=`echo $passfull | sed -n "s/pass.*//p"` 
131 }
132
133 # --- Extract parts from the found path ------------------------------
134 force=0
135 year=0
136 passfull=
137 passno=0
138 passpost=
139 passpre=
140 prodfull=
141 prodyear=0
142 prodletter=
143 prodpost=
144 remainder=
145 qanumber=0
146 barrel=0
147 get_parts()
148 {
149     mess 1 "Parsing information from job $@" 
150     year=$1 ; shift 
151     prodfull=$1 ; shift 
152     local lrunn=$1 ; shift
153     local ltype=$1 ; shift 
154     passfull=$1 ; shift 
155     remainder=$1 
156
157     mess 10 "year=$year" 
158     mess 10 "prodfull=$prodfull" 
159     mess 10 "lrunn=$lrunn" 
160     mess 10 "ltype=$ltype" 
161     mess 10 "passfull=$passfull" 
162     mess 10 "remainder=$remainder"
163
164     if test "x$passfull" = "x" ; then 
165         remainder=
166         passfull=$ltype 
167     fi
168     case x$passfull in 
169         *pass*) ;; 
170         *) remainder=$passfull 
171             passfull= 
172             ;;
173     esac
174     parse_pass 
175     parse_prod
176
177     case x$remainder in 
178         xQA*) qanumber=`echo $remainder | sed 's/QA//'`  ;; 
179         *) ;; 
180     esac
181
182 }
183 # --- Get the index for information ----------------------------------
184 skip=0
185 jobu="http://alimonitor.cern.ch/prod/jobs.jsp?t="
186 jobid=
187 get_job() 
188
189     mess 1 "Getting the job information" 
190     wget -q ${jobu}${jobid} -O job.html
191     local lskip
192     let lskip=$skip+1
193     p=`grep "/catalogue/index.jsp?path" job.html | head -n $lskip | tail -n 1 | sed -e 's,.*/alice/\(data\|sim\)/\([^<]*\)<.*,\2,' | tr '/' ' '` 
194     rm -f job.html
195     get_parts $p 
196 }
197
198 # --- Append path element --------------------------------------------
199 append_to_path()
200 {
201     local tmp=$1 ; shift 
202     local add=$1
203     if test "x$tmp" != "x" ; then tmp="${tmp}/" ; fi 
204     echo ${tmp}${add}
205 }
206
207 # --- Get a list of files to get -------------------------------------
208 file=trending.root
209 other=QAresults.root
210 files=
211 path=
212 numf=0
213 get_filelist()
214 {
215     mess 3 "Getting file list" 
216     
217     local datd=data
218     local esdd=ESDs/
219     if test ${barrel} -gt 0 ; then
220         esdd=
221     fi
222     if test ${barrel} -gt 1 ; then      
223         file=trending_barrel.root
224         other=QAresults_barrel.root
225     fi
226     case x$prodpost in 
227         x_*) ;; 
228         x) ;; 
229         *)  mess 3 "Assuming simulation output"
230             datd=sim 
231             esdd= 
232             ;; 
233     esac
234     
235     local paid=
236     if echo "$passno" | grep -q -E '^[0-9]*[.]?[0-9]*$' ; then 
237         if test "x$passfull" != "x" && test $passno -gt 0 ; then 
238             paid=pass${passno}
239         fi
240     else
241         paid=${passfull}
242         passpre=
243         post=
244     fi
245     local post=${passpost}
246     case x$post in 
247         x_*) ;; 
248         x) ;; 
249         *) post="_${post}" ;; 
250     esac
251
252     path=/alice/${datd}/${year}/${prodfull}/
253     local search="${esdd}${passpre}${paid}${post}"
254
255     if test $qanumber -gt 0 ; then 
256         qapost=`printf "QA%02d" $qanumber` 
257         search=`append_to_path "$search" $qapost` 
258     fi
259     
260     search=`append_to_path "$search" $file` 
261
262     cat <<EOF
263         Path:                   $path
264         Search:                 $search
265 EOF
266     mess 1 "Getting list of files from AliEn - can take minutes - be patient"
267     mess 2 "alien_find ${path} ${search}"
268     files=`alien_find ${path} ${search} | grep -v "\(files found\|AND THE\)" 2>> ${redir}` 
269     for i in $files ; do 
270         let numf=$numf+1
271     done 
272     mess 1 -n "Total of $numf files ... "
273     if test $maxf -lt 0 ; then 
274         mess 1 "using all" 
275     else
276         mess 1 "using $maxf first of these"
277     fi
278 }
279
280 # --- Change permissions on files ------------------------------------
281 fix_perm()
282 {
283     if test ! -f $1 ; then return ; fi 
284     chmod g+rwX $1
285     chmod o+rX $1
286 }
287
288 # --- Check if a file is OK ------------------------------------------
289 docheck=1
290 check_file()
291 {
292     if test $docheck -lt 1 ; then return 0; fi 
293     root -l -b  <<EOF >> ${redir} 2>&1 
294 .L $ALICE_ROOT/PWGLF/FORWARD/analysis2/qa/CheckQAFile.C
295 CheckQAFile("$1");
296 .q
297 EOF
298     local ret=$? 
299     mess 2 "Check of $1 -> $ret"
300     # rm -f ${scr}.C 
301     return $ret
302 }
303
304 # --- Analyse a file -------------------------------------------------
305 analyse_file()
306 {
307     local dir=`dirname $1` 
308     local inp=`basename $1` 
309     local out=`echo $inp | sed 's/trending_/tree_/'` 
310     local ret=0
311     mess 2 -n "Analysing $inp -> $out ... "
312
313     if test -f $dir/$out ; then 
314         if test $force -lt 1 ; then 
315             mess 2 "exits"
316             return 0
317         fi
318         rm -f $dir/$out
319     fi
320
321     (cd $dir 
322         root -l -b  <<EOF 
323 .L RunFileQA.C
324 RunFileQA("$inp", "$out", $prodyear, "$prodletter");
325 .q
326 EOF
327         ret=$? 
328         mess 2 " -> $ret"
329         # rm -f ${scr}.C 
330     ) 2>> $redir
331     return $ret
332 }
333
334 # --- Download a single file -----------------------------------------
335 also_results=0
336 analyse_run()
337 {
338     local source=$1 ; shift 
339     local store=$1 ; shift 
340     local r=$1 ; shift 
341     local o=${store}/`basename $file .root`_${r}.root 
342
343     mess 2 -n "$source -> $o ... "
344     if test -f $o && test $force -lt 2; then 
345         mess 2 "exists" 
346         # sleep 1
347     else
348         rm -f ${o}
349         mess 2 -n "copying ... " 
350         alien_cp alien:${source} file:${o} >> ${redir} 2>&1 
351         fix_perm $o 
352         mess 2 "done"
353     fi
354     if test ! -f $o ; then return 1 ; fi 
355
356     if test $also_results -gt 0 ; then 
357         local s=`dirname ${source}`/${other}
358         local q=${store}/`basename $other .root`_${r}.root
359
360         mess 2 -n "$s -> $q ... "
361         if test -f $q && test $force -lt 2 ; then 
362             mess 2 "exists" 
363         else
364             rm -rf ${q}
365             mess 2 -n "copying ... " 
366             alien_cp alien:${s} file:${q} >> ${redir} 2>&1 
367             fix_perm $q
368             mess 2 "done"
369         fi
370     fi
371
372         
373     check_file ${o} 
374     local ret=$? 
375     case $ret in 
376         0|2) ;; 
377         1|3|4|5|6) return 2 ;; 
378     esac
379
380     analyse_file ${o}
381
382     return 0
383 }
384
385 # --- Submit run analysis to background ------------------------------
386 submit_runs()
387 {
388     local out=$1 ; shift
389     local sta=$1 ; shift 
390     local max=$1 ; shift
391     
392     local joblist=
393     local counter=0
394     mess 5 "Submitting $maxjobs jobs from $sta/$maxf" 
395     for i in $@ ; do 
396         let cur=$sta+$counter
397
398         local b=`echo $i | sed -e "s,${path},,"` 
399         local r=`echo $b | sed -e "s,/.*,,"` 
400
401         printf "%3d/%3d: %s\n" $cur $max $r 
402         runs[$counter]=$r
403
404         let counter=$counter+1
405         
406         analyse_run $i $out $r &
407         j=`jobs %% | sed -e 's/^[^0-9]*//' -e 's/[^0-9]*$//'` 
408         joblist="$joblist $j"
409     done
410     
411     counter=0
412     mess 5 "will wait for jobs $joblist"
413     for i in $joblist ; do 
414         mess 5 "waiting for $i of $joblist"
415         wait %$i
416         mess 5 "Analysing ${runs[$counter]} returned $?" 
417         let counter=$counter+1
418     done
419 }
420     
421 # --- Analyse each run in turn ---------------------------------------
422 maxjobs=`grep "processor" /proc/cpuinfo | wc -l`
423 analyse_runs()
424 {
425     local out=$1 ; shift 
426     local max=$1 ; shift 
427     
428     local queued=0
429     local counter=0
430     local start=0
431     local list=
432     while test $# -gt 0 ; do 
433         if test $counter -ge $max ; then 
434             break;
435         fi
436
437         list="$list $1" 
438         shift 
439         let queued=$queued+1 
440         let counter=$counter+1 
441
442         if test $queued -eq 1 ; then 
443             start=$counter
444         fi
445         
446         if test $queued -ge $maxjobs ; then 
447             mess 1 "Submitting $queued jobs from $start/$max"
448             submit_runs $out $start $max $list 
449             list=
450             queued=0 
451         fi
452     done
453     if test $queued -gt 0 ; then 
454         mess 1 "Submitting $queued jobs from $start/$max"
455         submit_runs $out $start $max $list 
456     fi
457 }
458
459 # --- Copy style -----------------------------------------------------
460 copy_aliroot_file()
461 {
462     local file=$1 
463     if test ! -f $file ; then return ; fi 
464     base=`basename $file`
465     rm -f $base 
466     cp $file $base 
467     fix_perm $base
468 }
469 copy_style()
470 {
471     copy_aliroot_file $style
472 }       
473
474 # --- Run the final trending -----------------------------------------
475 make_trend()
476 {
477     local dir=$1 
478     local ret=0
479     mess 1 -n "Analysing $dir ... "
480     (cd $dir 
481         rm -f trend_*_*.html 
482         rm -f trend_*_*.pdf
483         rm -f trend_*_*.root
484
485         root -l -b <<EOF 
486 .L RunFinalQA.C
487 RunFinalQA(".", $prodyear, "$prodletter");
488 .q
489 EOF
490         mess 1 -n " ... "
491         # mess 3 -n "root -l -b -q ${scr}.C "
492         # root -l -b -q ${scr}.C  > /dev/null 2>&1 
493         # local ret=$? 
494         # mess 1 " -> $ret"
495         # rm -f ${scr}.C 
496
497         # do the index file 
498         local idx=`ls trend_*_*.html 2> /dev/null` 
499         for i in $idx ; do 
500             mess 1 "Making index.html point to $i" 
501             sed -e 's,index.html,../index.html,' \
502                 -e "s,!--JOBID--,a target='_blank' href='${jobu}${jobid}'>Job</a," \
503                 < $i > index.html 
504             cp index.html $i
505         done
506         
507         if test ! -f index.html ; then 
508             echo "No index file found" 
509             ret=1
510         else 
511             fix_perm index.html 
512             fix_perm . > /dev/null 2>&1 
513         fi
514
515         copy_style
516         copy_aliroot_file $favicon
517         copy_aliroot_file $logo
518     ) 2>> $redir
519     return $ret
520 }
521
522 # --- Make index file ------------------------------------------------
523 make_index()
524 {
525     local dir=$1   ; shift  
526     local title=$1 ; shift
527     local desc=$1  ; shift 
528     mess 1 "Making index in $dir ($title)"
529     
530     (cd $dir
531         local date=`date` 
532         
533         rm -f index.html 
534
535         cat <<EOF > index.html
536 <!DOCTYPE html>
537 <html>
538   <head>
539     <title>$title</title>
540     <link rel='stylesheet' href='style.css'>
541     <link rel='shortcut icon' href='fmd_favicon.png' type='image/x-png'>
542   </head>
543   <body>
544     <h1><img style='width: 200px;' src='fmd_logo.png'>  &nbsp;$title</h1>
545 EOF
546         if test ! "x$desc" = "x" ; then 
547             echo "<p>$desc</p>" >> index.html
548         fi
549         echo "      <ul>" >> index.html
550         for i in * ; do 
551             if test ! -d $i ; then continue ; fi 
552             echo "      <li><a href='$i'>$i</a></li>" >> index.html
553         done
554         echo "      </ul>" >> index.html 
555         if test "x$desc" = "x" ; then 
556             echo "      <div class='back'><a href='../'>Back</a></div>" \
557                 >> index.html
558         fi
559         cat <<EOF >> index.html    
560     <div class='change'>Last update: $date</div>
561   </body>
562 </html>
563 EOF
564         copy_style 
565         copy_aliroot_file $favicon
566         copy_aliroot_file $logo
567         fix_perm index.html
568         fix_perm . > /dev/null 2>&1 
569     )
570 }
571
572
573 # --- Pass command line options --------------------------------------
574 redir=/dev/null
575 maxf=-1
576 top=.
577 while test $# -gt 0 ; do 
578     case $1 in 
579         -h|--help) usage ; exit 0 ;; 
580         -v|--verbose)      let verb=$verb+1   ;; 
581         -j|--jobid)        jobid=$2           ; shift ;; 
582         -m|--max-files)    maxf=$2            ; shift ;; 
583         -M|--max-jobs)     maxjobs=$2         ; shift ;;
584         -t|--top)          top=$2             ; shift ;;
585         -R|--also-results) also_results=1     ;; 
586         -Q|--qa-number)    qanumber=$2        ; shift ;;
587         -l|--log-file)     redir=             ;; 
588         -b|--barrel)       barrel=$2          ; shift ;;
589         -f|--force)        let force=$force+1 ;; 
590         -p|--production) 
591             prodfull=$2; shift; parse_prod ; year=20${prodyear} ;;
592         -P|--pass) 
593             passfull=$2; shift; parse_pass ;;
594         *) echo "$0: Unknown argument: $1" > /dev/stderr ; exit 1 ;; 
595     esac
596     shift
597 done
598 # --- Initial setup --------------------------------------------------
599 # First, check we have a valid AliEn token, then retrieve the job 
600 # information to parse out the location of the files we need, and 
601 # finally make our output directory and check the lock 
602 check_token
603
604 if test ! "x$jobid" = x ; then 
605     if test ! "x$prodfull" = "x" || test ! "x$passfull" = "x" ; then 
606         cat <<EOF > /dev/stderr
607 Option -j ${jobid} and options -p and -P are mutually exclusive 
608 EOF
609         exit 1
610     fi
611     get_job
612 else 
613     if test "x$prodfull" = "x" || test "x$passfull" = "x" ; then 
614         cat<<EOF > /dev/stderr
615 When specifying prodcution and/or pass both options -p and -P _must_ 
616 be specified. 
617 EOF
618         exit 1
619     elif test ! "x$jobid"  = "x" ; then 
620         cat <<EOF > /dev/stderr
621 Option -j and options -p ${prodfull} and -P ${passfull} are mutually exclusive 
622 EOF
623         exit 1
624     fi
625 fi      
626
627 proddir=LHC${prodyear}${prodletter}
628 store=${proddir}
629 if test ! "x$passno" = "x" ; then 
630     if test "x${passpre}" = "xv" ; then 
631         store=${store}/${passpre}pass${passno}
632     else
633         store=${store}/pass${passno}
634     fi
635 elif test ! "x$prodpost" = "x" ; then 
636     proddir=${proddir}${prodpost}
637     store=${proddir}/sim
638 fi
639 if test ! "x$qanumber" = "x" && test $qanumber -gt 0 ; then 
640     store=${store}_QA${qanumber}
641 fi
642 mkdir -p ${top}/$store 
643 fix_perm ${top}/${proddir}
644 fix_perm ${top}/$store
645
646 if test "x$redir" = "x" ; then 
647     redir=${top}/$store/qa.log 
648     rm -f $redir
649     fix_perm $redir
650 fi
651
652 check_lock ${top}/$store
653
654 # --- Some friendly information --------------------------------------
655 cat <<EOF
656         Year:                   $year
657         Production:             $prodfull 
658           Year:                 $prodyear
659           Letter:               $prodletter
660           Suffix:               $prodpost
661         Pass:                   $passfull
662           Number:               $passno
663           Prefix:               $passpre
664           Postfix:              $passpost
665         Remainder               $remainder
666           QA number             $qanumber
667         Output directory:       ${store}
668         Lock file:              ${lock}
669         Log:                    ${redir}
670         Force:                  ${force}
671 EOF
672 # --- Do a search to find our files ----------------------------------
673 get_filelist
674
675 if test $maxf -gt 0 && test $maxf -lt $numf ; then 
676     numf=$maxf 
677 fi
678
679 # --- Copy scripts to target and compile -----------------------------
680 for i in QABase.h QAPlotter.C QARing.h QAStructs.h QATrender.C \
681     RunFileQA.C RunFinalQA.C ; do
682     cp $ALICE_ROOT/PWGLF/FORWARD/analysis2/qa/$i ${store}/${i}
683     rm -f ${store}/`echo $i | tr '.' '_'`.{so,d}
684 done
685 mess 1 "Compiling QATrender.C"
686 (cd $store && root -l -b <<EOF 
687 gROOT->LoadMacro("QABase.h++g");
688 gROOT->LoadMacro("QATrender.C++g");
689 .q
690 EOF
691 )
692 mess 1 "Compiling QAPlotter.C"
693 (cd $store && root -l -b <<EOF 
694 gROOT->LoadMacro("QABase.h++g");
695 gROOT->LoadMacro("QAPlotter.C++g");
696 .q
697 EOF
698 )
699
700
701 # --- Now get and analyse each run -----------------------------------
702 analyse_runs ${top}/$store $numf $files
703
704 # --- Now analyse all runs -------------------------------------------
705 make_trend ${top}/$store
706
707 # --- Make index files -----------------------------------------------
708 make_index ${top}/${proddir} ${proddir}
709 make_index ${top} "QA for the FMD" \
710     "For more information see <a href='https://twiki.cern.ch/twiki/bin/viewauth/ALICE/FMDQA'>TWiki pages</a>."
711
712 #
713 # EOF
714 #