]> git.uio.no Git - u/mrichter/AliRoot.git/blob - PWGPP/QA/scripts/runQA.sh
Merge branch 'master' of https://git.cern.ch/reps/AliRoot
[u/mrichter/AliRoot.git] / PWGPP / QA / scripts / runQA.sh
1 #!/bin/bash
2 main()
3 {
4   if [[ -z $1 ]]; then
5     echo "Usage: $0 configFile [optionalStuff]"
6     echo "  - optionalStuff overrides config file, e.g.:"
7     echo "       $0 configFile inputList=somefile.list outputDirectory='${PWD}'/output"
8     exit 1
9   fi
10   [[ ! -f $1 ]] && echo "argument not a file" && exit 1  
11
12  
13   configFile=${1}
14   shift 1
15
16   [[ -z $ALICE_ROOT ]] && source $alirootEnv
17   [[ -z $ALICE_ROOT ]] && echo "ALICE_ROOT not defined" && exit 1
18
19   ocdbregex='raw://'
20   [[ ${ocdbStorage} =~ ${ocdbregex} ]] && alien-token-init
21
22   updateQA ${configFile} $@
23 }
24
25 updateQA()
26 {
27   #this guy takes config file as only positional argument
28   #optional stugg allowerd to override config
29   umask 0002
30   configFile=${1}
31   shift 1
32   parseConfig $configFile $@
33
34   dateString=$(date +%Y-%m-%d-%H-%M)
35   echo "Start time QA process: $dateString"
36
37   #logging
38   mkdir -p $logDirectory
39   [[ ! -d $logDirectory ]] && echo "no log dir $logDirectory" && exit 1
40   logFile="$logDirectory/${0##*/}.${dateString}.log"
41   touch ${logFile}
42   [[ ! -f ${logFile} ]] && echo "cannot write logfile $logfile" && exit 1
43   echo "logFile = $logFile"
44   exec &>${logFile}
45
46   #check lock
47   lockFile=${logDirectory}/runQA.lock
48   [[ -f ${lockFile} ]] && echo "lock ${lockFile} exists!" && exit 1
49   touch ${lockFile}
50   [[ ! -f ${lockFile} ]] && echo "cannot lock $lockFile" && exit 1
51   
52   #be paranoid and make some full paths
53   inputList=$(readlink -f ${inputList})
54   workingDirectory=$(readlink -f ${workingDirectory})
55   mkdir -p ${workingDirectory}
56   if [[ ! -d ${workingDirectory} ]]; then
57     echo "working dir $workingDirectory does not exist and cannot be created"
58     return 1
59   fi
60   cd ${workingDirectory}
61
62   ################################################################
63   #ze detector loop
64   for detectorScript in $ALICE_ROOT/PWGPP/QA/detectorQAscripts/*; do
65
66     [[ ! ${detectorScript} =~ .*\.sh ]] && continue
67     detector=${detectorScript%.sh}
68     detector=${detector##*/}
69     outputDir=$(substituteDetectorName ${detector} ${outputDirectory})
70     tmpRunDir=${workingDirectory}/tmpQArunDir${detector}
71     if ! mkdir -p ${tmpRunDir}; then
72       echo "cannot create the temp dir $tmpRunDir"
73       continue
74     fi
75     cd ${tmpRunDir}
76
77     tmpPrefix=${tmpRunDir}/${outputDir}
78     echo "running QA for ${detector}"
79     echo "  outputDir=$outputDir"
80     echo "  tmpPrefix=$tmpPrefix"
81     
82     unset -f runLevelQA
83     unset -f periodLevelQA
84     source ${detectorScript}
85
86     #################################################################
87     #produce the QA and trending tree for each file (run)
88     while read qaFile; do
89     
90       guessRunData ${qaFile}
91
92       runDir=${tmpPrefix}/${dataType}/${year}/${period}/${pass}/000${runNumber}
93       mkdir -p ${runDir}
94       cd ${runDir}
95
96       #handle the case of a zip archive
97       [[ "$qaFile" =~ .*.zip$ ]] && qaFile="${qaFile}#QAresults.root"
98       
99       echo running ${detector} runLevelQA for run ${runNumber} from ${qaFile}
100       runLevelQA ${qaFile} &> runLevelQA.log
101
102       cd ${tmpRunDir}
103     
104     done < ${inputList}
105
106     #################################################################
107     #cache which productions were (re)done
108     arrOfTouchedProductions=( $(/bin/ls -d ${tmpPrefix}/*/*/*/*) )
109     echo "list of processed productions:"
110     echo "    ${arrOfTouchedProductions[@]}"
111     echo
112     #################################################################
113     #(re)do the merging/trending in the final destination
114     for tmpProductionDir in ${arrOfTouchedProductions[@]}; do
115     
116       productionDir=${outputDir}/${tmpProductionDir#${tmpPrefix}}
117       
118       echo mkdir -p ${productionDir}
119       mkdir -p ${productionDir}
120       if [[ ! -d ${productionDir} ]]; then 
121         echo "cannot make productionDir $productionDir" && continue
122       fi
123       
124       #move to final destination
125       for dir in ${tmpProductionDir}/*; do
126         oldRunDir=${outputDir}/${dir#${tmpPrefix}}
127         if [[ -d ${oldRunDir} ]]; then
128           echo "removing old run: rm -rf ${oldRunDir}"
129           rm -rf ${oldRunDir}
130         fi
131         echo "moving output to final destination"
132         echo mv -f ${dir} ${productionDir}
133         mv -f ${dir} ${productionDir}
134       done
135     
136       guessRunData "${productionDir}/dummyName"
137
138       cd ${productionDir}
139
140       rm -f trending.root
141       hadd trending.root 000*/trending.root
142
143       echo running ${detector} periodLevelQA for production ${period}/${pass}
144       periodLevelQA trending.root &> periodLevelQA.log
145       
146       cd ${tmpRunDir}
147     
148     done
149
150     cd ${workingDirectory}
151     echo cleaning up: rm -rf ${tmpRunDir}
152     rm -rf ${tmpRunDir}
153   done
154
155   #remove lock
156   rm -f ${lockFile}
157 }
158
159 parseConfig()
160 {
161   configFile=${1}
162   shift
163
164   #first, source the config file
165   if [ -f ${configFile} ]; then
166     source ${configFile}
167   else
168     echo "config file ${configFile} not found!, skipping..."
169   fi
170
171   #then, parse the options as they override the options from file
172   while [[ -n ${1} ]]; do
173     local var=${1#--}
174     eval "${var}"
175     shift
176   done
177 }
178
179 guessRunData()
180 {
181   #guess the period from the path, pick the rightmost one
182   period=""
183   runNumber=""
184   year=""
185   pass=""
186   legoTrainRunNumber=""
187   dataType=""
188
189   local shortRunNumber=""
190   local IFS="/"
191   declare -a path=( $1 )
192   local dirDepth=$(( ${#path[*]}-1 ))
193   i=0
194   for ((x=${dirDepth};x>=0;x--)); do
195
196     [[ $((x-1)) -ge 0 ]] && local fieldPrev=${path[$((x-1))]}
197     local field=${path[${x}]}
198     local fieldNext=${path[$((x+1))]}
199
200     [[ ${field} =~ ^[0-9]*$ && ${fieldNext} =~ (.*\.zip$|.*\.root$) ]] && legoTrainRunNumber=${field}
201     [[ -n ${legoTrainRunNumber} && -z ${pass} ]] && pass=${fieldPrev}
202     [[ ${field} =~ ^LHC[0-9][0-9][a-z].*$ ]] && period=${field%_*}
203     [[ ${field} =~ ^000[0-9][0-9][0-9][0-9][0-9][0-9]$ ]] && runNumber=${field#000}
204     [[ ${field} =~ ^[0-9][0-9][0-9][0-9][0-9][0-9]$ ]] && shortRunNumber=${field}
205     [[ ${field} =~ ^20[0-9][0-9]$ ]] && year=${field}
206     [[ ${field} =~ ^(^sim$|^data$) ]] && dataType=${field}
207     (( i++ ))
208   done
209   [[ -z ${legoTrainRunNumber} ]] && pass=${path[$((dirDepth-1))]}
210   [[ "${dataType}" =~ ^sim$ ]] && pass="passMC" && runNumber=${shortRunNumber}
211   
212   if [[ -z ${dataType} || -z ${year} || -z ${period} || -z ${runNumber}} || -z ${pass} ]];
213   then
214     #error condition
215     return 1
216   else
217     #ALL OK
218     return 0
219   fi
220 }
221
222 substituteDetectorName()
223 {
224   local det=$1
225   local dir=$2
226   [[ ${dir} =~ \%det ]] && det=${det,,} && echo ${dir/\%det/${det}}
227   [[ ${dir} =~ \%DET ]] && det=${det} && echo ${dir/\%DET/${det}}
228 }
229
230 main $@