ATLAS Offline Software
dq_defect_summary.py
Go to the documentation of this file.
1 #!/bin/env python
2 # Author: Steve Farrell <sfarrell@cern.ch>
3 # Part of the DataQuality/DQDefects package
4 # June 2012
5 
6 import sys
7 import fnmatch
8 
9 from argparse import ArgumentParser
10 from textwrap import dedent
11 import logging; log = logging.getLogger("dq_defect_summary")
12 
13 from DQDefects import DefectsDB
14 from DQDefects.db import DEFAULT_CONNECTION_STRING
15 
16 from DQUtils.general import timer
17 from DQUtils.logger import init_logger
18 from DQUtils.lumi import fetch_lumi_inputs, compute_lumi, compute_lumi_many_channels
19 from DQUtils.periods import fetch_project_period_runs
20 
21 
22 class Defect(object):
23  """
24  Class to hold all the information needed for printing DQ summary for one defect
25  """
26  def __init__(self, name, description, depends, virtual, intolerable, lumi):
27  if description == name:
28  # Don't bother pretending that there is a description if it is just
29  # equal to the name
30  description = ""
31 
32  (self.name, self.description, self.depends, self.lumi, self.virtual,
33  self.intolerable) = (
34  name, description, depends, lumi, virtual, intolerable)
35 
36  self.lumiStr = "{0:<.2f}".format(self.lumi)
37 
38 
39 def print_virtual_tree(defect, all_defects, depth=0, max_depth=0):
40 
41  if defect.lumi > 0 or depth == 0:
42  print("| "*depth + defect.lumiStr, defect.name)
43 
44  if max_depth < 0 or depth < max_depth:
45  parents = [ all_defects[d] for d in defect.depends ]
46 
47  # Sort list of parents by lumi
48  parents.sort(key=lambda d: d.lumi, reverse=True)
49 
50  # Recursively call this function on defects down the tree
51  for parent in parents:
52  print_virtual_tree(parent, all_defects, depth+1, max_depth)
53 
54 
55 def get_primary_defects(defect, all_defects):
56  primary_defects = set()
57  def recursive_search(defect):
58  if defect.virtual:
59  for parent in defect.depends:
60  recursive_search(all_defects[parent])
61  else:
62  primary_defects.add(defect)
63  recursive_search(defect)
64  return primary_defects
65 
66 def print_primary_defects(defect, all_defects, max_primary):
67  primary_list = sorted(get_primary_defects(defect, all_defects),
68  key=lambda d: d.lumi, reverse=True)
69  print(defect.lumiStr, defect.name)
70  if max_primary >= 0:
71  del primary_list[max_primary:]
72  for primary in primary_list:
73  if primary.lumi > 0:
74  print(" " + primary.lumiStr, primary.name)
75 
76 def main():
77  parser = ArgumentParser(description="Summarize DQ Defects")
78  a = parser.add_argument
79  add_group = parser.add_argument_group
80 
81  # Specify range to process
82  a("-p", "--project", default="data15_13TeV",
83  help="Data project (default: data15_13TeV)")
84  a("-P", "--period", default=None, nargs="*", help="Data period(s)")
85  a("-r", "--run", default=None, nargs="*", help="Run number(s) to process")
86  a("-R", "--range", help="Inclusive run range: e.g. 150000-151000")
87 
88  # Specify defects to process
89  a("-d", "--defects", default=None, nargs="*",
90  help="Defects to process. Use * for wildcard (default: None)")
91 
92  # Print mode, primary or virtual tree
93  a("-q", "--tree", action="store_true",
94  help="Dump virtual defect tree. Set depth with -D")
95 
96  # Other job options
97  a("-n", "--num-primary", default=-1, type=int,
98  help="Max number of primary defects to display in default mode (default: all)")
99  a("-D", "--depth", default=-1, type=int,
100  help="Max virtual defect depth to print in virtual tree mode (default: all)")
101  a("-c", "--connection-string", default=DEFAULT_CONNECTION_STRING,
102  help="Database connection to use (default: %s)" % DEFAULT_CONNECTION_STRING)
103  a("-l", "--lumi-tag", default='OflLumi-8TeV-002',
104  help="Luminosity tag (default: OflLumi-8TeV-002)")
105  a("-t", "--tag", default="HEAD",
106  help="Tag to use (default: HEAD)")
107  a("--require-ready", default=True, type=int,
108  help="Calculate luminosity with respect to ATLAS READY (default: True)")
109  a("--reject-busy", default=False, type=int,
110  help="Calculate luminosity with respect to not-busy (default: False)")
111  a("--nb", action="store_true", help="Show lumi in units of 1/nb instead of 1/pb")
112  a("-v", "--verbose", default=1, type=int,
113  help="Set verbosity (default: 1)")
114 
115  args = parser.parse_args()
116 
117  init_logger(verbose=args.verbose)
118 
119  # Units
120  units = 1e3 if args.nb else 1e6
121  unit_string = "(1/nb)" if args.nb else "(1/pb)"
122 
123  # Instantiate the database interface
124  with timer("Instantiate DefectsDB"):
125  db = DefectsDB(args.connection_string, tag=args.tag)
126 
127  # Set runs to process
128  # TODO: control these via run lumi iovs, rather than a set of good_runs
129  # similar to how it is done in dq_defect_compare_tags
130  good_runs = None
131  if args.range:
132  since, until = map(int, args.range.split("-"))
133  elif args.run:
134  good_runs = set( map(int, args.run) )
135  #since, until = args.run, args.run+1
136  since, until = min(good_runs), max(good_runs)+1
137  else:
138  project_dict = fetch_project_period_runs()
139  if args.period:
140  #good_runs = set( project_dict[args.project][args.period] )
141  good_runs = set()
142  for period in args.period:
143  good_runs.update( project_dict[args.project][period] )
144  since, until = min(good_runs), max(good_runs)+1
145  else:
146  good_runs = set()
147  for period, period_runs in project_dict[args.project].iteritems():
148  good_runs.update(period_runs)
149  since, until = min(good_runs), max(good_runs)+1
150 
151 
152  iov_range = (since, 0), (until, 0)
153  log.info("Processing range: " + str(iov_range))
154  #log.info(good_runs)
155 
156  # Fetch all defect IOVs in range
157  with timer("Fetch defects"):
158  all_defect_iovs = db.retrieve(*iov_range)
159 
160  # Grab defect information
161  with timer("Fetch defect info"):
162  descriptions = db.all_defect_descriptions
163  intolerables = db.get_intolerable_defects()
164  virtuals = db.virtual_defect_names
165 
166  # Grab lbs and lumi variables in range
167  with timer("Fetch lumi inputs"):
168  lbs, lumis = fetch_lumi_inputs(iov_range, args.lumi_tag)
169 
170  # Compute lumi per channel
171  with timer("Compute luminosities"):
172  # Filtering defects
173  exclude_iovs = []
174  # Defect for ATLAS READY
175  if args.require_ready:
176  exclude_iovs.append(all_defect_iovs.by_channel["GLOBAL_NOTREADY"])
177  # Defect for detector busy
178  if args.reject_busy:
179  exclude_iovs.append(all_defect_iovs.by_channel["GLOBAL_BUSY"])
180  # Compute total luminosity
181  lumi_total = compute_lumi(lbs, lumis, lbs, exclude_iovsets=exclude_iovs,
182  good_runs=good_runs)/units
183  # Compute luminosity for all defects
184  lumi_by_defect = compute_lumi_many_channels(lbs, lumis, all_defect_iovs,
185  exclude_iovsets=exclude_iovs,
186  good_runs=good_runs)
187 
188  my_defect_names = []
189  if args.defects:
190  all_defect_names = db.defect_names | db.virtual_defect_names
191  for defect_arg in args.defects:
192  my_defect_names.extend(sorted(fnmatch.filter(all_defect_names, defect_arg)))
193 
194  logics = db.virtual_defect_logics
195 
196  # Build the defect objects
197  all_defects = {}
198  for name, description in sorted(descriptions.iteritems()):
199  virtual, intolerable = name in virtuals, name in intolerables
200  depends = []
201  logic = logics.get(name, None)
202  if logic: depends = logic.clauses
203  all_defects[name] = Defect(name, description, depends, virtual, intolerable,
204  lumi_by_defect.get(name, 0)/units)
205 
206  # My defects
207  my_defects = [ all_defects[d] for d in my_defect_names ]
208  my_defects.sort(key=lambda d: d.lumi, reverse=True)
209 
210  print("\nTotal luminosity", unit_string, "\n")
211  print("{0:<.2f}".format(lumi_total))
212 
213  print("\nDefect luminosity", unit_string, "\n")
214 
215  #for defect_name in my_defect_names:
216  for defect in my_defects:
217 
218  if args.tree:
219  # Virtual defect tree
220  print_virtual_tree(defect, all_defects, depth=0, max_depth=args.depth)
221  else:
222  # Primary defect dump
223  print_primary_defects(defect, all_defects, max_primary=args.num_primary)
224 
225  print()
226 
227 
228 if __name__ == "__main__":
229  main()
python.lumi.compute_lumi_many_channels
def compute_lumi_many_channels(lbs, lumis, iovs, exclude_iovsets=[], good_runs=None)
Definition: lumi.py:66
python.Bindings.iteritems
iteritems
Definition: Control/AthenaPython/python/Bindings.py:812
max
#define max(a, b)
Definition: cfImp.cxx:41
dq_defect_summary.print_virtual_tree
def print_virtual_tree(defect, all_defects, depth=0, max_depth=0)
Definition: dq_defect_summary.py:39
vtune_athena.format
format
Definition: vtune_athena.py:14
dq_defect_summary.Defect
Definition: dq_defect_summary.py:22
dq_defect_summary.get_primary_defects
def get_primary_defects(defect, all_defects)
Definition: dq_defect_summary.py:55
python.lumi.fetch_lumi_inputs
def fetch_lumi_inputs(range_iov, tag="OflLumi-7TeV-002")
Definition: lumi.py:125
dq_defect_summary.Defect.__init__
def __init__(self, name, description, depends, virtual, intolerable, lumi)
Definition: dq_defect_summary.py:26
python.utils.AtlRunQueryTimer.timer
def timer(name, disabled=False)
Definition: AtlRunQueryTimer.py:86
python.periods.fetch_project_period_runs
def fetch_project_period_runs()
Definition: periods.py:64
compute_lumi
Definition: compute_lumi.py:1
dq_defect_summary.Defect.lumiStr
lumiStr
Definition: dq_defect_summary.py:36
DerivationFramework::TriggerMatchingUtils::sorted
std::vector< typename T::value_type > sorted(T begin, T end)
Helper function to create a sorted vector from an unsorted one.
CxxUtils::set
constexpr std::enable_if_t< is_bitmask_v< E >, E & > set(E &lhs, E rhs)
Convenience function to set bits in a class enum bitmask.
Definition: bitmask.h:224
min
#define min(a, b)
Definition: cfImp.cxx:40
python.logger.init_logger
def init_logger(verbose=False, quiet=False)
Definition: DataQuality/DQUtils/python/logger.py:113
dq_defect_summary.print_primary_defects
def print_primary_defects(defect, all_defects, max_primary)
Definition: dq_defect_summary.py:66
a
TList * a
Definition: liststreamerinfos.cxx:10
Muon::print
std::string print(const MuPatSegment &)
Definition: MuonTrackSteering.cxx:28
dq_defect_summary.main
def main()
Definition: dq_defect_summary.py:76
pickleTool.object
object
Definition: pickleTool.py:30
str
Definition: BTagTrackIpAccessor.cxx:11