From ec2017abc8184261ea6498227308eadd8e38d5b0 Mon Sep 17 00:00:00 2001
From: Mark Stockton <mark@cern.ch>
Date: Fri, 24 Jul 2020 15:22:41 +0200
Subject: [PATCH] Move PrescaleJSON creation to TMMT from TrigConfigSvc

Move applyPrescale to MenuPrescaleConfig and cleanup of other non-used MenuUtil functions
---
 .../TrigConfigSvc/python/TrigConfigSvcCfg.py  |  26 -----
 .../TriggerJobOpts/share/runHLT_standalone.py |  12 +-
 .../HLTMenuConfig/Menu/GenerateMenuMT.py      |   6 +-
 .../HLTMenuConfig/Menu/HLTPrescaleJSON.py     |  66 +++++++++++
 .../HLTMenuConfig/Menu/MenuPrescaleConfig.py  |  28 ++++-
 .../python/HLTMenuConfig/Menu/MenuUtil.py     | 107 +++++++-----------
 6 files changed, 146 insertions(+), 99 deletions(-)
 create mode 100644 Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/HLTPrescaleJSON.py

diff --git a/Trigger/TrigConfiguration/TrigConfigSvc/python/TrigConfigSvcCfg.py b/Trigger/TrigConfiguration/TrigConfigSvc/python/TrigConfigSvcCfg.py
index a1603a63f1b9..d5faa4f17ab3 100644
--- a/Trigger/TrigConfiguration/TrigConfigSvc/python/TrigConfigSvcCfg.py
+++ b/Trigger/TrigConfiguration/TrigConfigSvc/python/TrigConfigSvcCfg.py
@@ -92,32 +92,6 @@ def createL1PrescalesFileFromMenu( flags=None ):
         log.info("Generated default L1 prescale set %s", outfile.name)
 
 
-# Creates an HLT Prescale file from the menu
-# this is a temporary solution, in the final version the HLTPrescalesSet file should come from the menu
-def createHLTPrescalesFileFromMenu( flags=None ):
-    log = logging.getLogger('TrigConfigSvcCfg')
-    menuFN = getHLTMenuFileName( flags )
-    with open(menuFN,'r') as fh:
-        data = json.load(fh, object_pairs_hook = odict)
-        pso = odict()
-        pso['filetype'] = 'hltprescale'
-        pso['name'] = data['name']
-        pso['prescales'] = odict()
-        ps = pso['prescales']
-        for name, chain in data['chains'].items():
-            ps[name] = odict([
-                ("name", name),
-                ("counter", chain['counter']),
-                ("hash", chain['nameHash']),
-                ("prescale", 1),
-                ("enabled", 1)
-            ])
-    psFN = getHLTPrescalesSetFileName( flags )
-    with open(psFN, 'w') as outfile:
-        json.dump(pso, outfile, indent = 4)
-        log.info("Generated default HLT prescale set %s", outfile.name)
-
-
 def getTrigConfigFromFlag( flags=None ):
     log = logging.getLogger('TrigConfigSvcCfg')
     if flags is None: # old-style TriggerFlags
diff --git a/Trigger/TriggerCommon/TriggerJobOpts/share/runHLT_standalone.py b/Trigger/TriggerCommon/TriggerJobOpts/share/runHLT_standalone.py
index efb1cee05c4e..dd3fae4a93cf 100644
--- a/Trigger/TriggerCommon/TriggerJobOpts/share/runHLT_standalone.py
+++ b/Trigger/TriggerCommon/TriggerJobOpts/share/runHLT_standalone.py
@@ -496,6 +496,11 @@ if not opt.createHLTMenuExternally:
     # generating the HLT structure requires 
     # the L1Decoder to be defined in the topSequence
     menu.generateMT()
+    # Note this will also create the requested HLTPrescale JSON
+    # - the default file (with all prescales set to 1) is not really needed.
+    # - If no file is provided all chains are either enabled or disabled,
+    #   depending on the property L1Decoder.PrescalingTool.KeepUnknownChains being True or False
+
 
     if opt.endJobAfterGenerate:
         import sys
@@ -513,13 +518,6 @@ from TrigConfigSvc.TrigConfigSvcCfg import getHLTConfigSvc, setupHLTPrescaleCond
 svcMgr += conf2toConfigurable( getHLTConfigSvc() )
 setupHLTPrescaleCondAlg()
 
-if not opt.createHLTMenuExternally:
-    # the generation of the prescale set file from the menu (with all prescales set to 1)
-    # is not really needed. If no file is provided all chains are either enabled or disabled,
-    # depending on the property L1Decoder.PrescalingTool.KeepUnknownChains being True or False
-    from TrigConfigSvc.TrigConfigSvcCfg import createHLTPrescalesFileFromMenu
-    createHLTPrescalesFileFromMenu()
-
 
 
 # ---------------------------------------------------------------
diff --git a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/GenerateMenuMT.py b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/GenerateMenuMT.py
index f5f6bc50aee4..83c9d73ffe24 100755
--- a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/GenerateMenuMT.py
+++ b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/GenerateMenuMT.py
@@ -14,9 +14,8 @@ from TriggerMenuMT.HLTMenuConfig.Menu.TriggerConfigHLT  import TriggerConfigHLT
 from TriggerMenuMT.HLTMenuConfig.Menu.HLTCFConfig import makeHLTTree
 from TriggerMenuMT.HLTMenuConfig.Menu.DictFromChainName import dictFromChainName
 from TriggerMenuMT.HLTMenuConfig.Menu.ChainDictTools import splitInterSignatureChainDict
-from TriggerMenuMT.HLTMenuConfig.Menu.MenuPrescaleConfig import MenuPrescaleConfig
+from TriggerMenuMT.HLTMenuConfig.Menu.MenuPrescaleConfig import MenuPrescaleConfig, applyHLTPrescale
 from TriggerMenuMT.HLTMenuConfig.Menu.ChainMerging import mergeChainDefs
-from TriggerMenuMT.HLTMenuConfig.Menu.MenuUtil import applyHLTPrescale
 
 from AthenaCommon.Logging import logging
 log = logging.getLogger( __name__ )
@@ -373,4 +372,7 @@ class GenerateMenuMT(object):
         from TriggerMenuMT.HLTMenuConfig.Menu.HLTMenuJSON import generateJSON
         generateJSON()
 
+        from TriggerMenuMT.HLTMenuConfig.Menu.HLTPrescaleJSON import generateJSON as generatePrescaleJSON
+        generatePrescaleJSON()
+
         return finalListOfChainConfigs
diff --git a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/HLTPrescaleJSON.py b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/HLTPrescaleJSON.py
new file mode 100644
index 000000000000..b7444519e724
--- /dev/null
+++ b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/HLTPrescaleJSON.py
@@ -0,0 +1,66 @@
+# Copyright (C) 2002-2019 CERN for the benefit of the ATLAS collaboration
+
+import json
+from collections import OrderedDict as odict
+from TrigConfigSvc.TrigConfigSvcCfg import getHLTPrescalesSetFileName
+from AthenaCommon.Logging import logging
+__log = logging.getLogger( __name__ )
+
+
+def __generateJSON( chainDicts, chainConfigs, menuName, fileName ):
+    """ Generates JSON given the ChainProps and sequences
+    """
+    # Prescale dictionary that is used to create the JSON content
+    prescaleDict = odict([ ("filetype", "hltprescale"), ("name", menuName), ("prescales", odict()) ])
+
+    from TriggerMenuMT.HLTMenuConfig.Menu import StreamInfo
+    for chain in chainDicts:
+        # Prepare information for stream list
+        chainStreamTags = []
+        for streamName in chain["stream"]:
+            streamTag = StreamInfo.getStreamTag(streamName)
+            # Stream needs to have been defined in StreamInfo.py otherwise is not added to JSON
+            if streamTag is None:
+                __log.error('Stream %s does not have StreamTags defined excluding from JSON', streamName)
+                continue
+            # Add stream to the chain
+            chainStreamTags.append(streamName)
+
+        # Now have all information to write the chain to the menu dictionary
+        chainName = chain["chainName"]
+        prescaleDict["prescales"][chainName] = odict([
+            ("name", chainName),
+            ("counter", chain["chainCounter"]),
+            ("hash", chain["chainNameHash"]),
+            ("prescale", 1),
+            ("enabled", 1)
+            #("streams", chainStreamTags)
+        ])
+
+        #Prescale testing
+        __log.info( "Chain %s prescale %s", chainName, chain["prescale"] )
+
+    # Prescale dictionary now completed, write to JSON
+    __log.info( "Writing HLT Prescale JSON to %s", fileName )
+    with open( fileName, 'w' ) as fp:
+        json.dump( prescaleDict, fp, indent=4, sort_keys=False )
+
+
+def generateJSON():
+    __log.info("Generating HLT Prescale JSON in the rec-ex-common job")
+    from TriggerJobOpts.TriggerFlags import TriggerFlags
+    from TriggerMenuMT.HLTMenuConfig.Menu.TriggerConfigHLT import TriggerConfigHLT
+
+    return __generateJSON( TriggerConfigHLT.dictsList(),
+                           TriggerConfigHLT.configsList(),
+                           TriggerFlags.triggerMenuSetup(),
+                           getHLTPrescalesSetFileName() )
+
+def generateJSON_newJO( chainDicts, chainConfigs ):
+    __log.info("Generating HLT Prescale JSON in the new JO")
+    from AthenaConfiguration.AllConfigFlags import ConfigFlags
+
+    return __generateJSON( chainDicts,
+                           chainConfigs,
+                           ConfigFlags.Trigger.triggerMenuSetup,
+                           getHLTPrescalesSetFileName( ConfigFlags) )
diff --git a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuPrescaleConfig.py b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuPrescaleConfig.py
index 1ff6323e2b47..15c5da426a9b 100755
--- a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuPrescaleConfig.py
+++ b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuPrescaleConfig.py
@@ -1,7 +1,8 @@
 # Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration
 
 from TriggerJobOpts.TriggerFlags import TriggerFlags
-#from TriggerMenu.menu.MenuUtil import applyHLTPrescale, resetAllPrescales
+#from TriggerMenu.menu.MenuUtil import resetAllPrescales
+from six import iteritems
 
 from AthenaCommon.Logging import logging
 log = logging.getLogger( __name__ )
@@ -156,3 +157,28 @@ def addSliceChainsToPrescales(flags, cosmic_prescales):
     combined.update(cosmic_prescales)
     from copy import deepcopy
     cosmic_prescales = deepcopy(combined)
+
+def applyHLTPrescale(triggerPythonConfig, HLTPrescale, signaturesOverwritten):
+    for item, prescales in iteritems(HLTPrescale):
+        # prescales is a list of 3 integers [HLT_prescale, HLT_pass_through, rerun_prescale]
+        if item not in triggerPythonConfig.dicts().keys():
+            if signaturesOverwritten:
+                log.warning('Attempt to set prescales for nonexisting chain: %s', item)
+                continue
+            else:
+                log.error('Attempt to set prescales for nonexisting chain: %s', item)
+                continue
+        n = len(prescales)
+        hltchain = triggerPythonConfig.dicts()[item]
+        if n > 0:
+            hltchain['prescale'] = str(prescales[0])
+        log.info('Applied HLTPS to the item '+item+': PS'+ hltchain['prescale'])
+        #
+        #passthrough and rerun still in the HLTPrescale object but not needed currently
+        #
+        #if n > 1:
+        #    hltchain['pass_through'] = str(prescales[1])
+        #if n > 2:
+        #    hltchain['rerun_prescale'] = str(prescales[2])
+        #
+        #log.info('Applied HLTPS to the item '+item+': PS'+ hltchain.prescale+" PT"+hltchain.pass_through+" RerunPS"+hltchain.rerun_prescale)
diff --git a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuUtil.py b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuUtil.py
index 9474a783b1bf..694651cf487b 100755
--- a/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuUtil.py
+++ b/Trigger/TriggerCommon/TriggerMenuMT/python/HLTMenuConfig/Menu/MenuUtil.py
@@ -2,61 +2,37 @@
 
 from TriggerJobOpts.TriggerFlags import TriggerFlags
 from AthenaCommon.Logging import logging
-from six import iteritems
 
 log = logging.getLogger(__name__)
 
 
-def getStreamTagForRerunChains(triggerPythonConfig, HLTPrescale):
-    list=[]
-    for item, prescales in HLTPrescale.iteritems():
-        # prescales is a list of 3 integers [HLT_prescale, HLT_pass_through, rerun_prescale]
-        if item not in triggerPythonConfig.allChains.keys():
-            log.debug('Signature %s not registered to TriggerPythonConfig', item)
-            continue
-        n = len(prescales)
-        hltchain = None
-        for ch in triggerPythonConfig.allChains[item]:
-            if ch.level == 'HLT': 
-                hltchain = ch
-            if n > 3  and hltchain:
-                if hltchain.prescale != "0":
-                    log.warning("chain %s in rerun mode with special strema tag does not have the correct HLT PS [=0] ",
-                                hltchain.chain_name)
-                if hltchain.rerun_prescale !=  "1":
-                    log.error("chain %s has special stream tag but it's not in rerun mode", hltchain.chain_name)
-                list.append( "%s:%s", hltchain.chain_name, prescales[3] )
-            
-
-    return list
-
-                
-
-
-def applyHLTPrescale(triggerPythonConfig, HLTPrescale, signaturesOverwritten):
-    for item, prescales in iteritems(HLTPrescale):
-        # prescales is a list of 3 integers [HLT_prescale, HLT_pass_through, rerun_prescale]
-        if item not in triggerPythonConfig.dicts().keys():
-            if signaturesOverwritten:
-                log.warning('Attempt to set prescales for nonexisting chain: %s', item)
-                continue
-            else:
-                log.error('Attempt to set prescales for nonexisting chain: %s', item)
-                continue
-        n = len(prescales)
-        hltchain = triggerPythonConfig.dicts()[item]
-        if n > 0:
-            hltchain['prescale'] = str(prescales[0])
-        log.info('Applied HLTPS to the item '+item+': PS'+ hltchain['prescale'])
-        #
-        #passthrough and rerun still in the HLTPrescale object but not needed currently
-        #
-        #if n > 1:
-        #    hltchain['pass_through'] = str(prescales[1])
-        #if n > 2:
-        #    hltchain['rerun_prescale'] = str(prescales[2])
-        #
-        #log.info('Applied HLTPS to the item '+item+': PS'+ hltchain.prescale+" PT"+hltchain.pass_through+" RerunPS"+hltchain.rerun_prescale)
+# Commenting as not currently used (likely can be removed)
+#
+# If needed the code should be updated to TMMT, for reference see:
+# (TMMT) MenuPrescaleConfig.applyHLTPrescale verses (TM) MenuUtil.applyHLTPrescale
+#
+#def getStreamTagForRerunChains(triggerPythonConfig, HLTPrescale):
+#    list=[]
+#    for item, prescales in HLTPrescale.iteritems():
+#        # prescales is a list of 3 integers [HLT_prescale, HLT_pass_through, rerun_prescale]
+#        if item not in triggerPythonConfig.allChains.keys():
+#            log.debug('Signature %s not registered to TriggerPythonConfig', item)
+#            continue
+#        n = len(prescales)
+#        hltchain = None
+#        for ch in triggerPythonConfig.allChains[item]:
+#            if ch.level == 'HLT':
+#                hltchain = ch
+#            if n > 3  and hltchain:
+#                if hltchain.prescale != "0":
+#                    log.warning("chain %s in rerun mode with special strema tag does not have the correct HLT PS [=0] ",
+#                                hltchain.chain_name)
+#                if hltchain.rerun_prescale !=  "1":
+#                    log.error("chain %s has special stream tag but it's not in rerun mode", hltchain.chain_name)
+#                list.append( "%s:%s", hltchain.chain_name, prescales[3] )
+#
+#
+#    return list
 
 
 
@@ -157,18 +133,23 @@ def checkStreamConsistency(triggerPythonConfig):
                 already_used_robs[rob_id]=stream
                 
 
-def resetAllPrescales(triggerPythonConfig):
-    for sig in triggerPythonConfig.allChains.values():
-        for chain in sig:
-            if float(chain.prescale) > 0.:
-                chain.prescale = '1'
-            if float(chain.pass_through) > 0.:
-                chain.pass_through = '1'
-            if float(chain.rerun_prescale) > 0.:   
-                chain.rerun_prescale = '1'
-    for item in triggerPythonConfig.allItems.values():
-        if float(item.prescale) > 0.:
-            item.prescale = '1'
+# Commenting as not currently used (likely can be removed)
+#
+# If needed the code should be updated to TMMT, for reference see:
+# (TMMT) MenuPrescaleConfig.applyHLTPrescale verses (TM) MenuUtil.applyHLTPrescale
+#
+#def resetAllPrescales(triggerPythonConfig):
+#    for sig in triggerPythonConfig.allChains.values():
+#        for chain in sig:
+#            if float(chain.prescale) > 0.:
+#                chain.prescale = '1'
+#            if float(chain.pass_through) > 0.:
+#                chain.pass_through = '1'
+#            if float(chain.rerun_prescale) > 0.:
+#                chain.rerun_prescale = '1'
+#    for item in triggerPythonConfig.allItems.values():
+#        if float(item.prescale) > 0.:
+#            item.prescale = '1'
         
 def allSignatures():
     sigs = []
-- 
GitLab