CMS 3D CMS Logo

runregparse.py
Go to the documentation of this file.
1 #!/usr/bin/env python
2 
3 # LM: version date: 01/02/2010 --> fixed dataset search and added json output file (optional)
4 # LM: updated 03/04/2010 --> adapted to new runreg api (and dcs status info)
5 # LM: updated 15/04/2010 --> added bfield threshold
6 
7 # include XML-RPC client library
8 # RR API uses XML-RPC webservices interface for data access
9 from __future__ import print_function
10 import xmlrpclib,sys,ConfigParser,os,string,commands,time,re
11 # for json support
12 try: # FUTURE: Python 2.6, prior to 2.6 requires simplejson
13  import json
14 except:
15  try:
16  import simplejson as json
17  except:
18  print("Please use lxplus or set an environment (for example crab) with json lib available")
19  sys.exit(1)
20 
21 global QF_Req,ls_temp_data,QF_ALL_SYS,EXCEPTION,EXRUN
22 EXCEPTION=False
23 EXRUN=-1
24 
25 def invert_intervals(intervals,min_val=1,max_val=9999):
26  # first order and merge in case
27  if not intervals:
28  return []
29  intervals=merge_intervals(intervals)
30  intervals = sorted(intervals, key = lambda x: x[0])
31  result = []
32  if min_val==-1:
33  # defin min and max
34  (a,b)=intervals[0]
35  min_val=a
36  if max_val==-1:
37  (a,b)=intervals[len(intervals)-1]
38  max_val=b
39 
40  curr_min=min_val
41  for (x,y) in intervals:
42  if x>curr_min:
43  result.append((curr_min,x-1))
44  curr_min=y+1
45  if curr_min<max_val:
46  result.append((curr_min,max_val))
47 
48 # print min_val,max_val
49  return result
50 
51 def merge_intervals(intervals):
52  if not intervals:
53  return []
54  intervals = sorted(intervals, key = lambda x: x[0])
55  result = []
56  (a, b) = intervals[0]
57  for (x, y) in intervals[1:]:
58  if x <= b:
59  b = max(b, y)
60  else:
61  result.append((a, b))
62  (a, b) = (x, y)
63  result.append((a, b))
64  return result
65 
66 def remove_html_tags(data):
67  p = re.compile(r'<.*?>')
68  newdata=p.sub('', data)
69  newdata=newdata.replace("&nbsp;","")
70  return newdata
71 
73  result= re.sub(r'\s', '', data)
74  return result
75 
76 def searchrun(runno):
77  global QF_Req,ls_temp_data,QF_ALL_SYS,EXCEPTION,EXRUN
78  intervallist=[]
79  selectls=""
80 
81  for line in ls_temp_data.split("\n"):
82  if runno in line:
83 # print line
84  try:
85  if "%%%BAD LS INFO BEGIN%%%" in line:
86  selectls=line.split("%%%BAD LS INFO BEGIN%%%")[1]
87  selectls=selectls.split("%%%BAD LS INFO END%%%")[0]
88  selectls=remove_html_tags(selectls)
89  selectls=remove_extra_spaces(selectls)
90  # print selectls
91  for tag in QF_ALL_SYS:
92  selectls=selectls.replace(tag+":","\n"+tag+":")
93  # print selectls
94 
95  for line in selectls.split("\n"):
96  try:
97  tag=line.split(":")[0]
98  intervals=line.split(":")[1]
99  except:
100  continue
101  if tag in QF_Req.keys():
102  if QF_Req[tag]=="GOOD":
103  for interval in intervals.split(","):
104  if "ALL" in interval:
105  lmin=1
106  lmax=9999
107  else:
108  strmin=interval.split('-')[0]
109  strmax=interval.split('-')[1]
110  lmin=int(strmin)
111  if "END" in strmax:
112  lmax=9999
113  else:
114  lmax=int(strmax)
115  intervallist.append((lmin,lmax))
116  except:
117  EXCEPTION=True
118  EXRUN=int(runno)
119  intervallist=merge_intervals(intervallist)
120  # print runno, intervallist
121  return intervallist
122 
123 
124 
125 #main starts here#
126 
127 QF_Req={}
128 GOODRUN={}
129 compactList = {}
130 
131 QF_ALL_SYS=["Hcal","Track","Strip","Egam","Es","Dt","Csc","Pix","Muon","Rpc","Castor","Jmet","Ecal","L1t","Hlt","NONE"]
132 QF_ALL_STAT=["GOOD","BAD","EXCL","NONE"]
133 DCS_ALL=['Bpix','Fpix','Tibtid','TecM','TecP','Tob','Ebminus','Ebplus','EeMinus','EePlus','EsMinus','EsPlus','HbheA','HbheB','HbheC','H0','Hf','Dtminus','Dtplus','Dt0','CscMinus','CscPlus','Rpc','Castor',"NONE"]
134 
135 # reading config file
136 CONFIGFILE='runreg.cfg'
137 CONFIG = ConfigParser.ConfigParser()
138 print('Reading configuration file from ',CONFIGFILE)
139 CONFIG.read(CONFIGFILE)
140 
141 DATASET=CONFIG.get('Common','Dataset')
142 GROUP=CONFIG.get('Common','Group')
143 HLTNAMEFILTER=CONFIG.get('Common','HLTnameFilter')
144 ADDRESS=CONFIG.get('Common','RunReg')
145 RUNMIN=CONFIG.get('Common','Runmin')
146 RUNMAX=CONFIG.get('Common','Runmax')
147 QFLAGS=CONFIG.get('Common','QFLAGS')
148 BFIELD=CONFIG.get('Common','BField_thr')
149 LSPARSE=CONFIG.get('Common','LSCOMMENT')
150 DCSSTAT=CONFIG.get('Common','DCS')
151 DCSLIST=string.split(DCSSTAT,',')
152 
153 OUTPUTFILENAME=CONFIG.get('Common',"OutputFileName")
154 
155 LSCOMMENT=True
156 if "TRUE" in LSPARSE.upper() or "1" in LSPARSE.upper() or "YES" in LSPARSE.upper():
157  LSCOMMENT=True
158 elif "FALSE" in LSPARSE.upper() or "0" in LSPARSE.upper() or "NO" in LSPARSE.upper():
159  LSCOMMENT=False
160 else:
161  print("Error in parsing LSCOMMENT cfg parameter: LSPARSE")
162  sys.exit(1)
163 
164 QFlist=string.split(QFLAGS,',')
165 for QF in QFlist:
166  syst=string.split(QF,":")[0]
167  value=string.split(QF,":")[1]
168  if syst not in QF_ALL_SYS or value not in QF_ALL_STAT:
169  print("QFLAG not valid:",syst,value)
170  sys.exit(1)
171  QF_Req[syst]=value
172 
173 for dcs in DCSLIST:
174  if dcs not in DCS_ALL:
175  print("DCS not valid:",dcs)
176  sys.exit(1)
177 
178 
179 CFGLIST=CONFIG.items('Common')
180 JSONFILE=CONFIG.get('Common','JSONFILE')
181 
182 try:
183  BFIELD_float=float(BFIELD)
184 except:
185  print("BFIELD threshold value not understood:",BFIELD)
186  sys.exit(1)
187 
188 # report the request
189 
190 print("You asked for the runreg info in the run range:"+RUNMIN+"-"+RUNMAX)
191 print("for dataset: "+DATASET)
192 print("with the following quality flags:")
193 for SS in QF_Req.keys():
194  print(SS, QF_Req[SS])
195 print("and with the following DCS status:")
196 for dcs in DCSLIST:
197  print(dcs)
198 print("Manual bad LS in comment column:",LSCOMMENT)
199 #sys.exit(1)
200 
201 # get handler to RR XML-RPC server
202 FULLADDRESS=ADDRESS+"/xmlrpc"
203 print("RunRegistry from: ",FULLADDRESS)
204 server = xmlrpclib.ServerProxy(FULLADDRESS)
205 
206 # build up selection in RUN table
207 sel_runtable="{groupName} ='"+GROUP+"' and {runNumber} >= "+RUNMIN+" and {runNumber} <= "+RUNMAX+" and {bfield}>"+BFIELD+" and {datasetName} LIKE '"+DATASET+"'"
208 
209 # the lumisection selection is on the Express dataset:
210 sel_dstable="{groupName} ='"+GROUP+"' and {runNumber} >= "+RUNMIN+" and {runNumber} <= "+RUNMAX+" and {bfield}>"+BFIELD+" and {datasetName} LIKE '%Express%'"
211 
212 for key in QF_Req.keys():
213  if key != "NONE" and QF_Req[key]!="NONE":
214  sel_runtable+=" and {cmp"+key+"} = '"+QF_Req[key]+"'"
215  sel_dstable+=" and {cmp"+key+"} = '"+QF_Req[key]+"'"
216 #print sel_runtable
217 
218 # build up selection in RUNLUMISECTION table, not requestuing bfield here because only runs in the run table selection will be considered
219 sel_dcstable="{groupName} ='"+GROUP+"' and {runNumber} >= "+RUNMIN+" and {runNumber} <= "+RUNMAX
220 for dcs in DCSLIST:
221  if dcs !="NONE":
222  sel_dcstable+=" and {parDcs"+dcs+"} = 1"
223 # = 'True'"
224 # print sel_dcstable
225 
226 Tries=0
227 print(" ")
228 while Tries<10:
229  try:
230  print("Accessing run registry....")
231  dcs_data = server.DataExporter.export('RUNLUMISECTION', 'GLOBAL', 'json', sel_dcstable)
232  run_data = server.DataExporter.export('RUN', 'GLOBAL', 'csv_runs', sel_runtable)
233  ls_temp_data = server.DataExporter.export('RUN', 'GLOBAL', 'csv_datasets', sel_dstable)
234  break
235  except:
236  print("Something wrong in accessing runregistry, retrying in 3s....")
237  Tries=Tries+1
238  time.sleep(3)
239 if Tries==10:
240  print("Run registry unaccessible.....exiting now")
241  sys.exit(1)
242 
243 #print dcs_data
244 # print "run data: ", run_data
245 #print ls_temp_data
246 # find LS info in comment
247 
248 
249 
250 LISTOFRUN=[]
251 selectedRuns = open(OUTPUTFILENAME, 'w')
252 print("Saving selected runs to file OUTPUTFILENAME")
253 for line in run_data.split("\n"):
254  run=line.split(',')[0]
255  if run.isdigit():
256  hlt=line.split(',')[9]
257  print("for run", run, "hlt is", hlt)
258  if HLTNAMEFILTER == "" or hlt.find(HLTNAMEFILTER):
259  LISTOFRUN.append(run)
260  selectedRuns.write(run+"\n")
261 selectedRuns.close()
262 
263 selected_dcs={}
264 jsonlist=json.loads(dcs_data)
265 
266 
267 for element in jsonlist:
268  if element in LISTOFRUN:
269 # first search manual ls certification
270  if LSCOMMENT:
271  # using LS intervals in comment
272  manualbad_int=searchrun(element)
273  # make a badlumi list
274  dcsbad_int=invert_intervals(jsonlist[element])
275  combined=[]
276  for interval in manualbad_int:
277  combined.append(interval)
278  for interval in dcsbad_int:
279  combined.append(interval)
280  combined=merge_intervals(combined)
281  combined=invert_intervals(combined)
282  selected_dcs[element]=combined
283  else:
284  # using only DCS info
285  selected_dcs[element]=jsonlist[element]
286  # combined include bith manual LS and DCS LS
287 
288 #JSONOUT=json.dumps(selected_dcs)
289 # WARNING: Don't use selected_dcs before dumping into file, it gets screwed up (don't know why!!)
290 if JSONFILE != "NONE":
291  lumiSummary = open(JSONFILE, 'w')
292  json.dump(selected_dcs, lumiSummary)
293  lumiSummary.close()
294  print(" ")
295  print("-------------------------------------------")
296  print("Json file: ",JSONFILE," written.")
297 
298 
299 # buildup cms snippet
300 selectlumi="process.source.lumisToProcess = cms.untracked.VLuminosityBlockRange(\n"
301 ranges = []
302 runs_to_print = sorted(selected_dcs.keys())
303 for run in runs_to_print:
304  blocks = sorted(selected_dcs[run])
305  prevblock = [-2,-2]
306  for lsrange in blocks:
307  if lsrange[0] == prevblock[1]+1:
308  print("Run: ",run,"- This lumi starts at ", lsrange[0], " previous ended at ", prevblock[1]+1, " so I should merge")
309  prevblock[1] = lsrange[1]
310  ranges[-1] = "\t'%s:%d-%s:%d',\n" % (run, prevblock[0],
311 run, prevblock[1])
312  else:
313  ranges.append("\t'%s:%d-%s:%d',\n" % (run, lsrange[0],
314 run, lsrange[1]))
315  prevblock = lsrange
316 selectlumi += "".join(ranges)
317 selectlumi += ")"
318 
319 
320 print("-------------------------------------------")
321 print(" ")
322 print("CFG snippet to select:")
323 print(selectlumi)
324 
325 if EXCEPTION:
326  print("WARNING: Something wrong in manual lumisection selection tag for run: "+str(EXRUN))
S & print(S &os, JobReport::InputFile const &f)
Definition: JobReport.cc:66
def invert_intervals(intervals, min_val=1, max_val=9999)
Definition: runregparse.py:25
def merge_intervals(intervals)
Definition: runregparse.py:51
static std::string join(char **cmd)
Definition: RemoteFile.cc:18
def remove_extra_spaces(data)
Definition: runregparse.py:72
def remove_html_tags(data)
Definition: runregparse.py:66
#define str(s)
def searchrun(runno)
Definition: runregparse.py:76