diff --git a/.flake8 b/.flake8
new file mode 100644
index 0000000000000000000000000000000000000000..f09edf220fceaa55a412c0d38a93e91e3bd4ddf1
--- /dev/null
+++ b/.flake8
@@ -0,0 +1,9 @@
+[flake8]
+extend-ignore = E501
+exclude =
+    Phys/CommonParticlesArchive/*
+    Phys/StrippingSettings/*
+    Phys/StrippingArchive/*
+    Phys/Stripping/*
+    Phys/StrippingSelections/*
+    Phys/StrippingDoc/python/StrippingDoc/stripping*
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 57454c2f4aadb7ed71db4702e68783f9521e73ea..80ec5edebac0be911ac4f5326a9e2cf57b62a6db 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -1,5 +1,5 @@
-###############################################################################
-## (c) Copyright 2019 CERN for the benefit of the LHCb Collaboration           #
+################################################################################
+## (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 ##                                                                             #
 ## This software is distributed under the terms of the GNU General Public      #
 ## Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -8,8 +8,263 @@
 ## granted to it by virtue of its status as an Intergovernmental Organization  #
 ## or submit itself to any jurisdiction.                                       #
 ################################################################################
+stages:
+    - Lint
+    - WGtest
+
+# Rules are defined for the different jobs so that the individual working group tests only run on the respective WG dev branches (contain the name of the WG)
+
 check-copyright:
   image: gitlab-registry.cern.ch/ci-tools/ci-worker:cc7
+  stage: Lint
   script:
     - curl -o check_copyright.py "https://gitlab.cern.ch/lhcb-core/LbDevTools/raw/master/LbDevTools/SourceTools.py?inline=false"
     - python check_copyright.py origin/2018-patches
+  rules:
+    - if: $CI_COMMIT_REF_NAME =~ /patch/
+default:
+  image: gitlab-registry.cern.ch/lhcb-core/lbdocker/centos7-build:latest
+
+python-linting:
+  stage: Lint
+  tags:
+    - cvmfs
+  script:
+    - . /cvmfs/lhcb.cern.ch/lib/LbEnv.sh
+    # TODO: get rid of ignores and run on full directory !
+    - flake8 --extend-ignore E501 $(find Phys/StrippingConf/python/StrippingConf/ -name '*.py')
+
+.setup_script_2016:
+    before_script:
+        - source /cvmfs/lhcb.cern.ch/lib/LbEnv
+        - git config --global user.email "noreply@cern.ch"
+        - git config --global user.name "gitlabCI"
+        - eval "$(apd-login)"
+        - lb-dev DaVinci/v44r11p4
+        - cd DaVinciDev_v44r11p4
+        - mkdir Phys
+        - cp -rp $PWD/../Phys/StrippingSelections Phys/StrippingSelections
+        - cp -rp $PWD/../Phys/StrippingSettings Phys/StrippingSettings
+        - make configure && make
+        - lb-conda default python Phys/StrippingSelections/tests/CI/DataAuthentication.py
+
+.setup_script_2017:
+    before_script:
+        - source /cvmfs/lhcb.cern.ch/lib/LbEnv
+        - git config --global user.email "noreply@cern.ch"
+        - git config --global user.name "gitlabCI"
+        - eval "$(apd-login)"
+        - lb-dev DaVinci/v44r11p4
+        - cd DaVinciDev_v44r11p4
+        - mkdir Phys
+        - cp -rp $PWD/../Phys/StrippingSelections Phys/StrippingSelections
+        - cp -rp $PWD/../Phys/StrippingSettings Phys/StrippingSettings
+        - make configure && make
+        - lb-conda default python Phys/StrippingSelections/tests/CI/DataAuthentication.py
+
+.setup_script_2018:
+    before_script:
+        - source /cvmfs/lhcb.cern.ch/lib/LbEnv
+        - git config --global user.email "noreply@cern.ch"
+        - git config --global user.name "gitlabCI"
+        - eval "$(apd-login)"
+        - lb-dev DaVinci/v44r11p4
+        - cd DaVinciDev_v44r11p4
+        - mkdir Phys
+        - cp -rp $PWD/../Phys/StrippingSelections Phys/StrippingSelections
+        - cp -rp $PWD/../Phys/StrippingSettings Phys/StrippingSettings
+        - make configure && make
+        - lb-conda default python Phys/StrippingSelections/tests/CI/DataAuthentication.py
+
+TestWGLines_2016_BandQ:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 BandQ | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BandQ/
+
+TestWGLines_2017_BandQ:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 BandQ | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BandQ/
+
+TestWGLines_2018_BandQ:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 BandQ | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BandQ/
+
+TestWGLines_2016_BnoC:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 BnoC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BnoC/
+
+TestWGLines_2017_BnoC:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 BnoC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BnoC/
+
+TestWGLines_2018_BnoC:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 BnoC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /BnoC/
+
+TestWGLines_2016_B2CC:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 B2CC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2CC/
+
+TestWGLines_2017_B2CC:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 B2CC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2CC/
+
+TestWGLines_2018_B2CC:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 B2CC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2CC/
+
+TestWGLines_2016_B2OC:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 B2OC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2OC/
+
+TestWGLines_2017_B2OC:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 B2OC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2OC/
+
+TestWGLines_2018_B2OC:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 B2OC | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /B2OC/
+
+TestWGLines_2016_Charm:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 Charm | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Charm/
+
+TestWGLines_2017_Charm:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 Charm | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Charm/
+
+TestWGLines_2018_Charm:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 Charm | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Charm/
+
+TestWGLines_2016_QEE:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 QEE | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /QEE/
+
+TestWGLines_2017_QEE:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 QEE | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /QEE/
+
+TestWGLines_2018_QEE:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 QEE | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /QEE/
+
+TestWGLines_2016_Semileptonic:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 Semileptonic | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Semileptonic/
+
+TestWGLines_2017_Semileptonic:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 Semileptonic | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Semileptonic/
+
+TestWGLines_2018_Semileptonic:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 Semileptonic | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /Semileptonic/
+
+TestWGLines_2016_IFT:
+    stage: WGtest
+    extends: .setup_script_2016
+    script:
+    - echo -n 2016 IFT | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /IFT/
+
+TestWGLines_2017_IFT:
+    stage: WGtest
+    extends: .setup_script_2017
+    script:
+    - echo -n 2017 IFT | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /IFT/
+
+TestWGLines_2018_IFT:
+    stage: WGtest
+    extends: .setup_script_2018
+    script:
+    - echo -n 2018 IFT | ./run gaudirun.py -T Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+    rules:
+        - if: $CI_COMMIT_REF_NAME =~ /IFT/
+
diff --git a/Phys/StandardParticles/python/StandardParticles/__init__.py b/Phys/StandardParticles/python/StandardParticles/__init__.py
index 1f277f5b3cc52a6d240205ca175e5a92504f12f3..0f7b8435a4256befd670fc70640e266bcfd869a6 100644
--- a/Phys/StandardParticles/python/StandardParticles/__init__.py
+++ b/Phys/StandardParticles/python/StandardParticles/__init__.py
@@ -12,10 +12,12 @@
 Module containing AutomaticDatas corresponding to common particles
 from CommonParticles.StandardBasic.
 """
+from __future__ import print_function
+
+__author__ = 'Juan Palacios palacios@physik.uzh.ch'
 
 from PhysSelPython.Wrappers import AutomaticData
 from CommonParticles import StandardBasic, StandardIntermediate
-__author__ = 'Juan Palacios palacios@physik.uzh.ch'
 
 from sys import modules
 _this = modules[__name__]
@@ -59,6 +61,6 @@ addParticleModule(StandardIntermediate)
 getStdPartAlgorithms()
 
 if __name__ == '__main__':
-    print '\nStandardParticles: available Selections:\n'
+    print('\nStandardParticles: available Selections:\n')
     for sel in selections:
-        print '\t', sel.name()
+        print('\t', sel.name())
diff --git a/Phys/StrippingArchive/python/StrippingArchive/__init__.py b/Phys/StrippingArchive/python/StrippingArchive/__init__.py
index 50c9d82079427ead4ed09aa6226cc2379f95c1c8..484ef97322cb8e38f78bfab0313ce4f48393ab27 100644
--- a/Phys/StrippingArchive/python/StrippingArchive/__init__.py
+++ b/Phys/StrippingArchive/python/StrippingArchive/__init__.py
@@ -35,7 +35,19 @@ _known_strippings = ['Stripping24r2',
 
 # List of obsolete strippings (ie, which don't run with the current stack).
 # This only affects which Strippings are tested in the nightlies.
-_relinfo_obsolete_strippings = []
+_relinfo_obsolete_strippings = [
+                    'Stripping24r2',
+                     'Stripping25',
+                     'Stripping27',
+                     'Stripping28r2',
+                     'Stripping30r2',
+                     'Stripping30r3',
+                     'Stripping31r1',
+                     'Stripping31r2',
+                     'Stripping33r2',
+                     'Stripping34',
+                     'Stripping34r0p1',
+]
 
 
 #give a dictionary of strippings which use the same line builders
diff --git a/Phys/StrippingArchive/tests/refs/instantiate-all-strip.ref b/Phys/StrippingArchive/tests/refs/instantiate-all-strip.ref
index 646200ee0dbf5e9cd0cc60523a4ec13123c22fab..25e6e078eb618c3f4c4272ea63f3b69e13de8bfa 100644
--- a/Phys/StrippingArchive/tests/refs/instantiate-all-strip.ref
+++ b/Phys/StrippingArchive/tests/refs/instantiate-all-strip.ref
@@ -1,10 +1,8 @@
 RelInfo-obsolete strippings are
-[]
+['Stripping24r2', 'Stripping25', 'Stripping27', 'Stripping28r2', 'Stripping30r2', 'Stripping30r3', 'Stripping31r1', 'Stripping31r2', 'Stripping33r2', 'Stripping34', 'Stripping34r0p1']
 Trying to import module StrippingArchive.Stripping24r2
 Trying to import module StrippingArchive.Stripping25
-Hello Im S25 and Im now using PatLongLivedTracking instead of PatDownStream
 Trying to import module StrippingArchive.Stripping27
-I am now using PatLongLivedTracking instead of PatDownStream
 Trying to import module StrippingArchive.Stripping28r2
 Trying to import module StrippingArchive.Stripping28r2p1
 Trying to import module StrippingArchive.Stripping30r2
@@ -18,139 +16,7 @@ Trying to import module StrippingArchive.Stripping34r0p2
 Trying to import module StrippingArchive.Stripping35r2
 Trying to import module StrippingArchive.Stripping35r3
 looping over:
-['Stripping24r2', 'Stripping25', 'Stripping27', 'Stripping28r2', 'Stripping28r2p1', 'Stripping30r2', 'Stripping30r3', 'Stripping31r1', 'Stripping31r2', 'Stripping33r2', 'Stripping34', 'Stripping34r0p1', 'Stripping34r0p2', 'Stripping35r2', 'Stripping35r3']
-=============================================
-Stripping24r2 :
-=============================================
-Requested Stripping24r2
-Trying to import module StrippingArchive.Stripping24r2
-In Z02MuMu builder
-B0 -> mu+ mu- mu+ mu- K*(892)0
-B0 -> e+ e- e+ e- K*(892)0
-B0 -> K+ K- K+ K- K*(892)0
-B0  -> pi+ pi- pi+ pi- K*(892)0
-B0 -> p+ p~- p+ p~- K*(892)0
-B+ -> mu+ mu- mu+ mu- K+
-B+ -> e+ e- e+ e- K+
-B+ -> K+ K- K+ K- K+
-B+  -> pi+ pi- pi+ pi- K+
-B+ -> p+ p~- p+ p~- K+
-B_s0 -> e+ e- e+ e-
-B_s0 -> K+ K- K+ K-
-B_s0  -> pi+ pi- pi+ pi-
-B_s0 -> p+ p~- p+ p~-
-# WARNING: lineButo5h_5pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_K4pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_pp3pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_ppKpipi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-Creating Bhadron stream with 1106 lines
-# WARNING: Line StrippingB2XEtaB2etaGGKSLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKSDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKstarLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2pKetaGGLine has prescale <= 0, it will be removed from stream Bhadron
-Creating Semileptonic stream with 153 lines
-Creating BhadronCompleteEvent stream with 153 lines
-Creating Leptonic stream with 367 lines
-# WARNING: Line StrippingTau23MuDs23PiLine has prescale <= 0, it will be removed from stream Leptonic
-Creating Dimuon stream with 96 lines
-Creating Charm stream with 306 lines
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMB has prescale <= 0, it will be removed from stream Charm
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMBTrEff has prescale <= 0, it will be removed from stream Charm
-Creating EW stream with 127 lines
-# WARNING: Line StrippingExoticaPrmptDiMuonHighMassLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiELine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaRHNuLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplPhiPhiLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaQuadMuonNoIPLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonNoPointLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaLFVPrmptLine has prescale <= 0, it will be removed from stream EW
-Creating CharmCompleteEvent stream with 67 lines
-=============================================
-Stripping25 :
-=============================================
-Requested Stripping25
-Trying to import module StrippingArchive.Stripping25
-Hello Im S25 and Im now using PatLongLivedTracking instead of PatDownStream
-inside MiniBias {'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': "(HLT_PASS('Hlt2PassThroughDecision'))", 'MicroBiasPrescale': 1.0, 'NoBiasPrescale': 0.2, 'MicroBiasLowMultPrescale': 1.0, 'MicroBiasLowMultHlt1Filter': "(HLT_PASS('Hlt1MBMicroBiasLowMultVeloDecision'))", 'NoBiasPostscale': 1.0, 'MicroBiasHlt1Filter': "(HLT_PASS('Hlt1MBMicroBiasVeloDecision'))", 'NoBiasHlt2Filter': "(HLT_PASS('Hlt2PassThroughDecision'))", 'CheckPV': False, 'NoBiasHlt1Filter': "(HLT_PASS('Hlt1MBNoBiasLeadingCrossingDecision'))", 'MicroBiasHlt2Filter': "(HLT_PASS('Hlt2PassThroughDecision'))|(HLT_PASS('Hlt2SMOGPhysicsDecision'))"}
-Creating ALL stream with 40 lines
-Creating MiniBias stream with 3 lines
-=============================================
-Stripping27 :
-=============================================
-Requested Stripping27
-Trying to import module StrippingArchive.Stripping27
-I am now using PatLongLivedTracking instead of PatDownStream
-inside MiniBias {'odin': ['Beam1'], 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'NoBiasPrescale': 1.0, 'MicroBiasLowMultPrescale': 0.001, 'MicroBiasLowMultHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'NoBiasPostscale': 1.0, 'MicroBiasHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasVeloDecision'))", 'NoBiasHlt2Filter': None, 'CheckPV': False, 'NoBiasHlt1Filter': "(HLT_PASS('Hlt1BENoBiasDecision'))", 'MicroBiasHlt2Filter': None}
-inside SingleElectron {'odin': ['Beam1'], 'MaxNSpd': 50, 'Postscale': 1.0, 'MaxP': 25000.0, 'MaxNDown': 4, 'Hlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'MaxEta': 7.0, 'MaxNBack': 2, 'Hlt2Filter': None, 'Prescale': 1.0, 'MaxNUp': 4, 'MaxPt': 180.0, 'MaxNvelo': 5, 'MinEta': 3.5, 'MaxNTT': 3}
-Creating IFT stream with 40 lines
-Creating MiniBias stream with 4 lines
-=============================================
-Stripping28r2 :
-=============================================
-Requested Stripping28r2
-Trying to import module StrippingArchive.Stripping28r2
-In Z02MuMu builder
-B0 -> mu+ mu- mu+ mu- K*(892)0
-B0 -> e+ e- e+ e- K*(892)0
-B0 -> K+ K- K+ K- K*(892)0
-B0  -> pi+ pi- pi+ pi- K*(892)0
-B0 -> p+ p~- p+ p~- K*(892)0
-B+ -> mu+ mu- mu+ mu- K+
-B+ -> e+ e- e+ e- K+
-B+ -> K+ K- K+ K- K+
-B+  -> pi+ pi- pi+ pi- K+
-B+ -> p+ p~- p+ p~- K+
-B_s0 -> e+ e- e+ e-
-B_s0 -> K+ K- K+ K-
-B_s0  -> pi+ pi- pi+ pi-
-B_s0 -> p+ p~- p+ p~-
-# WARNING: lineButo5h_5pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_K4pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_pp3pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_ppKpipi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-In Z02MuMuCalibration builder
-Creating Bhadron stream with 1109 lines
-# WARNING: Line StrippingB2XEtaB2etaGGKSLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKSDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKstarLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2pKetaGGLine has prescale <= 0, it will be removed from stream Bhadron
-Creating Semileptonic stream with 153 lines
-Creating BhadronCompleteEvent stream with 150 lines
-Creating Leptonic stream with 367 lines
-# WARNING: Line StrippingTau23MuDs23PiLine has prescale <= 0, it will be removed from stream Leptonic
-Creating Dimuon stream with 96 lines
-Creating Charm stream with 306 lines
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMB has prescale <= 0, it will be removed from stream Charm
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMBTrEff has prescale <= 0, it will be removed from stream Charm
-Creating EW stream with 127 lines
-# WARNING: Line StrippingExoticaPrmptDiMuonHighMassLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiELine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaRHNuLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplPhiPhiLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaQuadMuonNoIPLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonNoPointLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaLFVPrmptLine has prescale <= 0, it will be removed from stream EW
-Creating CharmCompleteEvent stream with 67 lines
-Creating LowMult stream with 37 lines
-# WARNING: Line StrippingL0DiHadronLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingL0DiEMLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingL0PhotonLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingL0DiMuonLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingL0MuonLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingL0ElectronLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultLMR2HH_mediumPSLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultLMR2HHHH_mediumPSLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultLMR2HH_heavyPSLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultLMR2HHHH_heavyPSLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultTechnicalLine has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultTMP1Line has prescale <= 0, it will be removed from stream LowMult
-# WARNING: Line StrippingLowMultTMP2Line has prescale <= 0, it will be removed from stream LowMult
+['Stripping28r2p1', 'Stripping34r0p2', 'Stripping35r2', 'Stripping35r3']
 =============================================
 Stripping28r2p1 :
 =============================================
@@ -214,141 +80,6 @@ Creating Dimuon stream with 85 lines
 # WARNING: Line StrippingB2MuMuMuMuD24MuLine has prescale <= 0, it will be removed from stream Dimuon
 # WARNING: Line StrippingB2MuMuMuMuB2DetachedDimuonsLine has prescale <= 0, it will be removed from stream Dimuon
 =============================================
-Stripping30r2 :
-=============================================
-Requested Stripping30r2
-Trying to import module StrippingArchive.Stripping30r2
-inside GammaHadron {'NoConvHCAL2ECAL': 0.05, 'gammaConvIPCHI': 0, 'DDProbNNe': 0.0, 'NoBiasPostscale': 1.0, 'gammaConvPT1': 500, 'ConvGhostLL': 0.2, 'gammaCL': 0.9, 'ConvGhostDD': 0.25, 'MicroBiasHlt2Filter': None, 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'NoBiasPrescale': 1.0, 'MicroBiasLowMultPrescale': 1.0, 'NoBiasHlt1Filter': None, 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'gammaPT2': 1500, 'gammaPT1': 1000, 'gammaConvPT2': 1000, 'gammaConvMDD': 200, 'LLProbNNe': 0.0, 'MicroBiasLowMultHlt1Filter': None, 'MicroBiasHlt1Filter': None, 'NoBiasHlt2Filter': None, 'CheckPV': True, 'gammaConvMLL': 60}
-['[D0 -> K- pi+]cc']
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (PT > 5000.0) & (PT < 100000.0)
-Creating IFT stream with 48 lines
-=============================================
-Stripping30r3 :
-=============================================
-Requested Stripping30r3
-Trying to import module StrippingArchive.Stripping30r3
-inside GammaHadron {'NoConvHCAL2ECAL': 0.05, 'gammaConvIPCHI': 0, 'DDProbNNe': 0.0, 'NoBiasPostscale': 1.0, 'gammaConvPT1': 500, 'ConvGhostLL': 0.2, 'gammaCL': 0.9, 'ConvGhostDD': 0.25, 'MicroBiasHlt2Filter': None, 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'NoBiasPrescale': 1.0, 'MicroBiasLowMultPrescale': 1.0, 'NoBiasHlt1Filter': None, 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'gammaPT2': 1500, 'gammaPT1': 1000, 'gammaConvPT2': 1000, 'gammaConvMDD': 200, 'LLProbNNe': 0.0, 'MicroBiasLowMultHlt1Filter': None, 'MicroBiasHlt1Filter': None, 'NoBiasHlt2Filter': None, 'CheckPV': True, 'gammaConvMLL': 60}
-['[D0 -> K- pi+]cc']
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (PT > 5000.0) & (PT < 100000.0)
-Creating IFT stream with 48 lines
-=============================================
-Stripping31r1 :
-=============================================
-Requested Stripping31r1
-Trying to import module StrippingArchive.Stripping31r1
-['[D0 -> K- pi+]cc']
-inside MiniBias {'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'MicroBiasPostscale': 1.0, 'GEC_HighMult': '( recSummaryTrack(LHCb.RecSummary.nVeloTracks, TrVELO) >= 10000) ', 'MicroBiasLowMultPrescale': 1.0, 'MicroBiasLowMultHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'MicroBiasHlt1Filter': "(HLT_PASS('Hlt1BBMicroBiasVeloDecision'))|(HLT_PASS('Hlt1BEMicroBiasVeloDecision'))", 'GEC_LowMult': '( recSummaryTrack(LHCb.RecSummary.nVeloTracks, TrVELO) > 1) ', 'CheckPV': False, 'MicroBiasHlt2Filter': None, 'odinSMOG': ['Beam1', 'Beam2']}
-inside SingleElectron {'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'MaxNSpd': 50, 'Postscale': 1.0, 'MaxP': 25000.0, 'MaxNDown': 4, 'Hlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'MaxEta': 7.0, 'MaxNBack': 2, 'Hlt2Filter': None, 'Prescale': 1.0, 'MaxNUp': 4, 'MaxPt': 180.0, 'MaxNvelo': 5, 'MinEta': 3.5, 'MaxNTT': 3}
-Creating IFT stream with 44 lines
-=============================================
-Stripping31r2 :
-=============================================
-Requested Stripping31r2
-Trying to import module StrippingArchive.Stripping31r2
-inside GammaHadron {'gammaConvIPCHI': 0, 'DDProbNNe': 0.3, 'NoBiasPostscale': 1.0, 'ConvGhostLL': 0.3, 'gammaCL': 0.9, 'ConvGhostDD': 0.3, 'MicroBiasHlt2Filter': None, 'gammaConvPT': 1500, 'NoBiasPrescale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPrescale': 1.0, 'NoBiasHlt1Filter': None, 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'gammaPT2': 5000, 'gammaPT1': 1500, 'LLProbNNe': 0.5, 'gammaConvMDD': 60, 'NoConvHCAL2ECAL': 0.05, 'MicroBiasLowMultHlt1Filter': None, 'MicroBiasHlt1Filter': None, 'NoBiasHlt2Filter': None, 'CheckPV': True}
-['[D0 -> K- pi+]cc']
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (BPVDIRA > 1 - 0.03*PT/P) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (BPVDIRA > 1 - 0.03*PT/P) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (BPVDIRA > 1 - 0.03*PT/P) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 200.0) & (BPVDIRA > 1 - 0.03*PT/P) & (PT > 5000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 5000.0) & (PT < 10000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 5000.0) & (PT < 10000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 5000.0) & (PT < 10000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 5000.0) & (PT < 10000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 10000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 10000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 10000.0) & (PT < 100000.0)
-(BPVVDZ > 0) & (BPVIPCHI2() < 1000.0) & (BPVDIRA > 1 - 1.0*PT/P) & (PT > 10000.0) & (PT < 100000.0)
-inside MiniBias {'BEMicroBiasHlt2Filter': None, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'MicroBiasPostscale': 0.2, 'GEC_HighMult': "( recSummaryTrack(LHCb.RecSummary.nVeloClusters, 'Raw/Velo/Clusters') >= 20000) ", 'MicroBiasLowMultPrescale': 1.0, 'MicroBiasLowMultHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'BEMicroBiasPostscale': 1.0, 'MicroBiasHighMultPrescale': 1.0, 'BEMicroBiasHlt1Filter': None, 'GEC_LowMult': "( recSummaryTrack(LHCb.RecSummary.nVeloTracks, TrVELO) > 1) & ( recSummary(LHCb.RecSummary.nVeloClusters, 'Raw/Velo/Clusters') < 20000)", 'MicroBiasHlt2Filter': None, 'MicroBiasHighMultPostscale': 0.05, 'MicroBiasHlt1Filter': "(HLT_PASS('Hlt1BBMicroBiasVeloDecision')) | (HLT_PASS('Hlt1BBHighMultDecision')) ", 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'BEMicroBiasPrescale': 1.0, 'CheckPV': False}
-Creating IFT stream with 62 lines
-=============================================
-Stripping33r2 :
-=============================================
-Requested Stripping33r2
-Trying to import module StrippingArchive.Stripping33r2
-inside GammaHadron {'gammaConvIPCHI': 0, 'DDProbNNe': 0.0, 'NoBiasPostscale': 1.0, 'ConvGhostLL': 0.3, 'gammaCL': 0.9, 'ConvGhostDD': 0.3, 'MicroBiasHlt2Filter': None, 'gammaConvPT': 1500, 'NoBiasPrescale': 1.0, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'MicroBiasPrescale': 1.0, 'MicroBiasPostscale': 1.0, 'MicroBiasLowMultPrescale': 1.0, 'NoBiasHlt1Filter': None, 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'gammaPT2': 5000, 'gammaPT1': 1500, 'LLProbNNe': 0.0, 'gammaConvMDD': 60, 'NoConvHCAL2ECAL': 0.05, 'MicroBiasLowMultHlt1Filter': None, 'MicroBiasHlt1Filter': None, 'NoBiasHlt2Filter': None, 'CheckPV': True}
-['[D0 -> K- pi+]cc']
-inside MiniBias {'MBNoBiasPostscale': 1.0, 'MBNoBiasPrescale': 1.0, 'MBNoBiasHlt2Filter': None, 'MicroBiasLowMultPostscale': 1.0, 'MicroBiasLowMultHlt2Filter': None, 'GEC_LowMult': '( recSummaryTrack(LHCb.RecSummary.nVeloTracks, TrVELO) > 1)  ', 'MicroBiasPostscale': 1.0, 'GEC_LowMultBackwardCut': '( recSummaryTrack(LHCb.RecSummary.nVeloTracks, TrVELO) > 1) & ( recSummaryTrack(LHCb.RecSummary.nBackTracks, TrBACKWARD) < 10) ', 'MicroBiasLowMultPrescale': 0.01, 'MicroBiasLowMultHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision'))", 'MicroBiasHlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasVeloDecision'))", 'MicroBiasNoBackwardCutPostscale': 0.5, 'MicroBiasPrescale': 1.0, 'CheckPV': False, 'MBNoBiasHlt1Filter': "(HLT_PASS('Hlt1BENoBiasDecision'))", 'MicroBiasHlt2Filter': None, 'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing']}
-inside SingleElectron {'odin': ['NoBeam', 'Beam1', 'Beam2', 'BeamCrossing'], 'MaxNSpd': 50, 'Postscale': 1.0, 'MaxP': 25000.0, 'MaxNDown': 4, 'Hlt1Filter': "(HLT_PASS('Hlt1BEMicroBiasLowMultVeloDecision') ) | (HLT_PASS('Hlt1BEMicroBiasLowMultVeloNoBiasDecision') )", 'MaxEta': 7.0, 'MaxNBack': 2, 'Hlt2Filter': None, 'Prescale': 1.0, 'MaxNUp': 4, 'MaxPt': 180.0, 'MaxNvelo': 5, 'MinEta': 3.5, 'MaxNTT': 3}
-Creating IFT stream with 45 lines
-# WARNING: Line StrippingK0SDDLineVznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingPhiLLLineVznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingLam0LLLine_HiPVznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingLam0DDLineVznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingLam0LLIsMUONLine1VznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingLam0LLIsMUONLine2VznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-# WARNING: Line StrippingLam0DDIsMUONLineVznoPID_ForIFT has prescale <= 0, it will be removed from stream IFT
-=============================================
-Stripping34 :
-=============================================
-Requested Stripping34
-Trying to import module StrippingArchive.Stripping34
-# WARNING: lineButo5h_5pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_K4pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_pp3pi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-# WARNING: lineButo5h_ppKpipi_exclLine uses plain Gaudi configurable Buto5hGlobalEVventCutFilter. Consider using Selection instead!
-Creating Bhadron stream with 1044 lines
-# WARNING: Line StrippingB2XEtaB2etaGGKSLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKSDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLLLLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2etaGGLDDLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaB2etaGGKstarLine has prescale <= 0, it will be removed from stream Bhadron
-# WARNING: Line StrippingB2XEtaLb2pKetaGGLine has prescale <= 0, it will be removed from stream Bhadron
-Creating Semileptonic stream with 79 lines
-Creating BhadronCompleteEvent stream with 96 lines
-Creating Leptonic stream with 253 lines
-# WARNING: Line StrippingTau23MuDs23PiLine has prescale <= 0, it will be removed from stream Leptonic
-Creating Dimuon stream with 80 lines
-Creating Charm stream with 255 lines
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMB has prescale <= 0, it will be removed from stream Charm
-# WARNING: Line StrippingDstarD02xxDst2PiD02Kpi_untagged_BoxMBTrEff has prescale <= 0, it will be removed from stream Charm
-Creating EW stream with 98 lines
-# WARNING: Line StrippingExoticaPrmptDiMuonHighMassLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiELine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaRHNuLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplPhiPhiLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaQuadMuonNoIPLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaDisplDiMuonNoPointLine has prescale <= 0, it will be removed from stream EW
-# WARNING: Line StrippingHltQEEExoticaLFVPrmptLine has prescale <= 0, it will be removed from stream EW
-Creating CharmCompleteEvent stream with 53 lines
-=============================================
-Stripping34r0p1 :
-=============================================
-Requested Stripping34r0p1
-Trying to import module StrippingArchive.Stripping34r0p1
-B0 -> mu+ mu- mu+ mu- K*(892)0
-B0 -> e+ e- e+ e- K*(892)0
-B0 -> K+ K- K+ K- K*(892)0
-B0  -> pi+ pi- pi+ pi- K*(892)0
-B0 -> p+ p~- p+ p~- K*(892)0
-B+ -> mu+ mu- mu+ mu- K+
-B+ -> e+ e- e+ e- K+
-B+ -> K+ K- K+ K- K+
-B+  -> pi+ pi- pi+ pi- K+
-B+ -> p+ p~- p+ p~- K+
-B_s0 -> e+ e- e+ e-
-B_s0 -> K+ K- K+ K-
-B_s0  -> pi+ pi- pi+ pi-
-B_s0 -> p+ p~- p+ p~-
-Creating Bhadron stream with 407 lines
-Creating Semileptonic stream with 116 lines
-Creating BhadronCompleteEvent stream with 71 lines
-Creating Leptonic stream with 241 lines
-# WARNING: Line StrippingLFVExoticaPromptLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingLFVExoticaSameSignPromptLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingLFVExoticaDetachedLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingLFVExoticaSameSignDetachedLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingLFVExoticaEMuXDetachedLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingLFVExoticaEMuXSameSignDetachedLine has prescale <= 0, it will be removed from stream Leptonic
-# WARNING: Line StrippingTau23MuDs23PiLine has prescale <= 0, it will be removed from stream Leptonic
-Creating Charm stream with 83 lines
-Creating EW stream with 30 lines
-Creating Dimuon stream with 42 lines
-Creating CharmCompleteEvent stream with 13 lines
-=============================================
 Stripping34r0p2 :
 =============================================
 Requested Stripping34r0p2
diff --git a/Phys/StrippingConf/python/StrippingConf/Configuration.py b/Phys/StrippingConf/python/StrippingConf/Configuration.py
old mode 100755
new mode 100644
index 479a36ebc3c052f882e5335fd6e71662b0a97e95..5e535cf89259f6b827913c8fe868a0a7eaabd255
--- a/Phys/StrippingConf/python/StrippingConf/Configuration.py
+++ b/Phys/StrippingConf/python/StrippingConf/Configuration.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -9,44 +9,45 @@
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
 """
-High level configuration tools for StrippingConf, to be used with Moore and DaVinci
+High level configuration tools for StrippingConf,
+to be used with Moore and DaVinci.
 """
 
-__author__  = "Anton Poluektov <A.O.Poluektov@warwick.ac.uk>"
+from __future__ import print_function
+__author__ = "Anton Poluektov <A.O.Poluektov@warwick.ac.uk>"
+from StrippingStream import StrippingStream
+from StrippingLine import StrippingLine  # noqa
+from Configurables import StrippingAlg
+from Gaudi.Configuration import log, WARNING
+from Utils import limitCombinatorics
+
 
 #
-# Configuration of stripping framework. 
+# Configuration of stripping framework.
 #
 
-from os import environ
-from pprint import *
-from Gaudi.Configuration import *
-from Configurables import StrippingAlg
-from StrippingStream import StrippingStream
-from StrippingLine import StrippingLine
-from Utils import limitCombinatorics 
-
-class StrippingConf ( object ) :
-
-    def __init__( self,
-                  name = "",
-                  TESPrefix = 'Strip', 
-                  HDRLocation = 'Phys/DecReports', 
-                  Streams = [],
-                  DSTStreams = [],
-                  MicroDSTStreams = [],
-                  GlobalFlavourTagging = True,
-                  BadEventSelection = None, 
-                  AcceptBadEvents = True,
-                  MaxCandidates = None, 
-                  MaxCombinations = None,
-                  ActiveMDSTStream = False,
-                  Verbose = False ) :
-        
-        log.info("Initialising StrippingConf "+ name)
-        if name == "" :
+
+class StrippingConf (object):
+
+    def __init__(self,
+                 name="",
+                 TESPrefix='Strip',
+                 HDRLocation='Phys/DecReports',
+                 Streams=[],
+                 DSTStreams=[],
+                 MicroDSTStreams=[],
+                 GlobalFlavourTagging=True,
+                 BadEventSelection=None,
+                 AcceptBadEvents=True,
+                 MaxCandidates=None,
+                 MaxCombinations=None,
+                 ActiveMDSTStream=False,
+                 Verbose=False):
+
+        log.info("Initialising StrippingConf " + name)
+        if name == "":
             self._name = "StrippingGlobal"
-        else :
+        else:
             self._name = name
 
         self._verbose = Verbose
@@ -66,32 +67,33 @@ class StrippingConf ( object ) :
         self.MaxCandidates = MaxCandidates
         self.MaxCombinations = MaxCombinations
 
-        ## To be uncommented to limit combinatorics for StandardParticles
-        if self.MaxCandidates != None or self.MaxCombinations != None:
+        # To be uncommented to limit combinatorics for StandardParticles
+        if self.MaxCandidates is not None or self.MaxCombinations is not None:
             self.limitCombForStdParticles()
 
-        ## Forces the limits on all configurables that implement the option...
-        if self.MaxCandidates != None or self.MaxCombinations != None:
+        # Forces the limits on all configurables that implement the option...
+        if self.MaxCandidates is not None or self.MaxCombinations is not None:
             self.checkAllForCombLimit()
 
         self.checkFlavourTagging(Streams)
 
         linesForFT = []
         if self._GlobalFlavourTagging:
-          for stream in Streams:
-            for line in stream.lines:
-              if line._EnableFlavourTagging: 
-                line._EnableFlavourTagging = False
-                linesForFT += [ line ]
+            for stream in Streams:
+                for line in stream.lines:
+                    if line._EnableFlavourTagging:
+                        line._EnableFlavourTagging = False
+                        linesForFT += [line]
 
-        for stream in Streams :
+        for stream in Streams:
             self.appendStream(stream)
 
-	# Global FT locations have to be filled after appending streams, 
-	# because outputLocations of lines can be redefined
+        # Global FT locations have to be filled after appending streams,
+        # because outputLocations of lines can be redefined
         if self._GlobalFlavourTagging:
-          for line in linesForFT:
-            self._taggingLocations += [ line.outputLocation().replace("/Particles","") ]
+            for line in linesForFT:
+                self._taggingLocations += [
+                    line.outputLocation().replace("/Particles", "")]
 
         if self._GlobalFlavourTagging and self._taggingLocations != []:
             self.appendFlavourTagging()
@@ -100,437 +102,497 @@ class StrippingConf ( object ) :
         self.checkUniqueOutputLocations()
 
         if self._verbose:
-          self.checkRawEventRequests()
-          self.checkMDSTFlag()
+            self.checkRawEventRequests()
+            self.checkMDSTFlag()
 
         if self._activeMDST:
-            mdstLines = [ line for line in self.activeLines(self.MicroDSTStreams) if line.MDSTFlag ]
+            mdstLines = [line for line in self.activeLines(
+                self.MicroDSTStreams) if line.MDSTFlag]
             if self._verbose:
-                mdstLinesNames = [ line.name() for line in mdstLines ]
+                mdstLinesNames = [line.name() for line in mdstLines]
                 log.warning("The lines going to FTAG.DST are")
-                print mdstLinesNames
-                log.warning("This was the former MDST.DST which is now a regular DST stream. This implementation should only be present in S28")
-                
+                print(mdstLinesNames)
+                log.warning(
+                    "This was the former MDST.DST which is now a regular DST stream. This implementation should only be present in S28")  # noqa
+
             if mdstLines != []:
-              mdstStream = StrippingStream( "FTAG", Lines = mdstLines )
-              self.appendStream(mdstStream)
+                mdstStream = StrippingStream("FTAG", Lines=mdstLines)
+                self.appendStream(mdstStream)
             else:
-              log.warning("No line has been selected to go to the FTAG stream (former MDST), thus it will be skipped")
- 
+                log.warning(
+                    "No line has been selected to go to the FTAG stream (former MDST), thus it will be skipped")  # noqa
+
         from Gaudi.Configuration import appendPostConfigAction
-        appendPostConfigAction ( defaultToolConfigCheck )
+        appendPostConfigAction(defaultToolConfigCheck)
 
-    def checkRawEventRequests(self) :
-        for stream in self.activeStreams() : stream.checkRawEventRequests()
+    def checkRawEventRequests(self):
+        for stream in self.activeStreams():
+            stream.checkRawEventRequests()
 
-    def checkMDSTFlag(self) :
-        for stream in self.activeStreams() : stream.checkMDSTFlag()
+    def checkMDSTFlag(self):
+        for stream in self.activeStreams():
+            stream.checkMDSTFlag()
 
-    def checkFlavourTagging(self,streams) :
-        for stream in streams : 
-          if stream.name() in self.DSTStreams : stream.checkFlavourTagging(disableFT=True,verbose=self._verbose)
-          elif stream.name() in self.MicroDSTStreams : stream.checkFlavourTagging(disableFT=False,verbose=self._verbose)
-          else : stream.checkFlavourTagging(disableFT=False,verbose=self._verbose)
+    def checkFlavourTagging(self, streams):
+        for stream in streams:
+            if stream.name() in self.DSTStreams:
+                stream.checkFlavourTagging(
+                    disableFT=True, verbose=self._verbose)
+            elif stream.name() in self.MicroDSTStreams:
+                stream.checkFlavourTagging(
+                    disableFT=False, verbose=self._verbose)
+            else:
+                stream.checkFlavourTagging(
+                    disableFT=False, verbose=self._verbose)
 
-    def checkAppendedLines (self) : 
+    def checkAppendedLines(self):
         """
         Check if all declared lines are appended to streams
         """
         allAppended = True
         from StrippingLine import strippingLines
-        for line in strippingLines() : 
-            if not line.isAppended() : 
-                log.warning("Line " + line.name() + " is declared but not appended to any stream")
+        for line in strippingLines():
+            if not line.isAppended():
+                log.warning("Line " + line.name() +
+                            " is declared but not appended to any stream")
                 allAppended = False
-	
-        if allAppended : 
+
+        if allAppended:
             log.info("All declared lines are appended to streams")
 
-    def checkUniqueOutputLocations (self) : 
+    def checkUniqueOutputLocations(self):
         """
         Check if the output locations of all active lines are unique
         """
         log.info("Checking uniqueness of output locations")
-        import sys
         locations = {}
-        for stream in self.activeStreams() :
-            for line in stream.lines :
+        for stream in self.activeStreams():
+            for line in stream.lines:
                 location = line.outputLocation()
-                if location and location != '' :
-                    if location not in locations.keys() : 
-                        locations[location] = [ (line.name(),stream.name()) ]
-                    else : 
-                        locations[location] += [ (line.name(),stream.name()) ]
+                if location and location != '':
+                    if location not in locations.keys():
+                        locations[location] = [(line.name(), stream.name())]
+                    else:
+                        locations[location] += [(line.name(), stream.name())]
         locationsUnique = True
         locationsUniqueSameStream = True
         message = ''
         messagesamestream = ''
-        for loc, nameandstream in locations.iteritems() : 
-            if len(nameandstream) > 1 :
+        for loc, nameandstream in locations.iteritems():
+            if len(nameandstream) > 1:
                 innermessage = ''
                 innerlines = {}
                 for ns in nameandstream:
-                    if innermessage=='':
-                        innermessage=str(ns[0])+"(stream "+str(ns[1])+")"
+                    if innermessage == '':
+                        innermessage = str(ns[0])+"(stream "+str(ns[1])+")"
                     else:
-                        innermessage+=" ,"+str(ns[0])+"(stream "+str(ns[1])+")"
-                    if ns[1] not in innerlines.keys() :
+                        innermessage += " ," + \
+                            str(ns[0])+"(stream "+str(ns[1])+")"
+                    if ns[1] not in innerlines.keys():
                         innerlines[ns[1]] = [ns[0]]
                     else:
-                        innerlines[ns[1]] += [ ns[0] ]
-                message += "\tLines "+innermessage+" share the same output location '"+loc+"'\n"
-                #sys.stderr.write(message)
+                        innerlines[ns[1]] += [ns[0]]
+                message += "\tLines "+innermessage+" share the same output location '"+loc+"'\n"  # noqa
+                # sys.stderr.write(message)
                 locationsUnique = False
 
-                #print innerlines
-                
-                for stinner, linner in innerlines.iteritems() :
-                    if len(linner) > 1 :
+                # print innerlines
+
+                for stinner, linner in innerlines.iteritems():
+                    if len(linner) > 1:
                         inmsg = ''
                         for inl in linner:
-                            if inmsg=='':
-                                inmsg=str(inl)+"(stream "+stinner+")"
+                            if inmsg == '':
+                                inmsg = str(inl)+"(stream "+stinner+")"
                             else:
-                                inmsg=" ,"+str(inl)+"(stream "+stinner+")"
-                        messagesamestream+="\tLines "+inmsg+" share the same output location '"+loc+"' and the same stream '"+stinner+"! Please remove duplicates in configuration'\n"
+                                inmsg = " ,"+str(inl)+"(stream "+stinner+")"
+                        messagesamestream += "\tLines "+inmsg + \
+                                             " share the same output location '"+loc + \
+                            "' and the same stream '"+stinner+"! Please remove duplicates in configuration'\n"  # noqa
                         locationsUniqueSameStream = False
-                        
-                    
-                    
-        if not locationsUnique : 
-            #raise Exception('\n' + message)
+
+        if not locationsUnique:
+            # raise Exception('\n' + message)
             log.warning('\n' + message)
 
-        if not locationsUniqueSameStream :
-            #raise Exception('\n' + message)
+        if not locationsUniqueSameStream:
+            # raise Exception('\n' + message)
             raise Exception('\n' + messagesamestream)
 
-
-    def activeStreams (self) :
+    def activeStreams(self):
         """
-        Return the list of all active StrippingStreams. 
+        Return the list of all active StrippingStreams.
         """
         return self._streams
 
-    def activeLines (self,selStream = [] ) :
+    def activeLines(self, selStream=[]):
         """
-        Return the list of all stripping lines 
+        Return the list of all stripping lines.
         """
         streams = self.activeStreams()
         lines = []
         for stream in streams:
-          if selStream != [] and stream.name() in selStream:
-            for line in stream.lines:
-              lines.append(line)
-          elif selStream == []:
-            for line in stream.lines:
-              lines.append(line)
-    
+            if selStream != [] and stream.name() in selStream:
+                for line in stream.lines:
+                    lines.append(line)
+            elif selStream == []:
+                for line in stream.lines:
+                    lines.append(line)
+
         return lines
 
-    def sequence (self) :
+    def sequence(self):
         """
         Return GaudiSequencer containing stream sequencers
         """
         from Configurables import GaudiSequencer
-        log.debug("Initialising GaudiSequencer/"+ self._name)
-        if self._sequence == None :
-            log.debug("Initialising GaudiSequencer/"+ self._name)
+        log.debug("Initialising GaudiSequencer/" + self._name)
+        if self._sequence is None:
+            log.debug("Initialising GaudiSequencer/" + self._name)
             selSeq = GaudiSequencer(self._name+"_Selection",
-                                    ModeOR = True, 
-                                    ShortCircuit = False,
-                                    OutputLevel = WARNING, 
-                                    Members = self._streamSequencers)
+                                    ModeOR=True,
+                                    ShortCircuit=False,
+                                    OutputLevel=WARNING,
+                                    Members=self._streamSequencers)
 
-            self._sequence = GaudiSequencer(self._name,Members = [selSeq])
+            self._sequence = GaudiSequencer(self._name, Members=[selSeq])
 
             if self._GlobalFlavourTagging and self._taggingLocations != []:
                 self._sequence.Members += [self._taggingSeq]
 
         return self._sequence
 
-    def selections (self) :
+    def selections(self):
         """
         Return list of selection names for TagCreator
         """
-        _selections = [ self._name ]
-        for stream in self._streams : 
+        _selections = [self._name]
+        for stream in self._streams:
             streamName = stream.sequence().name()
             _selections.append(streamName)
-            for line in stream.lines :
+            for line in stream.lines:
                 _selections.append(line.name())
         return _selections
 
-    def appendStreams(self, streams) :
+    def appendStreams(self, streams):
         """
         Append a list of streams to the configuration.
         """
-        for stream in streams :
+        for stream in streams:
             self.appendStream(stream)
-            
-    def appendStream(self, stream) :
+
+    def appendStream(self, stream):
         """
         Append a StrippingStream to the configuration. Takes care of adding
         corresponding sequencer to _streamSequencers list.
         """
-        log.info(self._name+ " appending stream "+ stream.name())
-        
-        if stream.TESPrefix == None : 
+        log.info(self._name + " appending stream " + stream.name())
+
+        if stream.TESPrefix is None:
             stream.TESPrefix = self._tesPrefix
         stream.HDRLocation = self._hdrLocation
-        if stream.BadEventSelection == "Override" :
-            if isinstance(self.BadEventSelection,dict):
-              if stream.name() in self.BadEventSelection.keys():
-                stream.BadEventSelection = self.BadEventSelection[stream.name()]
-		log.info(self._name+ " setting BadEventSelection for stream "+ stream.name() + " as " + str(stream.BadEventSelection))
-              else:
-                stream.BadEventSelection = self.BadEventSelection['default']
-                log.info(self._name+ " setting BadEventSelection for stream "+ stream.name() + " as " + str(stream.BadEventSelection))
-	      log.info(self._name+ " setting BadEventSelection for stream "+ stream.name())
+        if stream.BadEventSelection == "Override":
+            if isinstance(self.BadEventSelection, dict):
+                if stream.name() in self.BadEventSelection.keys():
+                    stream.BadEventSelection = self.BadEventSelection[stream.name()]  # noqa
+                    log.info(self._name +
+                             " setting BadEventSelection for stream " +
+                             stream.name() + " as " +
+                             str(stream.BadEventSelection))
+                else:
+                    stream.BadEventSelection = self.BadEventSelection['default']  # noqa
+                    log.info(self._name +
+                             " setting BadEventSelection for stream " +
+                             stream.name() + " as " +
+                             str(stream.BadEventSelection))
+                log.info(self._name +
+                         " setting BadEventSelection for stream " +
+                         stream.name())
             else:
-              stream.BadEventSelection = self.BadEventSelection
-        if stream.AcceptBadEvents == None :
-            if isinstance(self.AcceptBadEvents,dict):
-              if stream.name() in self.AcceptBadEvents.keys():
-                stream.AcceptBadEvents = self.AcceptBadEvents[stream.name()]
-              	log.info(self._name+ " setting AcceptBadEvents for stream "+ stream.name()  + " as " + str(stream.AcceptBadEvents))
-	      else:
-                stream.AcceptBadEvents = self.AcceptBadEvents['default']
-		log.info(self._name+ " setting AcceptBadEvents for stream "+ stream.name()  + " as " + str(stream.AcceptBadEvents))
-              log.info(self._name+ " setting AcceptBadEvents for stream "+ stream.name())
+                stream.BadEventSelection = self.BadEventSelection
+        if stream.AcceptBadEvents is None:
+            if isinstance(self.AcceptBadEvents, dict):
+                if stream.name() in self.AcceptBadEvents.keys():
+                    stream.AcceptBadEvents = self.AcceptBadEvents[stream.name(
+                    )]
+                    log.info(self._name +
+                             " setting AcceptBadEvents for stream " +
+                             stream.name() + " as " +
+                             str(stream.AcceptBadEvents))
+                else:
+                    stream.AcceptBadEvents = self.AcceptBadEvents['default']
+                    log.info(self._name +
+                             " setting AcceptBadEvents for stream " +
+                             stream.name() +
+                             " as " + str(stream.AcceptBadEvents))
+                log.info(
+                    self._name + " setting AcceptBadEvents for stream " +
+                    stream.name())
             else:
-              stream.AcceptBadEvents = self.AcceptBadEvents
+                stream.AcceptBadEvents = self.AcceptBadEvents
+
+        if stream.MaxCandidates == "Override":
+            stream.MaxCandidates = self.MaxCandidates
+        if stream.MaxCombinations == "Override":
+            stream.MaxCombinations = self.MaxCombinations
 
-        if stream.MaxCandidates == "Override" : 
-    	    stream.MaxCandidates = self.MaxCandidates
-        if stream.MaxCombinations == "Override" : 
-    	    stream.MaxCombinations = self.MaxCombinations
-        
         stream.createConfigurables()
         self._streams.append(stream)
         self._appendSequencer(stream)
 
-    def appendFlavourTagging(self) :
+    def appendFlavourTagging(self):
         from Configurables import BTagging, BTaggingTool, GaudiSequencer
         from FlavourTagging.Tunings import applyTuning
-        btag = BTagging( "BTag_Global",Inputs = self._taggingLocations )
+        btag = BTagging("BTag_Global", Inputs=self._taggingLocations)
         btag.addTool(BTaggingTool)
         applyTuning(btag.BTaggingTool)
-        self._taggingSeq = GaudiSequencer("BTaggingSequence", Members = [btag])
-        
-    def _appendSequencer(self, stream) :
+        self._taggingSeq = GaudiSequencer("BTaggingSequence", Members=[btag])
+
+    def _appendSequencer(self, stream):
         self._streamSequencers.append(stream.sequence())
 
-    def decReportLocations(self) : 
+    def decReportLocations(self):
         locs = []
-        for stream in self._streams : 
-            for line in stream.lines : 
+        for stream in self._streams:
+            for line in stream.lines:
                 loc = line.decReportLocation()
-                if loc != None and loc not in locs : locs.append(loc)
+                if loc is not None and loc not in locs:
+                    locs.append(loc)
 
         return locs
 
-    def limitCombForStdParticles(self,incidentName = 'ExceedsCombinatoricsLimit'):
+    def limitCombForStdParticles(self,
+                                 incidentName='ExceedsCombinatoricsLimit'):
         from StandardParticles import locations as stdLoc
-        for loc,alg in stdLoc.iteritems():
-            if hasattr(type(alg),'StopAtMaxCandidates') and \
-               hasattr(type(alg),'MaxCandidates') and \
-               hasattr(type(alg),'StopAtMaxCombinations') and \
-               hasattr(type(alg),'MaxCombinations'):
-                if self.MaxCandidates != None:
+        for loc, alg in stdLoc.iteritems():
+            if hasattr(type(alg), 'StopAtMaxCandidates') and \
+               hasattr(type(alg), 'MaxCandidates') and \
+               hasattr(type(alg), 'StopAtMaxCombinations') and \
+               hasattr(type(alg), 'MaxCombinations'):
+                if self.MaxCandidates is not None:
                     alg.StopAtMaxCandidates = True
                     alg.MaxCandidates = self.MaxCandidates
-                if self.MaxCombinations != None:
+                if self.MaxCombinations is not None:
                     alg.StopAtMaxCombinations = True
                     alg.MaxCombinations = self.MaxCombinations
-                if self.MaxCandidates != None or self.MaxCombinations != None :
+                if self.MaxCandidates is not None or self.MaxCombinations is not None:  # noqa
                     alg.StopIncidentType = incidentName
-                ## comment to be removed once performed some more test
-                #if self._verbose: log.warning('Changed parameters StopAtMaxCandidates = '+str(alg.StopAtMaxCandidates)+' MaxCandidates = '+str(alg.MaxCandidates)+' StopIncidentType = '+str(alg.StopIncidentType)+' for algorithm '+str(alg.name()))
-
+                # comment to be removed once performed some more test
+                # if self._verbose: log.warning('Changed parameters StopAtMaxCandidates = '+str(alg.StopAtMaxCandidates)+' MaxCandidates = '+str(alg.MaxCandidates)+' StopIncidentType = '+str(alg.StopIncidentType)+' for algorithm '+str(alg.name()))  # noqa
 
     # Loops over all known configurables and applies MaxCandidate limits
-    def checkAllForCombLimit(self) :
-        '''Limit the combinatorics of all configurables using self.MaxCandidates and self.MaxCombinations,
-        unless these have already been configured. This is normally called before the streams are appended 
-        & their configurables created.'''
 
-        if self.MaxCandidates == None and self.MaxCombinations == None :
+    def checkAllForCombLimit(self):
+        '''
+        Limit the combinatorics of all configurables
+        using self.MaxCandidates and self.MaxCombinations,
+        unless these have already been configured.
+        This is normally called before the streams are appended
+        & their configurables created.
+        '''
+
+        if self.MaxCandidates is None and self.MaxCombinations is None:
             return
 
         from Gaudi.Configuration import allConfigurables
-        
-        for conf in allConfigurables.values() :
-            limitCombinatorics(conf, self.MaxCandidates, self.MaxCombinations, False)
+
+        for conf in allConfigurables.values():
+            limitCombinatorics(conf, self.MaxCandidates,
+                               self.MaxCombinations, False)
 
 
 # =============================================================================
-# Some useful decorations 
+# Some useful decorations
 # =============================================================================
-## Calculate the effective length of the string
-#  which is the length from the last '\n'-symbol 
-def len1 ( line ) :
+# Calculate the effective length of the string
+#  which is the length from the last '\n'-symbol
+def len1(line):
     """
     Calculate the effective length of the line,
-    which is thw length from the last '\n'-symbol 
+    which is thw length from the last '\n'-symbol
     """
     _i = line.rfind('\n')
     return len(line) if _i < 0 else len(line) - _i
 
-## the major properties/attributes  
-_stripping_props_   =      [ 'AcceptFraction'    , 
-                   'PercertPass'       ,
-                   'L0Channels'        ,
-                   'InputSelection'    ,
-                   'InputSelection1'   ,
-                   'InputSelection2'   ,
-                   'InputSelection3'   ,
-                   'InputSelections'   ,
-                   'OutputSelection'   ,
-                   'RecoName'          ,
-                   'MatchName'         ,
-                   'FilterDescription' ] 
-
-## Get the tuple of major interesting properties for Hlt1  objects
-def strippingProps () :
+
+# the major properties/attributes
+_stripping_props_ = ['AcceptFraction',
+                     'PercertPass',
+                     'L0Channels',
+                     'InputSelection',
+                     'InputSelection1',
+                     'InputSelection2',
+                     'InputSelection3',
+                     'InputSelections',
+                     'OutputSelection',
+                     'RecoName',
+                     'MatchName',
+                     'FilterDescription']
+
+# Get the tuple of major interesting properties for Hlt1  objects
+
+
+def strippingProps():
     """
     Get the tuple of major interesting properties for Hlt1  objects
 
     """
-    _stripping_props_.sort() 
+    _stripping_props_.sort()
     return tuple(_stripping_props_)
 
 
 # =============================================================================
-## Try to promote a string to the corresponding configurable
-def string2Configurable( name ) :
+# Try to promote a string to the corresponding configurable
+def string2Configurable(name):
     # try to decode it into something reasonable
-    (n,t) = (name,None) if name.find('/') == -1 else name.split('/')
+    (n, t) = (name, None) if name.find('/') == -1 else name.split('/')
     from Gaudi.Configuration import allConfigurables
     cfg = allConfigurables.get(n)
-    if cfg :
-        if ( t and cfg.getType() == t ) or cfg.getType() == 'ConfigurableGeneric' :
+    if cfg:
+        if (t and cfg.getType() == t) or cfg.getType() == 'ConfigurableGeneric':  # noqa
             return cfg
-        else :
-            print 'got something for %s, don\'t know what to do with %s'%(self,str(cfg))
+        else:
+            print('got something for %s, don\'t know what to do with %s' %
+                  (name, str(cfg)))
             return None
-    print 'cannot convert %s into a known configurable' % name
+    print('cannot convert %s into a known configurable' % name)
     return None
 
 # =============================================================================
-## Print the major properties/attributes of the configurables
+# Print the major properties/attributes of the configurables
 #  @param obj  the object to be inspected
-#  @param lst  list of attributes/properties 
+#  @param lst  list of attributes/properties
 #  @param line the (output) line
 #  @paral l1   the indentation parameter
 #  @author Vanya BELYAEV Ivan.Belyaev@nikhef.nl
 #  @date 2008-08-06
-def prnt ( obj        ,   # the object 
-           lst  = []  ,   # list of 'major' properties
-           line = ''  ,   # the line to eb updated
-           l1   = 65  ) : # the indentation/format parameter 
+
+
+def prnt(obj,   # the object
+         lst=[],   # list of 'major' properties
+         line='',   # the line to eb updated
+         l1=65):  # the indentation/format parameter
     """
     Print the major properties/attributes of the configurables
     @param obj  the object to be inspected
-    @param lst  list of attributes/properties 
+    @param lst  list of attributes/properties
     @param line the (output) line
     @paral l1   the indentation parameter
     @author Vanya BELYAEV Ivan.Belyaev@nikhef.nl
     @date 2008-08-06
 
     >>> obj = ...  # get the object/configurable
-    >>> print prnt ( obj , [ 'OutputLevel' , 'Members'] ) # print... 
-    
+    >>> print prnt ( obj , [ 'OutputLevel' , 'Members'] ) # print...
+
     """
-    if not lst : lst = strippingProps () 
-    elif list  is type(lst) : pass
-    elif tuple is type(lst) : pass
-    else : lst = [ lst ]
+    if not lst:
+        lst = strippingProps()
+    elif list is type(lst):
+        pass
+    elif tuple is type(lst):
+        pass
+    else:
+        lst = [lst]
     #
-    for item in lst :
-        if hasattr ( obj , item ) :
-            if l1 < len1( line ) : line += '\n' + l1*' '
-            line += "%-15s : %s" % ( item , getattr ( obj , item ) )
-    return line 
+    for item in lst:
+        if hasattr(obj, item):
+            if l1 < len1(line):
+                line += '\n' + l1*' '
+            line += "%-15s : %s" % (item, getattr(obj, item))
+    return line
 
 # =============================================================================
-## The helper function for narcissic self-print of sequences  & algorithms 
+# The helper function for narcissic self-print of sequences  & algorithms
 #  @param self  the object to be inspected
 #  @param level the recursion level
-#  @param lst   the list of major properties/attributes 
+#  @param lst   the list of major properties/attributes
 #  @author Vanya BELYAEV Ivan.Belyaev@nikhef.nl
 #  @date 2008-08-06
-def __enroll__ ( self       ,   ## the object
-                 level = 0  ,   ## the recursion level
-                 lst   = [] ) : ## the major properties  
+
+
+def __enroll__(self,  # the object
+               level=0,  # the recursion level
+               lst=[]):  # the major properties
     """
-    The helper function for narcissic self-print of sequences  & algorithms 
+    The helper function for narcissic self-print of sequences  & algorithms
     @param self  the object to be inspected
     @param level the recursion level
-    @param lst   the list of major properties/attributes 
+    @param lst   the list of major properties/attributes
     @author Vanya BELYAEV Ivan.Belyaev@nikhef.nl
     @date 2008-08-06
-    
+
     """
 
-    if type(self) == str :
+    if type(self) == str:
         cfg = string2Configurable(self)
-        if cfg : self = cfg
-    if hasattr ( self , 'sequence' ) :
-        return __enroll__ ( self.sequence() , level )
-    if hasattr ( self , 'sequencer' ) :
-        return __enroll__ ( self.sequencer() , level )
+        if cfg:
+            self = cfg
+    if hasattr(self, 'sequence'):
+        return __enroll__(self.sequence(), level)
+    if hasattr(self, 'sequencer'):
+        return __enroll__(self.sequencer(), level)
 
     _tab = 50
-    _indent_ = ('%-3d'%level) + level * '   ' 
-    try:     line = _indent_ + self.name ()
-    except:  line = _indent_ + ( self if type(self) == str else '<UNKNOWN>' )
-        
-    if len1(line)>( _tab-1): line +=  '\n'+ _tab*' '
-    else :                   line +=  (_tab-len1(line))*' '
-    try:                     line +=  '%-25.25s'%self.getType()
-    except:                  line +=  '<UNKNOWN>'
-
-    line = prnt ( self , lst , line, l1 = _tab+25 ) + '\n'
-
-    # use the recursion 
-    if hasattr ( self , 'Members' ) :
-        for _m in getattr(self,'Members') : line += __enroll__ ( _m , level + 1 , lst ) 
-
-    if type(self) is StrippingAlg :
-        for i in [ 'Prescale','ODIN','L0DU','HLT','Filter1','Postscale' ] :
-            if hasattr(self,i) : line += __enroll__( getattr(self,i), level + 1, lst )
-
-    if type(self) is StrippingConf : 
+    _indent_ = ('%-3d' % level) + level * '   '
+    try:
+        line = _indent_ + self.name()
+    except:  # noqa
+        line = _indent_ + (self if type(self) == str else '<UNKNOWN>')
+
+    if len1(line) > (_tab-1):
+        line += '\n' + _tab*' '
+    else:
+        line += (_tab-len1(line))*' '
+    try:
+        line += '%-25.25s' % self.getType()
+    except:  # noqa
+        line += '<UNKNOWN>'
+
+    line = prnt(self, lst, line, l1=_tab+25) + '\n'
+
+    # use the recursion
+    if hasattr(self, 'Members'):
+        for _m in getattr(self, 'Members'):
+            line += __enroll__(_m, level + 1, lst)
+
+    if type(self) is StrippingAlg:
+        for i in ['Prescale', 'ODIN', 'L0DU', 'HLT', 'Filter1', 'Postscale']:
+            if hasattr(self, i):
+                line += __enroll__(getattr(self, i), level + 1, lst)
+
+    if type(self) is StrippingConf:
         lines = 0
-        for i in self.activeStreams() : 
+        for i in self.activeStreams():
             lines += len(i.sequence().Members)
-        line += "Summary: " + len(self.sequence().Members) + " streams, " + lines + " lines\n"
+        line += "Summary: " + len(self.sequence().Members) + \
+            " streams, " + lines + " lines\n"
 
     return line
 
-def defaultToolConfigCheck () : 
+
+def defaultToolConfigCheck():
     from Gaudi.Configuration import allConfigurables
-    
+
     log.info('Checking if public tools have default configuration')
 
-    for conf in allConfigurables.values() : 
-        if conf.name().find('ToolSvc.')>=0 : 
+    for conf in allConfigurables.values():
+        if conf.name().find('ToolSvc.') >= 0:
             difference = []
-            if isinstance(type(conf).__slots__,dict) : 
-                for k,v in type(conf).__slots__.iteritems() : 
-                    if hasattr(conf, k) : 
-                        val = getattr(conf,k)
-                        if val not in allConfigurables.values() : 
-                            if v != val : 
-                                difference.append( (k, v, val ) )
-            if len(difference) > 0 : 
-                log.warning( 'tool %s has non-default configuration! Attributes that differ:' % conf.name() )
-                for d in difference : 
-                    log.warning( '    %s = %s (default = %s)' % ( d[0], str(d[2]), str(d[1]) ) )
-
-
-for conf in [ StrippingAlg, StrippingStream, StrippingConf] :
-    if conf :
-        conf.__str__ = __enroll__ 
-
+            if isinstance(type(conf).__slots__, dict):
+                for k, v in type(conf).__slots__.iteritems():
+                    if hasattr(conf, k):
+                        val = getattr(conf, k)
+                        if val not in allConfigurables.values():
+                            if v != val:
+                                difference.append((k, v, val))
+            if len(difference) > 0:
+                log.warning(
+                    'tool %s has non-default configuration! Attributes that differ:' % conf.name())  # noqa
+                for d in difference:
+                    log.warning('    %s = %s (default = %s)' %
+                                (d[0], str(d[2]), str(d[1])))
+
+
+for conf in [StrippingAlg, StrippingStream, StrippingConf]:
+    if conf:
+        conf.__str__ = __enroll__
diff --git a/Phys/StrippingConf/python/StrippingConf/StrippingConfigurableUser.py b/Phys/StrippingConf/python/StrippingConf/StrippingConfigurableUser.py
old mode 100755
new mode 100644
index f10e7d7a07d680a1c76026e09c3aaa1f16700714..6200459c70eb02aa7d79115fa3aa9533ae7579e1
--- a/Phys/StrippingConf/python/StrippingConf/StrippingConfigurableUser.py
+++ b/Phys/StrippingConf/python/StrippingConf/StrippingConfigurableUser.py
@@ -18,7 +18,6 @@ __all__ = (
     'StrippingConfigurableUser'
 )
 
-from GaudiConf.Configuration import *
 from Configurables import LHCbConfigurableUser
 
 
diff --git a/Phys/StrippingConf/python/StrippingConf/StrippingLine.py b/Phys/StrippingConf/python/StrippingConf/StrippingLine.py
index c40e31bd36c6efc17d7230139429cb1caa634dab..f1fce07e34391ade7a1a679f4dc8488fd457f159 100755
--- a/Phys/StrippingConf/python/StrippingConf/StrippingLine.py
+++ b/Phys/StrippingConf/python/StrippingConf/StrippingLine.py
@@ -1,6 +1,6 @@
 #!/usr/bin/env python
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -10,6 +10,8 @@
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
 
+from __future__ import print_function
+
 #
 # StrippingLine
 #
@@ -20,14 +22,14 @@ __all__ = (
 )
 
 # cached related info information
-relatedInfoCache = { }
+relatedInfoCache = {}
 
 def makePropKey(props):
     return hash(repr(sorted(props.items())))
 
 import re
 from copy import deepcopy
-from Gaudi.Configuration import *
+from Gaudi.Configuration import log, WARNING
 from GaudiConfUtils import isConfigurable
 from Gaudi.Configuration import GaudiSequencer, Sequencer, Configurable
 import Configurables
@@ -51,52 +53,53 @@ from SelPy.selection import flatAlgorithmList
 from GaudiConfUtils import isConfigurable
 from Utils import limitCombinatorics
 
+
 ## Convention: the name of 'Filter' algorithm inside StrippingLine
-def filterName   ( line , level = 'Stripping') :
+def filterName(line, level='Stripping'):
     """Convention: the name of 'Filter' algorithm(s) inside StrippingLine"""
-    return '%s%sFilterSequence'   % (level,line)
+    return '%s%sFilterSequence' % (level,line)
 
 ## Convention: the name of 'PreScaler' algorithm inside StrippingLine
-def prescalerName  ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'PreScaler' algorithm inside StrippingLine """
-    return '%s%sPreScaler'  % (level,line)
+def prescalerName(line, level='Stripping'):
+    """ Convention: the name of 'PreScaler' algorithm inside StrippingLine"""
+    return '%s%sPreScaler' % (level, line)
 
 ## Convention: the name of 'PostScaler' algorithm inside StrippingLine
-def postscalerName ( line , level = 'Stripping') :
-    """ Convention: the name of 'PostScaler' algorithm inside StrippingLine """
+def postscalerName(line, level='Stripping'):
+    """ Convention: the name of 'PostScaler' algorithm inside StrippingLine"""
     return '%s%sPostScaler' % (level, line)
 
 ## Convention: the name of 'ODINFilter' algorithm inside StrippingLine
-def odinentryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'ODINFilter' algorithm inside StrippingLine """
+def odinentryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'ODINFilter' algorithm inside StrippingLine"""
     return '%s%sODINFilter'   % (level,line)
 
 ## Convention: the name of 'VOIDFilter' algorithm inside StrippingLine
-def voidentryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'VOIDFilter' algorithm inside StrippingLine """
+def voidentryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'VOIDFilter' algorithm inside StrippingLine"""
     return '%s%sVOIDFilter'   % (level,line)
 
 ## Convention: the name of 'L0DUFilter' algorithm inside StrippingLine
-def l0entryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'L0DUFilter' algorithm inside StrippingLine """
+def l0entryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'L0DUFilter' algorithm inside StrippingLine"""
     return '%s%sL0DUFilter'   % (level,line)
 
 ## Convention: the name of 'HLTFilter' algorithm inside StrippingLine
-def hltentryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'HLTFilter' algorithm inside StrippingLine """
+def hltentryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'HLTFilter' algorithm inside StrippingLine"""
     return '%s%sHltFilter'   % (level,line)
 
 ## Convention: the name of 'HLT1Filter' algorithm inside StrippingLine
-def hlt1entryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'HLT1Filter' algorithm inside StrippingLine """
+def hlt1entryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'HLT1Filter' algorithm inside StrippingLine"""
     return '%s%sHlt1Filter'   % (level,line)
 
 ## Convention: the name of 'HLT2Filter' algorithm inside StrippingLine
-def hlt2entryName    ( line, level = 'Stripping' ) :
-    """ Convention: the name of 'HLT2Filter' algorithm inside StrippingLine """
+def hlt2entryName    ( line, level = 'Stripping' ):
+    """ Convention: the name of 'HLT2Filter' algorithm inside StrippingLine"""
     return '%s%sHlt2Filter'   % (level,line)
 
-def decisionName   ( line, level = 'Stripping'  ) :
+def decisionName   ( line, level = 'Stripping'  ):
     """Convention: the name of 'Decision' algorithm inside StrippingLine"""
     return level + '%sDecision'   % line if line != 'Global' else level+'Global'
 
@@ -106,121 +109,121 @@ _stripping_lines__ = dict()
 # =============================================================================
 ## Add the created line into the local storage of created Hlt1Lines
 
-def _add_to_stripping_lines_( line ) :
+def _add_to_stripping_lines_(line):
     """
-    Add the line into the local storage of created Hlt1Lines
+    Add the line into the local storage of created Hlt1Lines.
     """
     lname = line.name()
     if lname in _stripping_lines__:
-        raise ValueError,"Created StrippingLine with duplicate name %s" % lname 
+        raise ValueError,"Created StrippingLine with duplicate name %s" % lname  # noqa
     _stripping_lines__[lname] = line
 
 
-def strippingLines () :
+def strippingLines():
     return _stripping_lines__.values()
 
-class bindMembers (object) :
+
+class bindMembers(object):
     """
-    Simple class to represent a set of StrippingLine members which are bound to a line
+    Simple class to represent a set of StrippingLine members
+    that are bound to a line.
     """
     __slots__ = ('_members', '_outputloc', '_selection')
 
-    def outputLocation( self ) :
+    def outputLocation(self):
         return self._outputloc
 
-    def selection( self ) :
+    def selection(self):
         return self._selection
 
-    def members( self ) :
+    def members(self):
         # remove (downstream) duplicates
         members = []
-        for m in self._members :
-            if m not in members : members += [ m ]
+        for m in self._members:
+            if m not in members:
+                members += [m]
         return members
 
-    def _getOutputLocation (self, alg) :
-        if type(alg) is GaudiSequencer :
-            for i in alg.Members :
-                self._getOutputLocation( i )
-        elif hasattr ( type(alg) , 'OutputSelection' ) :
-            if hasattr ( alg , 'OutputSelection' ) :
+    def _getOutputLocation(self, alg):
+        if type(alg) is GaudiSequencer:
+            for i in alg.Members:
+                self._getOutputLocation(i)
+        elif hasattr(type(alg), 'OutputSelection'):
+            if hasattr(alg, 'OutputSelection'):
                 self._outputloc = "Phys/"+alg.OutputSelection
-        elif hasattr ( type(alg) , 'OutputLocation' ) :
-            if hasattr ( alg , 'OutputLocation' ) :
+        elif hasattr(type(alg), 'OutputLocation'):
+            if hasattr(alg, 'OutputLocation'):
                 self._outputloc = alg.OutputLocation
-        else :
-#            self._outputsel = None
-#            self._outputloc = None
+        else:
+            # self._outputsel = None
+            # self._outputloc = None
             self._outputloc = "Phys/"+alg.name()
 
-    def _default_handler_( self, line, alg ) :
+    def _default_handler_(self, line, alg):
         return self._handle_Selection(line, alg)
 
-    def _handle_Configurable( self, line, alg ) :
+    def _handle_Configurable(self, line, alg):
         if isinstance(line, str) and line.find("Stream") != 0 :
             log.warning('line' + line + ' uses plain Gaudi configurable ' + alg.name() + '. Consider using Selection instead!')
         # if not known, blindly copy -- not much else we can do
-        self._members += [ alg ]
+        self._members += [alg]
         # try to guess where the output goes...
         self._getOutputLocation(alg)
 
 
-    def _handle_SelectionSequence(self, line, alg) :
+    def _handle_SelectionSequence(self, line, alg):
         raise TypeError('Line '+line+': Use of SelectionSequence forbidden. Use Selection types instead')
 
-    def _handleSelectionType(self, line, sel) :
+    def _handleSelectionType(self, line, sel):
         members = flatAlgorithmList(sel)
         self._members += members
         self._selection = sel
         loc = sel.outputLocation()
         self._outputloc = loc
 
-    def _handle_Selection(self, line, alg) :
+    def _handle_Selection(self, line, alg):
         sel = alg.clone(name=line)
-        self._handleSelectionType( line, sel )
+        self._handleSelectionType(line, sel)
 
-    def _handle_PassThroughSelection(self, line, alg) :
-        if alg.outputLocation() != '' :
+    def _handle_PassThroughSelection(self, line, alg):
+        if alg.outputLocation() != '':
             from PhysSelPython.Wrappers import MergedSelection
             alg = MergedSelection(line, RequiredSelections = [alg])
-            self._handleSelectionType( line, alg )
+            self._handleSelectionType(line, alg)
 
-    def _handle_VoidEventSelection(self, line, alg) :
-        if alg.outputLocation() != '' :
+    def _handle_VoidEventSelection(self, line, alg):
+        if alg.outputLocation() != '':
             from PhysSelPython.Wrappers import MergedSelection
             alg = MergedSelection(line, RequiredSelections = [alg])
-            self._handleSelectionType( line, alg )
+            self._handleSelectionType(line, alg)
 
-    def _handle_AutomaticData(self, line, alg) :
+    def _handle_AutomaticData(self, line, alg):
         from PhysSelPython.Wrappers import MergedSelection
         sel = MergedSelection(line, RequiredSelections = [alg])
-        self._handleSelectionType( line, sel )
+        self._handleSelectionType(line, sel)
 
     # allow chaining of previously bound members...
-    def _handle_bindMembers( self, line, alg ) :
-        self._members  += alg.members()
+    def _handle_bindMembers(self, line, alg):
+        self._members += alg.members()
         # sometimes, we want to ignore this...
         # add a flag to allow to skip this (when set to None?)
-        if alg.outputLocation() : self._outputloc = alg.outputLocation()
-
-    def __init__( self, line, algos ) :
+        if alg.outputLocation():
+            self._outputloc = alg.outputLocation()
 
+    def __init__(self, line, algos):
         self._members = []
         self._outputloc = None
         self._selection = None
         for alg in algos:
             # dispatch according to the type of alg...
-            if isConfigurable(alg) :
+            if isConfigurable(alg):
                 self._handle_Configurable(line, alg)
-            else :
+            else:
                 x = '_handle_' + type(alg).__name__
-
                 handle = getattr(self, x if hasattr(self, x) else '_default_handler_')
                 handle(line,alg)
 
 
-
-
 # =============================================================================
 ## @class StrippingLine
 class StrippingLine(object):
@@ -257,48 +260,48 @@ class StrippingLine(object):
 
     _protected_ = ( 'IgnoreFilterPassed' , 'Members' , 'ModeOR', 'DecisionName', 'Prescale','Postscale','Filter1' )
                            
-    def __init__ ( self             ,
-                   name             ,   # the base name for the Line
-                   prescale  = 1    ,   # prescale factor
-                   ODIN      = None ,   # ODIN predicate
-                   L0DU      = None ,   # L0DU predicate
-                   HLT       = None ,   # HltDecReports predicate  -> Deprecated since 2015
-                   HLT1      = None ,   # Hlt1DecReports predicate
-                   HLT2      = None ,   # Hlt2DecReports predicate
-                   FILTER    = None ,   # 'VOID'-predicate, e.g. Global Event Cut
-                   checkPV   = True ,   # Check PV before running algos
-                   algos     = None ,   # the list of stripping members
-                   selection = None ,
-                   postselalg = None,   # algorithm to run after the candidate has been selected
-                   postscale = 1    ,   # postscale factor
-                   MaxCandidates = "Override",   # Maxumum number of candidates for CombineParticles
-                   MaxCombinations = "Override", # Maxumum number of combinations for CombineParticles
-                   HDRLocation = None,           # if None, defined by stream name
-                   EnableFlavourTagging = False, # If True, run FlavourTaggingTool to store FT info
-
-                   ExtraInfoTools = None,        # Configuration of ExtraInfo tools, as a list of dictionaries (or None)
-                   ExtraInfoSelections = None,   # Input selections for ExtraInfo tools. If None, use the top-level selection of the line
-                   ExtraInfoDaughters = None,    # Daughter selections for which store ExtraInfo. If None, use only the top selection.
-                   ExtraInfoRecursionLevel = 1,  # Maximum depth in the decay tree to calculate ExtraInfo
-                                                 # Only used is ExtraInfoDaughters are given, otherwise is 0
-
-                   RelatedInfoTools = None,      # Configuration of Related Info tools, as a list of dictionaries (or None)
-                   RelatedInfoFilter = None,     # Optional filter which can use RelatedInfo, added to the line sequence
-                                                 # after RelatedInfoTools
-
-                   RequiredRawEvents = None,     # Possible list of RawEvent banks required by this line
-                   MDSTFlag          = False,     # Flag to ask the line to be written to MDST.DST stream
-                   **args           ) : # other configuration parameters that're passed to StrippingAlg
-
-        if algos and selection :
+    def __init__(self             ,
+                 name             ,   # the base name for the Line
+                 prescale  = 1    ,   # prescale factor
+                 ODIN      = None ,   # ODIN predicate
+                 L0DU      = None ,   # L0DU predicate
+                 HLT       = None ,   # HltDecReports predicate  -> Deprecated since 2015
+                 HLT1      = None ,   # Hlt1DecReports predicate
+                 HLT2      = None ,   # Hlt2DecReports predicate
+                 FILTER    = None ,   # 'VOID'-predicate, e.g. Global Event Cut
+                 checkPV   = True ,   # Check PV before running algos
+                 algos     = None ,   # the list of stripping members
+                 selection = None ,
+                 postselalg = None,   # algorithm to run after the candidate has been selected
+                 postscale = 1    ,   # postscale factor
+                 MaxCandidates = "Override",   # Maxumum number of candidates for CombineParticles
+                 MaxCombinations = "Override", # Maxumum number of combinations for CombineParticles
+                 HDRLocation = None,           # if None, defined by stream name
+                 EnableFlavourTagging = False, # If True, run FlavourTaggingTool to store FT info
+
+                 ExtraInfoTools = None,        # Configuration of ExtraInfo tools, as a list of dictionaries (or None)
+                 ExtraInfoSelections = None,   # Input selections for ExtraInfo tools. If None, use the top-level selection of the line
+                 ExtraInfoDaughters = None,    # Daughter selections for which store ExtraInfo. If None, use only the top selection.
+                 ExtraInfoRecursionLevel = 1,  # Maximum depth in the decay tree to calculate ExtraInfo
+                                               # Only used is ExtraInfoDaughters are given, otherwise is 0
+
+                 RelatedInfoTools = None,      # Configuration of Related Info tools, as a list of dictionaries (or None)
+                 RelatedInfoFilter = None,     # Optional filter which can use RelatedInfo, added to the line sequence
+                                               # after RelatedInfoTools
+
+                 RequiredRawEvents = None,     # Possible list of RawEvent banks required by this line
+                 MDSTFlag          = False,     # Flag to ask the line to be written to MDST.DST stream
+                 **args           ):  # other configuration parameters that're passed to StrippingAlg
+
+        if algos and selection:
             raise Exception('only algos or selection can be set. You have set both.')
-        if selection :
-            if isConfigurable(selection) :
+        if selection:
+            if isConfigurable(selection):
                 raise TypeError('StrippingLine selection cannot be Configurable type.')
             algos = [selection]
 
         # This only seems to apply if neither algos or selection are set?
-        if not algos :
+        if not algos:
             algos = []
 
         ## 1) clone all arguments
@@ -312,9 +315,10 @@ class StrippingLine(object):
         algos  = deepcopy ( algos  )
         args   = deepcopy ( args   )
         # 2) save all parameters (needed for the proper cloning)
-        self._name      = name
-        if callable(prescale) : prescale = prescale( self.name() )
-        self._prescale  = prescale
+        self._name = name
+        if callable(prescale):
+            prescale = prescale(self.name())
+        self._prescale = prescale
 
         self._ODIN      = ODIN
         self._L0DU      = L0DU
@@ -325,28 +329,26 @@ class StrippingLine(object):
         self._checkPV   = checkPV
         self._HDRLocation = HDRLocation
         self._EnableFlavourTagging = EnableFlavourTagging
-        if callable(postscale) : postscale = postscale( self.name() )
+        if callable(postscale):
+            postscale = postscale(self.name())
         self._postscale = postscale
         self._algos     = algos
         self._args      = args
         self.MaxCandidates = MaxCandidates
         self.MaxCombinations = MaxCombinations
-
         self.ExtraInfoTools = ExtraInfoTools
         self.ExtraInfoSelections = ExtraInfoSelections
         self.ExtraInfoDaughters = ExtraInfoDaughters
         self.ExtraInfoRecursionLevel = ExtraInfoRecursionLevel
-
         self.RelatedInfoTools = RelatedInfoTools
         self.RelatedInfoFilter = RelatedInfoFilter
-
         self._initialSelection = selection
         self._postselalg = postselalg
 
         validRawBanks = ["Trigger","Muon","Calo","Rich","Velo","Tracker","HC"] # hard coded list, should really come from elsewhere....
-        if RequiredRawEvents != None :
-            for bank in RequiredRawEvents :
-                if bank not in validRawBanks :
+        if RequiredRawEvents is not None:
+            for bank in RequiredRawEvents:
+                if bank not in validRawBanks:
                     raise Exception("RawBank "+bank+" is not a known type")
         self.RequiredRawEvents = RequiredRawEvents
 
@@ -354,7 +356,7 @@ class StrippingLine(object):
 
         line = self.subname()
 
-        self._appended  = False
+        self._appended = False
 
         # Configurable is not yet created
         self._configurable = None
@@ -369,30 +371,30 @@ class StrippingLine(object):
 
         # if needed, check Primary Vertex before running all algos
 
-        if checkPV == True:
-            check = CheckPV("checkPVmin1");
-            check.MinPVs = 1;
-            self._members.insert(0, check);
-        elif isinstance(checkPV, int) :
+        if checkPV:
+            check = CheckPV("checkPVmin1")
+            check.MinPVs = 1
+            self._members.insert(0, check)
+        elif isinstance(checkPV, int):
             check = CheckPV("checkPVmin%d" % checkPV)
             check.MinPVs = checkPV
-            self._members.insert(0, check);
-        elif isinstance(checkPV, tuple) :
-            if len(checkPV) == 2 :
+            self._members.insert(0, check)
+        elif isinstance(checkPV, tuple):
+            if len(checkPV) == 2:
                 check = CheckPV("checkPVmin%dmax%d" % checkPV)
                 check.MinPVs = checkPV[0]
                 check.MaxPVs = checkPV[1]
-                self._members.insert(0, check);
+                self._members.insert(0, check)
             else :
                 raise TypeError, "Wrong checkPV tuple length %d, should be 2" % len(checkPV)
-        elif checkPV != False :
+        elif checkPV != False:
             raise TypeError, "Wrong checkPV argument type '%s'" % type(checkPV).__name__
 
         # if needed, apply filter before running all algos
-        if FILTER :
-            if isinstance   ( FILTER , str   ) :
-                fltr = VOIDFilter  ( voidentryName  ( line ) , Code = FILTER )
-                self._members.insert ( 0 , fltr )
+        if FILTER:
+            if isinstance(FILTER, str):
+                fltr = VOIDFilter( voidentryName  ( line ) , Code = FILTER )
+                self._members.insert( 0 , fltr )
             elif isinstance ( FILTER , ( tuple , list ) ) and 2 == len ( FILTER ) :
                 fltr = VOIDFilter  ( voidentryName  ( line ) , Code = FILTER[0] , Preambulo = FILTER[1] )
                 self._members.insert ( 0 , fltr )
@@ -435,26 +437,28 @@ class StrippingLine(object):
                     #print "Added outputlocation %s to ExtraInfo in line %s" % (fullPath, self.name() )
             else :
                 raise AttributeError, "Storing ExtraInfo is not supported for selection of type '%s' (in line %s)" % \
-                      (type(sel).__name__, self.name() )
+                      (type(sel).__name__, self.name())
         return locList
 
-    def createConfigurable( self, TESPrefix = "Strip", HDRLocation = 'Phys/DecReports' ) :
+    def createConfigurable(self,
+                           TESPrefix="Strip",
+                           HDRLocation='Phys/DecReports'):
 
-        if self._configurable != None : 
-            log.info("Configurables already created for line %s, skipping" % self.subname() )
+        if self._configurable is not None:
+            log.info("Configurables already created for line %s, skipping" % self.subname())
             return self._configurable
 
-        if self._HDRLocation == None :
+        if self._HDRLocation is None:
             self.fullHDRLocation = TESPrefix + "/" + HDRLocation
         else :
             self.fullHDRLocation = self._HDRLocation
 
         # check for forbidden attributes
-        args    = self._args
+        args = self._args
 
         mdict = {}
-        for key in args :
-            if key in StrippingLine._protected_ :
+        for key in args:
+            if key in StrippingLine._protected_:
                 raise AttributeError, "The attribute'%s' is protected for %s"%(key,self.type())
             mdict[key] = args[key]
 
@@ -544,25 +548,26 @@ class StrippingLine(object):
             toolNames = []
             toolNum = 0
 
-            for itool in self.ExtraInfoTools :
+            for itool in self.ExtraInfoTools:
                 toolNum += 1
                 toolType = itool["Type"]
                 toolName = "Tool%d" % toolNum
                 module = __import__("Configurables", globals(), locals(), [ toolType ] )
-                toolClass = getattr( module, toolType )
-                extraInfoAlg.addTool( toolClass, toolName )
-                toolInstance = getattr( extraInfoAlg, toolName )
-                for property,value in itool.iteritems() :
-                    if property == "Type" : continue
-                    setattr( toolInstance, property, value)
-                toolNames += [ toolType + '/' + toolName ]
+                toolClass = getattr(module, toolType)
+                extraInfoAlg.addTool(toolClass, toolName)
+                toolInstance = getattr(extraInfoAlg, toolName)
+                for property,value in itool.iteritems():
+                    if property == "Type":
+                        continue
+                    setattr(toolInstance, property, value)
+                toolNames += [toolType + '/' + toolName]
             extraInfoAlg.Tools = toolNames
             self._members.append(extraInfoAlg)
 
-        if self.RelatedInfoTools != None :
+        if self.RelatedInfoTools is not None:
             self.addRelatedInfo()
-            if self.RelatedInfoFilter :
-                if hasattr(type(self.RelatedInfoFilter), "CloneFilteredParticles") : 
+            if self.RelatedInfoFilter:
+                if hasattr(type(self.RelatedInfoFilter), "CloneFilteredParticles"):
                     log.debug("Setting CloneFilteredParticles = True for RelatedInfoFilter %s " % self.RelatedInfoFilter.name() )
                     self.RelatedInfoFilter.CloneFilteredParticles = True
                 self._members.append( self.RelatedInfoFilter )
@@ -572,19 +577,18 @@ class StrippingLine(object):
                 self.addRelatedInfo()
 
         # Add flavour tagging tool to the end of line sequence if needed
-        if self._EnableFlavourTagging :
-            if not self.outputLocation() or self.outputLocation() == "" :
+        if self._EnableFlavourTagging:
+            if not self.outputLocation() or self.outputLocation() == "":
                 raise AttributeError, "Line %s does not have output, cannot do flavour tagging" % self.name()
             btag = BTagging("BTag_"+self.name(), Inputs = [ self.outputLocation() ] )
             self._members.append(btag)
 
-        if self._members :
-
-            filterSeq = GaudiSequencer( filterName( line,'Stripping' ), 
-                                        Members = self._members, 
-                                        OutputLevel = WARNING )
+        if self._members:
+            filterSeq = GaudiSequencer(filterName(line,'Stripping'),
+                                       Members=self._members, 
+                                       OutputLevel=WARNING)
 
-            mdict.update( { 'Filter1' : filterSeq } )
+            mdict.update({'Filter1': filterSeq})
 
         #print self._members
 
@@ -598,7 +602,7 @@ class StrippingLine(object):
         # put upper limit on combinatorics
         if self.MaxCandidates == "Override" : self.MaxCandidates = None
         if self.MaxCombinations == "Override" : self.MaxCombinations = None
-        if self.MaxCandidates != None or self.MaxCandidates != None :
+        if self.MaxCandidates is not None or self.MaxCandidates is not None:
             limitCombinatorics( self._configurable,
                                 MaxCandidates = self.MaxCandidates,
                                 MaxCombinations = self.MaxCombinations,
@@ -610,41 +614,41 @@ class StrippingLine(object):
         return self._configurable
 
     # Add related info tools if needed
-    def addRelatedInfo( self ) :
+    def addRelatedInfo(self):
 
-        if self.RelatedInfoTools :
+        if self.RelatedInfoTools:
 
             log.debug( "Add RelatedInfo tools for output location "+ self.outputLocation() )
 
             toolNum = 0
-            for itool in self.RelatedInfoTools :
+            for itool in self.RelatedInfoTools:
 
                 toolNum += 1
 
-                if 'Locations' in itool.keys() or 'RecursionLevel' in itool.keys() : 
+                if 'Locations' in itool.keys() or 'RecursionLevel' in itool.keys():
                     raise Exception("\n"+self.name()+": Old-style syntax for RelatedInfoTools is specified. Use \'DaughterLocations\' dictionary instead!\n")
 
                 output_basename = self.outputLocation().split("/")[-2]
                 relatedInfoAlg = AddRelatedInfo('RelatedInfo%d_%s' % ( toolNum, output_basename ) )
                 if 'TopSelection' in itool.keys() : # and 'Locations' in itool.keys() :
                     relatedInfoAlg.Inputs = self.selectionsToLocations( [ itool['TopSelection'] ] )
-                else :
+                else:
                     relatedInfoAlg.Inputs = [ "/Event/" + self.outputLocation() ]
 
-                if 'DaughterLocations' in itool.keys() :
+                if 'DaughterLocations' in itool.keys():
                     relatedInfoAlg.DaughterLocations = itool['DaughterLocations']
-                if 'Location' in itool.keys() :
+                if 'Location' in itool.keys():
                     relatedInfoAlg.Location = itool['Location']
                 if 'DaughterLocations' not in itool.keys() and 'Location' not in itool.keys() :
                     raise Exception('\n'+self.name()+': Neither "Location" nor "DaughterLocations" are defined in RelatedInfo dictionary')
-                if 'IgnoreUnmatchedDescriptors' in itool.keys() :
+                if 'IgnoreUnmatchedDescriptors' in itool.keys():
                     relatedInfoAlg.IgnoreUnmatchedDescriptors = itool['IgnoreUnmatchedDescriptors']
 
                 toolType = itool["Type"]
 
                 # Extract the remaining properties specific for the tool from the overall list
-                toolprops = { }
-                for property,value in itool.iteritems() :
+                toolprops = {}
+                for property,value in itool.iteritems():
                     if property not in ["Type", "Location", "DaughterLocations", "TopSelection", "IgnoreUnmatchedDescriptors" ] : 
                         toolprops[property] = value
 
@@ -656,12 +660,13 @@ class StrippingLine(object):
 
                 # Get the entry in the cache map for thios type of tool
                 toolcache = globals()["relatedInfoCache"]
-                if toolType not in toolcache.keys() : toolcache[toolType] = { "ToolNum" : 1, "Tools" : { } }
+                if toolType not in toolcache.keys():
+                    toolcache[toolType] = {"ToolNum": 1, "Tools":{}}
                 configmap = toolcache[toolType]
 
                 # Does an instance with the exact configuration requested already exist ?
                 toolName = "UNDEFINED"
-                if propkey in configmap["Tools"].keys() :
+                if propkey in configmap["Tools"].keys():
                     
                     # Just reuse the existing tool
                     toolName = configmap["Tools"][propkey]
@@ -670,8 +675,8 @@ class StrippingLine(object):
                     # need to configure a new tool
 
                     # Get instance class type
-                    module = __import__("Configurables", globals(), locals(), [ toolType ] )
-                    ToolClass = getattr( module, toolType )
+                    module = __import__("Configurables", globals(), locals(), [toolType])
+                    ToolClass = getattr(module, toolType)
 
                     # Construct global name
                     toolName = toolType+"_"+str(configmap["ToolNum"])
@@ -680,11 +685,11 @@ class StrippingLine(object):
                     configmap["ToolNum"] += 1
 
                     # make an instance owned by tool svc, i.e. public
-                    toolInstance = ToolClass( "ToolSvc." + toolName )
+                    toolInstance = ToolClass("ToolSvc." + toolName)
 
                     # set options
-                    for property,value in toolprops.iteritems() :
-                        setattr( toolInstance, property, value )
+                    for property, value in toolprops.iteritems():
+                        setattr(toolInstance, property, value)
 
                     # Save toolname in the cache map
                     configmap["Tools"][propkey] = toolName
@@ -700,35 +705,36 @@ class StrippingLine(object):
                 # add algorithm to the members to run
                 self._members.append(relatedInfoAlg)
 
-    def filterMembers( self ) :
+    def filterMembers(self):
         _members = GaudiSequencer( filterName ( self.subname(), 'Stripping' ) ).Members
 
-        while True :
+        while True:
             _foundSequencer = False
             _flattenedMembers = []
-            for i in _members :
-                if GaudiSequencer is type(i) :
+            for i in _members:
+                if GaudiSequencer is type(i):
                     _flattenedMembers += i.Members
                     _foundSequencer = True
-                else :
-                    _flattenedMembers += [ i ]
+                else:
+                    _flattenedMembers += [i]
             _members = _flattenedMembers
-            if not _foundSequencer : break
+            if not _foundSequencer:
+                break
 
-        log.debug( "FilterMembers for line %s : " % self.name() )
-        log.debug( _members )
+        log.debug("FilterMembers for line %s : " % self.name())
+        log.debug(_members)
 
         return _members
 
-    def subname   ( self ) :
+    def subname(self):
         """ 'Sub-name' of the Stripping line  """
-        return            self._name
+        return self._name
     ## Full name of Stripping line
-    def name      ( self ) :
+    def name(self):
         """ Full name of Stripping Line """
         return 'Stripping%s' % self._name
     ## the actual type of Stripping Line
-    def type      ( self ) :
+    def type(self):
         """ The actual type of StrippingLine Line """
         return StrippingLine
 
@@ -739,13 +745,13 @@ class StrippingLine(object):
     #  >>> line = Hlt2Line ( .... )
     #  >>> conf = line.configurable()
     #  @endcode
-    def configurable ( self ) :
+    def configurable (self):
         return self._configurable
 
-    def decReportLocation ( self ) :
+    def decReportLocation (self):
         return self.fullHDRLocation
 
-    def outputLocation ( self ) :
+    def outputLocation (self):
         """
         Get the name of output TES location of the line
 
@@ -757,10 +763,10 @@ class StrippingLine(object):
 #            raise AttributeError, "The line %s does not define valid output " % self.subname()
         return self._outputloc
 
-    def prescale( self ) :
+    def prescale(self):
         return self._prescale
 
-    def get_constructor_args(self) :
+    def get_constructor_args(self):
         '''Get the constructor args for this line. Note that they're not deepcopied.'''
         constructorargs = []
         for arg, attr in StrippingLine.__constructorargs__ :
@@ -790,7 +796,7 @@ class StrippingLine(object):
 
 
         ## 1) clone the arguyments
-        args = deepcopy ( args )
+        args = deepcopy(args)
 
         ## 2) Explictly copy all major structural parameters
         constructorargs = deepcopy(dict(self.get_constructor_args()))
@@ -799,92 +805,92 @@ class StrippingLine(object):
         del constructorargs['args']
         constructorargs.update(args)
 
-        if constructorargs['algos'] and constructorargs['selection'] :
+        if constructorargs['algos'] and constructorargs['selection']:
             # If 'algos' is defined in the args for the cloned line use 'algos',
-            # else just use 'selection', as algos is set to [selection] in that 
-            # case. 
-            if 'algos' in args :
+            # else just use 'selection', as algos is set to [selection] in that
+            # case.
+            if 'algos' in args:
                 del constructorargs['selection']
-            else :
+            else:
                 del constructorargs['algos']
 
         # restore the original deepcopy behaviour...
-        if origMethod :
+        if origMethod:
             copy._deepcopy_dispatch[types.MethodType] = origMethod
-        else :
+        else:
             del copy._deepcopy_dispatch[types.MethodType]
 
         ## 3) Check for forbidden arguments
         _other = {} # the rest (probably reconfiguration of members)
         _myslots_, _myattrs_ = zip(*StrippingLine.__constructorargs__)
-        for key in args :
+        for key in args:
             # Should this be StrippingAlg rather than GaudiSequencer? 
             # The args are passed to a StrippingAlg in the end. 
-            if key in GaudiSequencer.__slots__ or key in _myslots_ : 
+            if key in GaudiSequencer.__slots__ or key in _myslots_: 
                 continue
-            else : 
+            else: 
                 _other [key] = args[key]
 
         # unknown parameters/arguments
-        if _other :
+        if _other:
             raise AttributeError, 'Invalid attributes are detected: %s'%_other
 
         return StrippingLine ( **constructorargs )
 
-    def check_hlt_filters(self, hlt1lines, hlt2lines) :
+    def check_hlt_filters(self, hlt1lines, hlt2lines):
         '''Check what HLT line names the HLT filters for this line match,
         given the list of HLT1 and HLT2 line names. Prints a warning if there's 
         no match for a given filter.'''
         checks = []
-        if self._HLT :
+        if self._HLT:
             hltexprs = self._extract_hlt_exprs(self._HLT)
             checks.append([hltexprs, hlt1lines + hlt2lines])
-        if self._HLT1 :
+        if self._HLT1:
             hlt1exprs = self._extract_hlt_exprs(self._HLT1)
             checks.append([hlt1exprs, hlt1lines])
-        if self._HLT2 :
+        if self._HLT2:
             hlt2exprs = self._extract_hlt_exprs(self._HLT2)
             checks.append([hlt2exprs, hlt2lines])
-        for alg in self._members :
-            if hasattr(alg, 'TisTosSpecs') :
+        for alg in self._members:
+            if hasattr(alg, 'TisTosSpecs'):
                 exprs = self._extract_hlt_exprs('"' + '" "'.join(alg.TisTosSpecs.keys()) + '"')
                 checks.append([exprs, hlt1lines + hlt2lines])
-            for attr in 'Code', 'CombinationCut', 'MotherCut' :
-                if hasattr(alg, attr) and alg.isPropertySet(attr) :
+            for attr in 'Code', 'CombinationCut', 'MotherCut':
+                if hasattr(alg, attr) and alg.isPropertySet(attr):
                     exprs = self._extract_hlt_exprs(getattr(alg, attr))
-                    if exprs :
+                    if exprs:
                         checks.append([exprs, hlt1lines + hlt2lines])
-            if hasattr(alg, 'DaughtersCuts') and alg.isPropertySet(attr) :
+            if hasattr(alg, 'DaughtersCuts') and alg.isPropertySet(attr):
                 exprs = self._extract_hlt_exprs('"' + '" "'.join(alg.DaughtersCuts.values()) + '"')
-                if exprs :
+                if exprs:
                     checks.append([exprs, hlt1lines + hlt2lines])
         matches = {}
-        for exprs, lines in checks :
-            for expr in exprs :
-                linematches = filter(lambda line : re.match(expr, line), 
+        for exprs, lines in checks:
+            for expr in exprs:
+                linematches = filter(lambda line: re.match(expr, line), 
                                      lines)
                 matches[expr] = linematches
-                if not linematches :
-                    print 'WARNING: For line', self.name(), 'trigger requirement', \
-                        expr, 'doesn\'t match any trigger line!'
+                if not linematches:
+                    print('WARNING: For line' + self.name() + 'trigger requirement' +
+                          expr + 'doesn\'t match any trigger line!')
         return matches
 
-    def _extract_hlt_exprs(self, code) :
+    def _extract_hlt_exprs(self, code):
         '''Extract the HLT line names/regexs from one of the HLT filters of this line.'''
-        if isinstance(code, (tuple, list)) :
+        if isinstance(code, (tuple, list)):
             return self._extract_hlt_exprs(code[0])
-        if isinstance(code, dict) :
+        if isinstance(code, dict):
             return self._extract_hlt_exprs(code['Code'])
         matches = []
-        for pattern in "'([^']+?)'", '"([^"]+?)"' :
+        for pattern in "'([^']+?)'", '"([^"]+?)"':
             matches += re.findall(pattern, code)
         trigs = []
         decpattern = '(Hlt.+?)Decision'
-        for match in matches :
+        for match in matches:
             trigs += re.findall(decpattern, match)
         return trigs
     
-    def python_doc(self) :
+    def python_doc(self):
         '''Get a dict of doc for the python readable stripping documentation.'''
 
         doc = dict(self.get_constructor_args())
@@ -892,28 +898,28 @@ class StrippingLine(object):
 
         doc['outputlocation'] = self.outputLocation()
 
-        if self.selection() :
+        if self.selection():
             doc['decaydescriptors'] = self.selection().decayDescriptors()
             doc['topdecaydescriptors'] = self.selection().topDecayDescriptors()
             doc['decayheads'] = self.selection().decayHeads()
-        else :            
+        else:            
             doc['decaydescriptors'] = []
             doc['topdecaydescriptors'] = []
             doc['decayheads'] = []
         return doc
 
-def _stringdoc(obj) :
+def _stringdoc(obj):
     '''Recursively change selection objects for their name in a list or dict.'''
-    if isinstance(obj, list) :
-        for i, thing in enumerate(obj) :
-            if hasattr(thing, 'name') :
+    if isinstance(obj, list):
+        for i, thing in enumerate(obj):
+            if hasattr(thing, 'name'):
                 obj[i] = thing.name()
-            elif isinstance(thing, (list, dict)) :
+            elif isinstance(thing, (list, dict)):
                 _stringdoc(thing)
-    elif isinstance(obj, dict) :
-        for key, thing in obj.items() :
-            if hasattr(thing, 'name') :
+    elif isinstance(obj, dict):
+        for key, thing in obj.items():
+            if hasattr(thing, 'name'):
                 obj[key] = thing.name()
-            elif isinstance(thing, (list, dict)) :
+            elif isinstance(thing, (list, dict)):
                 _stringdoc(thing)
                 
diff --git a/Phys/StrippingConf/python/StrippingConf/StrippingStream.py b/Phys/StrippingConf/python/StrippingConf/StrippingStream.py
old mode 100755
new mode 100644
index 69f9bd0a539d6829d16ea93be127ddc507e27a99..d1487d95a3085b1fb7300c5fe28ce411b8010808
--- a/Phys/StrippingConf/python/StrippingConf/StrippingStream.py
+++ b/Phys/StrippingConf/python/StrippingConf/StrippingStream.py
@@ -1,6 +1,6 @@
 #!/usr/bin/env python
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -14,50 +14,49 @@
 # StrippingStream
 #
 
-__all__ = ( 
-	    'StrippingStream'
-	  )
+__all__ = ('StrippingStream')
 
-from Gaudi.Configuration import *
-from Gaudi.Configuration import GaudiSequencer, Sequencer, Configurable
-from Configurables import LHCbConfigurableUser
+from Gaudi.Configuration import log, GaudiSequencer
+from Gaudi.Configuration import WARNING
 from copy import copy
 
-class StrippingStream ( object ) :
 
-    def __init__ ( self,
-                   name = 'StrippingStream',
-                   Lines =  [],                                    # List of stream lines
-                   BadEventSelection = "Override",                 # Bad event selection algo
-                                                                   # By default, it will be 
-                                                                   # overridden in StrippingConf, 
-                                                                   # but can be set to None here
-                                                                   # to cancel bad event check
-
-                   AcceptBadEvents = None,                         # If None, will be overridden 
-                                                                   # in StrippingConf
-		               MaxCandidates = "Override", 
-		               MaxCombinations = "Override", 
-		               TESPrefix = None
-                 ) :
+class StrippingStream(object):
+    def __init__(self,
+                 name='StrippingStream',
+                 Lines=[],                                    # List of stream lines
+                 BadEventSelection="Override",                # Bad event selection algo
+                                                              # By default, it will be
+                                                              # overridden in StrippingConf,
+                                                              # but can be set to None here
+                                                              # to cancel bad event check
+                 AcceptBadEvents=None,                        # If None, will be overridden
+                                                              # in StrippingConf
+                 MaxCandidates="Override",
+                 MaxCombinations="Override",
+                 TESPrefix=None
+                 ):
 
         self._name = name
 
         self.lines = []
         for line in Lines:
-          if line.prescale() > 0:
-            self.lines += [line]
-          else:
-            log.warning('Line '+line.name()+' has prescale <= 0, it will be removed from stream '+self.name())
+            if line.prescale() > 0:
+                self.lines += [line]
+            else:
+                log.warning('Line '+line.name() +
+                            ' has prescale <= 0, it will be removed from stream ' +
+                            self.name()
+                            )
 
-        for line in Lines : 
-    	    line.declareAppended()
+        for line in Lines:
+            line.declareAppended()
 
         self.algs = []
         self.seq = None
         self.streamLine = None                   # Line with OR of all stream lines, created in createConfigurables()
         self.eventSelectionLine = None           # Line to mark bad events, created in createConfigurables()
-        self.goodEventFilter    = None           # filter to reject bad events
+        self.goodEventFilter = None              # filter to reject bad events
         self.BadEventSelection = BadEventSelection
         self.AcceptBadEvents = AcceptBadEvents
         self.MaxCandidates = MaxCandidates
@@ -65,46 +64,48 @@ class StrippingStream ( object ) :
         self.TESPrefix = TESPrefix               # Prefix for DecReports location, configured when appending stream
         self.HDRLocation = 'Phys/DecReports'     # DecReports location, configured when appending to StrippingConf
 
-    def name(self) :
+    def name(self):
         return self._name
 
-    def clone(self, name) : 
-        return StrippingStream(name, Lines = copy(self.lines), 
-	                       BadEventSelection = self.BadEventSelection, 
-	                       AcceptBadEvents = self.AcceptBadEvents, 
-	                       MaxCandidates = self.MaxCandidates, 
-	                       MaxCombinations = self.MaxCombinations)
-
-    def appendLines (self, lines) : 
-        for line in lines : 
+    def clone(self, name):
+        return StrippingStream(name,
+                               Lines=copy(self.lines),
+                               BadEventSelection=self.BadEventSelection,
+                               AcceptBadEvents=self.AcceptBadEvents,
+                               MaxCandidates=self.MaxCandidates,
+                               MaxCombinations=self.MaxCombinations
+                               )
+
+    def appendLines(self, lines):
+        for line in lines:
             self.lines.append(line)
             line.declareAppended()
 
-    def createConfigurables(self) :
-        from Configurables import StrippingCheck
-
+    def createConfigurables(self):
         # Create configurables
 
-        if self.TESPrefix == None : self.TESPrefix = self._name
+        if self.TESPrefix is None:
+            self.TESPrefix = self._name
 
         from StrippingLine import StrippingLine
         # If the BadEventsSelection was not given neither in StrippingConf nor in StrippingStream
 
-        if self.BadEventSelection == "Override" :
+        if self.BadEventSelection == "Override":
             self.BadEventSelection = None
 
         # Make the line to mark bad events (those satisfying BadEventSelection)
 
-        if self.BadEventSelection != None :
+        if self.BadEventSelection is not None:
 
             # create the line that select bad events
             self.eventSelectionLine = StrippingLine("Stream"+self.name()+"BadEvent",
-                                                    checkPV = False, 
-                                                    algos = [ self.BadEventSelection ] )
-            self.eventSelectionLine.createConfigurable( self.TESPrefix, self.HDRLocation )
+                                                    checkPV=False,
+                                                    algos=[self.BadEventSelection]
+                                                    )
+            self.eventSelectionLine.createConfigurable(self.TESPrefix, self.HDRLocation)
             self.eventSelectionLine.declareAppended()
 
-            if self.AcceptBadEvents != False :
+            if self.AcceptBadEvents is not False:
 
                 # Need to think a bit more on this
                 log.error("NOT POSSIBLE TO ACCEPT BAD EVENTS WITH THE CURRENT CONFIGURATION OF STRIPPINGCONF!!!")
@@ -112,68 +113,70 @@ class StrippingStream ( object ) :
 
             else:
 
-                # Create a filter that negates the bad events (select good events). 
+                # Create a filter that negates the bad events (select good events).
                 # This filter will be inserted at the beginning of the filters run by all the lines.
                 from Configurables import LoKi__VoidFilter as Filter
-                self.goodEventFilter = Filter( "StrippingGoodEventCondition"+self.name() ,
-                                               Code      = " ALG_EXECUTED('%s') & ~ALG_PASSED('%s') "
-                                               % (self.eventSelectionLine.name(), self.eventSelectionLine.name()) ,
-                                               Preambulo = [ "from LoKiHlt.algorithms import *" ] )
-
-
-        for line in self.lines : 
-            if line.MaxCandidates == "Override" : 
+                self.goodEventFilter = Filter("StrippingGoodEventCondition"+self.name(),
+                                              Code=" ALG_EXECUTED('%s') & ~ALG_PASSED('%s') "
+                                              % (self.eventSelectionLine.name(), self.eventSelectionLine.name()),
+                                              Preambulo=["from LoKiHlt.algorithms import *"]
+                                              )
+
+        for line in self.lines:
+            if line.MaxCandidates == "Override":
                 line.MaxCandidates = self.MaxCandidates
-            if line.MaxCombinations == "Override" : 
+            if line.MaxCombinations == "Override":
                 line.MaxCombinations = self.MaxCombinations
 
-            if self.BadEventSelection != None :
-                if not self.AcceptBadEvents != False :
+            if self.BadEventSelection is not None:
+                if self.AcceptBadEvents is not True:
                     # inserting filter for good events inside the lines
-                    if not "StrippingGoodEventCondition" in line._members[0].name() :
-                      line._members.insert(0,self.goodEventFilter)
+                    if "StrippingGoodEventCondition" not in line._members[0].name():
+                        line._members.insert(0, self.goodEventFilter)
 
-            if line.prescale() > 0. : 
-                line.createConfigurable( self.TESPrefix, self.HDRLocation )
-                log.debug("ADDING configurable " + line.configurable().name() + "to stream " + self.name() )
+            if line.prescale() > 0.:
+                line.createConfigurable(self.TESPrefix, self.HDRLocation)
+                log.debug("ADDING configurable " + line.configurable().name() + "to stream " + self.name())
                 self.algs.append(line.configurable())
-
-            else : 
-                line.RequiredRawEvents = None #forcing None rawevents to avoid (harmless) errors from the DSTWriter
-                log.warning("Line " + line.name() + " has zero prescale, skipping" )
+            else:
+                line.RequiredRawEvents = None  # forcing None rawevents to avoid (harmless) errors from the DSTWriter
+                log.warning("Line " + line.name() + " has zero prescale, skipping")
 
         # Make the line for stream decision (OR of all stream lines)
 
         linesSeq = GaudiSequencer("StrippingStreamSeq"+self.name(),
-                                  ModeOR = True,
-                                  #ShortCircuit = False,
-                                  OutputLevel = WARNING, 
-                                  Members = self.algs)
-
-        self.streamLine = StrippingLine("Stream"+self.name(), checkPV = False, algos = [ linesSeq ] )
-        ## I think it is redundant, otherwise if it comes out it is needed
-        ## uncomment the following lines
-        #if self.BadEventSelection != None :
-        #    if not self.AcceptBadEvents != False :
-        #        if not "StrippingGoodEventCondition" in self.streamLine._members[0].name() :
+                                  ModeOR=True,
+                                  # ShortCircuit=False,
+                                  OutputLevel=WARNING,
+                                  Members=self.algs)
+
+        self.streamLine = StrippingLine("Stream"+self.name(),
+                                        checkPV=False,
+                                        algos=[linesSeq])
+        # I think it is redundant, otherwise if it comes out it is needed
+        # uncomment the following lines
+        # if self.BadEventSelection != None:
+        #    if not self.AcceptBadEvents != False:
+        #        if not "StrippingGoodEventCondition" in self.streamLine._members[0].name():
         #            self.streamLine._members.insert(0,self.goodEventFilter)
-        self.streamLine.createConfigurable( self.TESPrefix, self.HDRLocation )
+        self.streamLine.createConfigurable(self.TESPrefix, self.HDRLocation)
         self.streamLine.declareAppended()
 
-    def sequence ( self ) :
-        if self.seq == None :
+    def sequence(self):
+        if self.seq is None:
 
-            if self.eventSelectionLine == None:
+            if self.eventSelectionLine is None:
                 # We don't care of BadEvents, thus not insert bad event line in the stream sequence
                 self.seq = GaudiSequencer("StrippingSequenceStream"+self.name(),
-                                          ModeOR = True,
-                                          ShortCircuit = False,
-                                          OutputLevel = WARNING,
-                                          Members =  self.algs + [ self.streamLine.configurable() ] )
+                                          ModeOR=True,
+                                          ShortCircuit=False,
+                                          OutputLevel=WARNING,
+                                          Members=self.algs + [self.streamLine.configurable()]
+                                          )
 
             else:
 
-                if self.AcceptBadEvents != False :
+                if self.AcceptBadEvents:
 
                     # Need to think a bit more on this
                     log.error("NOT POSSIBLE TO ACCEPT BAD EVENTS WITH THE CURRENT CONFIGURATION OF STRIPPINGCONF!!!")
@@ -183,96 +186,100 @@ class StrippingStream ( object ) :
                     # since we care of bad events we have to protect the execution of lines and stream-line
                     # inserting them in a sequence with ModeOR = True and ShortCircuit = False.
                     lineSeq = GaudiSequencer("StrippingProtectedSequence"+self.name(),
-                                             ModeOR = True,
-                                             ShortCircuit = False,
-                                             OutputLevel = WARNING,
-                                             Members = self.algs + [ self.streamLine.configurable() ] )
+                                             ModeOR=True,
+                                             ShortCircuit=False,
+                                             OutputLevel=WARNING,
+                                             Members=self.algs + [self.streamLine.configurable()]
+                                             )
 
                     # We need a badEventSeq with IgnoreFilterPassed = True in order to always run the protected sequence with
                     # lines and stream-lines
                     badEventSeq = GaudiSequencer("StrippingBadEventSequence"+self.name(),
-                                                 Members = [ self.eventSelectionLine.configurable() ],
-                                                 OutputLevel = WARNING,
-                                                 IgnoreFilterPassed = True)
+                                                 Members=[self.eventSelectionLine.configurable()],
+                                                 OutputLevel=WARNING,
+                                                 IgnoreFilterPassed=True)
 
-                    # The final sequence is an AND sequence of the badEventSeq and the lines + stream-lines
-                    #  algorithms (protected sequence)
+                    # The final sequence is an AND sequence of the badEventSeq
+                    #  and the lines + stream-lines algorithms (protected sequence)
                     self.seq = GaudiSequencer("StrippingSequenceStream"+self.name(),
-                                              OutputLevel = WARNING,
-                                              Members = [ badEventSeq, lineSeq ] )
+                                              OutputLevel=WARNING,
+                                              Members=[badEventSeq, lineSeq]
+                                              )
 
         return self.seq
 
-
-    def outputLocations (self) : 
+    def outputLocations(self):
         outputList = []
-        for i in self.lines :
+        for i in self.lines:
             output = i.outputLocation()
-            if output : 
+            if output:
                 outputList.append(output)
         return outputList
 
-
-    def filterMembers( self ) : 
+    def filterMembers(self):
         _members = []
-        for line in self.lines : 
+        for line in self.lines:
             lineMembers = line.filterMembers()
-            for i in lineMembers : 
-                if i not in _members : _members.append(i) 
+            for i in lineMembers:
+                if i not in _members:
+                    _members.append(i)
         return _members
 
-
-    def getRequiredRawEvents(self) :
-        rawEvents = { }
-        for line in self.lines : 
-            if ( line.RequiredRawEvents != None ) :
-                rawEvents[line.name()] = [ "/Event/"+r+"/RawEvent#1" for r in line.RequiredRawEvents ]
+    def getRequiredRawEvents(self):
+        rawEvents = {}
+        for line in self.lines:
+            if (line.RequiredRawEvents is not None):
+                rawEvents[line.name()] = ["/Event/" + r + "/RawEvent#1" for r in line.RequiredRawEvents]
         return rawEvents
 
+    def checkRawEventRequests(self):
+        for line in self.lines:
+            if line.RequiredRawEvents is not None:
+                log.debug("Stream='"+self.name() + "' Line='" + line.name() +
+                          "' Requests RawEvents " + str(line.RequiredRawEvents))
 
-    def checkRawEventRequests(self) :
-        for line in self.lines : 
-            if line.RequiredRawEvents != None :
-                log.debug("Stream='"+self.name()+"' Line='"+line.name()+
-                          "' Requests RawEvents "+str(line.RequiredRawEvents))
-
-    def checkMDSTFlag(self) :
-        for line in self.lines :
-            if line.MDSTFlag :
-                log.debug("Stream='"+self.name()+"' Line='"+line.name()+
+    def checkMDSTFlag(self):
+        for line in self.lines:
+            if line.MDSTFlag:
+                log.debug("Stream='" + self.name() + "' Line='" + line.name() +
                           "' Requests to go to MDST.DST")
 
-    def checkFlavourTagging(self,disableFT=False,verbose=False) :
-        for line in self.lines :
-            if line._EnableFlavourTagging :
-                if verbose : log.debug("Stream='"+self.name()+"' Line='"+line.name()+
-                                         "' Requests to run FlavourTagging")
+    def checkFlavourTagging(self, disableFT=False, verbose=False):
+        for line in self.lines:
+            if line._EnableFlavourTagging:
+                if verbose:
+                    log.debug("Stream='" + self.name() + "' Line='" + line.name() +
+                              "' Requests to run FlavourTagging")
                 if disableFT:
                     line._EnableFlavourTagging = False
-                    log.warning("Stream='"+self.name()+"' Line='"+line.name()+"' Requests Flavor Tagging but is not assigned to a micro-dst stream, Flavour Tagging has been disabled")
+                    log.warning("Stream='" + self.name() + "' Line='" +
+                                line.name() +
+                                "' Requests Flavor Tagging but is not assigned to a micro-dst stream, Flavour Tagging has been disabled")  # noqa
 
-    def checkPVRefit(self) :
-        for line in self.lines :
+    def checkPVRefit(self):
+        for line in self.lines:
             sel = line.selection()
-            #for algo in line._algos:
-            if sel != None:
+            # for algo in line._algos:
+            if sel is not None:
                 props = sel.algorithm().getProperties()
                 if props.has_key('ReFitPVs'):
-                    if props['ReFitPVs'] == True:
-                        log.warning("Stream='"+self.name()+"' Line='"+line.name()+
-                                    "' Requests to refit the PV")
+                    if props['ReFitPVs']:
+                        log.warning("Stream='" + self.name() + "' Line='" +
+                                    line.name() + "' Requests to refit the PV")
 
-    def getRelatedInfoLocations(self) : 
+    def getRelatedInfoLocations(self):
         locations = []
-        for line in self.lines : 
-            if line.RelatedInfoTools != None : 
-                for tool in line.RelatedInfoTools : 
-                    if 'Locations' in tool.keys() : 
+        for line in self.lines:
+            if line.RelatedInfoTools is not None:
+                for tool in line.RelatedInfoTools:
+                    if 'Locations' in tool.keys():
                         locs = tool['Locations']
-                        for part,loc in locs.iteritems() : 
-                            if loc not in locations : locations += [ loc ]
-                    if 'Location' in tool.keys() : 
+                        for part, loc in locs.iteritems():
+                            if loc not in locations:
+                                locations += [loc]
+                    if 'Location' in tool.keys():
                         loc = tool['Location']
-                        if loc not in locations : locations += [ loc ]
-        log.info("RelatedInfoLocations for stream %s: %s" % (self.name(), str(locations)) )
+                        if loc not in locations:
+                            locations += [loc]
+        log.info("RelatedInfoLocations for stream %s: %s" % (self.name(), str(locations)))
         return locations
diff --git a/Phys/StrippingConf/python/StrippingConf/Utils.py b/Phys/StrippingConf/python/StrippingConf/Utils.py
index dc34518f1e7463db91405011180967b92d34e000..bca422c6bfdee314690ef1d0a2e853af81f77afa 100644
--- a/Phys/StrippingConf/python/StrippingConf/Utils.py
+++ b/Phys/StrippingConf/python/StrippingConf/Utils.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -19,17 +19,22 @@ from Gaudi.Configuration import log
 
 def _limitCombinatoricsMaxCandidates(configurable, MaxCandidates,
                                      MaxCombinations, force, incidentName):
-    '''Limit combinatorics of a configurable assuming it has MaxCandidates,
-    StopAtMaxCandidates, MaxCombinations, StopAtMaxCombinations and StopIncidentType attributes.'''
+    '''
+    Limit combinatorics of a configurable assuming it has MaxCandidates,
+    StopAtMaxCandidates, MaxCombinations, StopAtMaxCombinations
+    and StopIncidentType attributes.
+    '''
 
     didsomething = False
-    if (force or not configurable.isPropertySet('MaxCandidates')) and None != MaxCandidates:
+    if (force or not configurable.isPropertySet('MaxCandidates')) and \
+            (MaxCandidates is not None):
         log.debug("Forcing MaxCandidates settings for " + configurable.name())
         configurable.MaxCandidates = MaxCandidates
         configurable.StopAtMaxCandidates = True
         didsomething = True
-    if (force or not configurable.isPropertySet('MaxCombinations')) and None != MaxCombinations:
-        log.debug("Forcing MaxCombinations settings for " + configurable.name())
+    if (force or not configurable.isPropertySet('MaxCombinations')) and \
+            (MaxCombinations is not None):
+        log.debug("Forcing MaxCombinations settings for " + configurable.name())  # noqa
         configurable.MaxCombinations = MaxCombinations
         configurable.StopAtMaxCombinations = True
         didsomething = True
@@ -38,11 +43,18 @@ def _limitCombinatoricsMaxCandidates(configurable, MaxCandidates,
     return didsomething
 
 
-def _limitCombinatoricsMaxParticles(configurable, MaxCandidates, force, incidentName):
-    '''Limit combinatorics for a configurable assuming it's got MaxParticles & StopIncidentType
-    attributes.'''
+def _limitCombinatoricsMaxParticles(configurable,
+                                    MaxCandidates,
+                                    force,
+                                    incidentName):
+    '''
+    Limit combinatorics for a configurable
+    assuming it's got MaxParticles & StopIncidentType
+    attributes.
+    '''
 
-    if (force or not configurable.isPropertySet('MaxParticles')) and None != MaxCandidates:
+    if (force or not configurable.isPropertySet('MaxParticles')) and \
+            (MaxCandidates is not None):
         log.debug("Forcing MaxParticles settings for " + configurable.name())
         configurable.MaxParticles = MaxCandidates
         configurable.StopIncidentType = incidentName
@@ -82,9 +94,11 @@ def limitCombinatorics(configurable,
                        force,
                        incidentName='ExceedsCombinatoricsLimit'):
     """
-    - This function has the highest call counts. So it needs careful optimization.
-    - Because the action is reactive, it's best to order the case of most-probable
-      to the least-probable to exit the check as early as possible.
+    - This function has the highest call counts.
+      So it needs careful optimization.
+    - Because the action is reactive, it's best to order
+      the case of most-probable to the least-probable
+      to exit the check as early as possible.
     """
 
     # Check the name by string is MUCH FASTER than by class.
@@ -102,13 +116,22 @@ def limitCombinatorics(configurable,
                 conf, MaxCandidates, MaxCombinations, force, incidentName)
         return val
 
-    if classname in ('CombineParticles', 'DaVinci__N3BodyDecays', 'DaVinci__N4BodyDecays', 'DaVinci__N5BodyDecays'):
-        return _limitCombinatoricsMaxCandidates(configurable, MaxCandidates, MaxCombinations, force, incidentName)
+    if classname in ('CombineParticles',
+                     'DaVinci__N3BodyDecays',
+                     'DaVinci__N4BodyDecays',
+                     'DaVinci__N5BodyDecays'
+                     ):
+        return _limitCombinatoricsMaxCandidates(configurable,
+                                                MaxCandidates,
+                                                MaxCombinations,
+                                                force,
+                                                incidentName)
 
     if classname == 'StrippingAlg':
         val = False
         stages = ['Filter1']
-        for conf in [getattr(configurable, stage) for stage in stages if hasattr(configurable, stage)]:
+        for conf in [getattr(configurable, stage)
+                     for stage in stages if hasattr(configurable, stage)]:
             val |= limitCombinatorics(
                 conf, MaxCandidates, MaxCombinations, force, incidentName)
         if val:
@@ -116,15 +139,28 @@ def limitCombinatorics(configurable,
         return val
 
     if classname in ('SubPIDMMFilter', 'SubstitutePID'):
-        return _limitCombinatoricsMaxParticles(configurable, MaxCandidates, force, incidentName)
+        return _limitCombinatoricsMaxParticles(configurable,
+                                               MaxCandidates,
+                                               force,
+                                               incidentName)
 
     # Generic handling (slow)
-    if hasattr(type(configurable), 'StopAtMaxCandidates') and hasattr(type(configurable), 'MaxCandidates') and \
-            hasattr(type(configurable), 'StopAtMaxCombinations') and hasattr(type(configurable), 'MaxCombinations'):
-        return _limitCombinatoricsMaxCandidates(configurable, MaxCandidates, MaxCombinations, force, incidentName)
-
-    if hasattr(configurable, 'MaxParticles') and hasattr(configurable, 'StopIncidentType'):
-        return _limitCombinatoricsMaxParticles(configurable, MaxCandidates, force, incidentName)
+    if hasattr(type(configurable), 'StopAtMaxCandidates') and \
+            hasattr(type(configurable), 'MaxCandidates') and \
+            hasattr(type(configurable), 'StopAtMaxCombinations') and \
+            hasattr(type(configurable), 'MaxCombinations'):
+        return _limitCombinatoricsMaxCandidates(configurable,
+                                                MaxCandidates,
+                                                MaxCombinations,
+                                                force,
+                                                incidentName)
+
+    if (hasattr(configurable, 'MaxParticles') and
+            hasattr(configurable, 'StopIncidentType')):
+        return _limitCombinatoricsMaxParticles(configurable,
+                                               MaxCandidates,
+                                               force,
+                                               incidentName)
 
     # Generic handling (slow)
     if hasattr(configurable, 'Members'):
@@ -135,5 +171,4 @@ def limitCombinatorics(configurable,
                 i, MaxCandidates, MaxCombinations, force, incidentName)
         return val
 
-    # log.warning('Not able to set MaxCandidates and MaxCombinations to algorithm '+str(type(configurable))+'/'+configurable.name())
     return False
diff --git a/Phys/StrippingConf/tests/test_strippingconf.py b/Phys/StrippingConf/tests/test_strippingconf.py
index bb4da0bf2096572b2b240b5a1acd07711fa5f142..4b99b243422a71f2e49cfea5f2869e5ba628fced 100755
--- a/Phys/StrippingConf/tests/test_strippingconf.py
+++ b/Phys/StrippingConf/tests/test_strippingconf.py
@@ -67,13 +67,13 @@ if '__main__' == __name__:
     message = ''
     summary = '\n'
     length = len(sorted(test_names,
-                        cmp=lambda x, y: cmp(len(y), len(x)))[0]) + 2
+                        cmp=lambda x, y: cmp(len(y), len(x)))[0]) + 2  # noqa
 
     for test in __tests:
         try:
             test[1]()
             message = 'PASS'
-        except:
+        except:  # noqa
             message = "FAIL"
         summary += test[0].ljust(length) + ':' + message.rjust(10) + '\n'
 
diff --git a/Phys/StrippingConf/tests/test_strippingline.py b/Phys/StrippingConf/tests/test_strippingline.py
index dab7945a246aaf2d385b15e64e38d8987f0e4c89..1aaaf9ac8c829d1be458e217d5c48b88a2d1473a 100644
--- a/Phys/StrippingConf/tests/test_strippingline.py
+++ b/Phys/StrippingConf/tests/test_strippingline.py
@@ -25,9 +25,9 @@ def test_instantiate_empty_line():
     line = StrippingLine('EmptyLine')
     assert line.name() == 'StrippingEmptyLine'
     assert line.subname() == 'EmptyLine'
-    assert line.isAppended() == False
-    assert line.outputLocation() == None
-    assert line.selection() == None
+    assert not line.isAppended()
+    assert line.outputLocation() is None
+    assert line.selection() is None
 
 
 def test_instantiate_from_Selection_object():
@@ -35,9 +35,9 @@ def test_instantiate_from_Selection_object():
     line = StrippingLine('SelectionLine', algos=[selection])
     assert line.name() == 'StrippingSelectionLine'
     assert line.subname() == 'SelectionLine'
-    assert line.isAppended() == False
+    assert not line.isAppended()
     assert line.outputLocation() == 'Phys/SelectionLine/Particles'
-    assert line.selection() != None
+    assert line.selection() is not None
     assert line.selection().outputLocation() == line.outputLocation()
 
 
@@ -56,10 +56,10 @@ def test_filterMembers():
     line = StrippingLine('FilterMembersTest', algos=[selection])
     assert line.name() == 'Stripping' + name
     assert line.subname() == name
-    assert line.isAppended() == False
+    assert not line.isAppended()
     assert line.outputLocation() == 'Phys/FilterMembersTest/Particles'
     stream = StrippingStream('stream', Lines=[line])
-    conf = StrippingConf('conf', Streams=[stream])
+    _ = StrippingConf('conf', Streams=[stream])
     assert [m.name() for m in line.filterMembers()] == ['checkPVmin1',
                                                         # 'SelFilterPhys_Selection_Particles',
                                                         'SELECT:Phys/Selection',
@@ -77,13 +77,13 @@ if '__main__' == __name__:
     message = ''
     summary = '\n'
     length = len(sorted(test_names,
-                        cmp=lambda x, y: cmp(len(y), len(x)))[0]) + 2
+                        cmp=lambda x, y: cmp(len(y), len(x)))[0]) + 2  # noqa
 
     for test in __tests:
         try:
             test[1]()
             message = 'PASS'
-        except:
+        except:  # noqa
             message = "FAIL"
         summary += test[0].ljust(length) + ':' + message.rjust(10) + '\n'
 
diff --git a/Phys/StrippingDoc/python/StrippingDoc/__init__.py b/Phys/StrippingDoc/python/StrippingDoc/__init__.py
index 3bb8f0d3032cd002c10d16fc86c398ff42fc0449..12029805466d2468694442dbf5beecb46a48a1db 100644
--- a/Phys/StrippingDoc/python/StrippingDoc/__init__.py
+++ b/Phys/StrippingDoc/python/StrippingDoc/__init__.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -9,55 +9,59 @@
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
 '''Python readable doc for the stripping.'''
-import os, glob, re
+import os
+import glob
+import re
 
-class StrippingDoc(object) :
+
+class StrippingDoc(object):
     '''Helper class to access the python stripping doc.'''
 
-    def __init__(self, version) :
+    def __init__(self, version):
         '''Get the doc for the given stripping version.'''
 
-        if isinstance(version, str) :
-            try :
-                self.module = __import__('StrippingDoc.' + version.lower(), fromlist = ['lines'])
-            except ImportError :
+        if isinstance(version, str):
+            try:
+                self.module = __import__('StrippingDoc.' + version.lower(), fromlist=['lines'])
+            except ImportError:
                 modules = []
-                for fname in sorted(glob.glob(os.path.join(os.environ['STRIPPINGDOCROOT'], 'python', 'StrippingDoc', 'stripping*.py'))) :
+                for fname in sorted(glob.glob(os.path.join(os.environ['STRIPPINGDOCROOT'], 'python', 'StrippingDoc', 'stripping*.py'))):
                     module = os.path.split(fname)[1][:-3]
                     modules.append(module[0].upper() + module[1:])
                 raise ValueError('No doc for version {0!r}. Known versions are:\n{1!r}'.format(version, modules))
         # Assume it's a module/class that has the desired attributes.
-        else :
+        else:
             self.module = version
 
-        # Could use 
+        # Could use
         # filter(lambda attr : not attr.startswith('_'), dir(self.module))
-        # so as not to have to maintain this list, but this checks that the given 
+        # so as not to have to maintain this list, but this checks that the given
         # object has the required attribues.
         for attr in 'DaVinciVersion', 'platform', 'TCK', 'datatype', 'CondDBtag', \
-                'DDDBtag', 'stepid', 'description' :
+                'DDDBtag', 'stepid', 'description':
             setattr(self, attr, getattr(self.module, attr))
 
         self.lines = {}
-        for name, line in self.module.lines.items() :
-            self.lines[name] = StrippingLineDoc(datatype = self.datatype, **line)
+        for name, line in self.module.lines.items():
+            self.lines[name] = StrippingLineDoc(datatype=self.datatype, **line)
 
-    def filter_lines(self, test) :
+    def filter_lines(self, test):
         '''Get lines for which the method 'test' returns True.'''
         return filter(test, self.lines.values())
 
-    def get_line(self, name) :
+    def get_line(self, name):
         '''Get the doc on the line of the given name.'''
-        try :
+        try:
             return self.lines[name]
-        except KeyError :
+        except KeyError:
             return None
 
-    def find_lines(self, pattern) :
+    def find_lines(self, pattern):
         '''Get the doc on lines whose name contains the given regex pattern'''
-        return self.filter_lines(lambda line : re.search(pattern, line.name))
+        return self.filter_lines(lambda line: re.search(pattern, line.name))
+
 
-def add_carets(Decay) :
+def add_carets(Decay):
     '''Add carets to a DecayDescriptor for DecayTreeTuple.'''
     # Add carets, except on the head particle, which should always be preceded by open bracket.
     Decay = re.sub('([^(]) ([A-Za-z])', '\\1 ^\\2', Decay)
@@ -65,79 +69,82 @@ def add_carets(Decay) :
     Decay = re.sub('([^|]) \\( ([A-Za-z])', '\\1 ^( \\2', Decay)
     return Decay
 
-class StrippingLineDoc(object) :
+
+class StrippingLineDoc(object):
     '''Helper class to access doc on a stripping line.'''
 
-    def __init__(self, **kwargs) :
+    def __init__(self, **kwargs):
         '''Takes the dict of info for a line stored in the stripping doc module.'''
-        for attr, val in kwargs.items() :
+        for attr, val in kwargs.items():
             setattr(self, attr, val)
 
-    def tuple_config(self, fulldescriptors = True) :
-        '''Get the configuration of a DecayTreeTuple instance for this line. If fulldescriptors = False,
+    def tuple_config(self, fulldescriptors=True):
+        '''
+        Get the configuration of a DecayTreeTuple instance for this line.
+        If fulldescriptors = False,
         just the top level decay descriptors will be used.'''
-        
-        if fulldescriptors :
+
+        if fulldescriptors:
             Decay = ' || '.join(self.decaydescriptors)
-        else :
+        else:
             Decay = ' || '.join(self.topdecaydescriptors)
         Decay = add_carets(Decay)
         Inputs = [self.outputlocation]
-        return dict(Inputs = Inputs, Decay = Decay)
+        return dict(Inputs=Inputs, Decay=Decay)
 
-    def related_info_config(self, stream = None) :
+    def related_info_config(self, stream=None):
         '''Get the configuration of a LoKi__Hybrid__TupleTool to read the output of the RelatedInfo tools
         of this line.'''
 
         stream = self._stream(stream)
 
         Variables = {}
-        config = dict(Variables = Variables)
-        if not self.RelatedInfoTools :
+        config = dict(Variables=Variables)
+        if not self.RelatedInfoTools:
             return config
-        for varinfo in self.RelatedInfoTools :
+        for varinfo in self.RelatedInfoTools:
             locations = []
-            if 'Location' in varinfo :
+            if 'Location' in varinfo:
                 locations.append(varinfo['Location'])
-            if 'DaughterLocations' in varinfo :
+            if 'DaughterLocations' in varinfo:
                 locations += varinfo['DaughterLocations'].values()
-            for loc in locations :
+            for loc in locations:
                 # The RELINFO functor seems to ignore RootInTES, so give it the full path.
                 location = '/'.join([self.root_in_TES(stream)] + self.outputlocation.split('/')[:-1] + [loc])
-                for var in varinfo['Variables'] :
+                for var in varinfo['Variables']:
                     Variables[loc + '_' + var] = 'RELINFO({0!r}, {1!r}, -999.)'.format(location, var)
         return config
 
-    def _stream(self, stream) :
-        if not stream :
-            stream = filter(lambda name : name.lower() not in ('ftag.dst', 'mdst.dst'), self.streams)[0]
+    def _stream(self, stream):
+        if not stream:
+            stream = filter(lambda name: name.lower() not in ('ftag.dst', 'mdst.dst'), self.streams)[0]
         return stream
-        
-    def root_in_TES(self, stream = None) :
+
+    def root_in_TES(self, stream=None):
         '''Get the RootInTES for reading the output of this line.'''
         stream = self._stream(stream)
         return '/Event' + ('/' + stream[:-5] if stream.lower().endswith('.mdst') else '')
 
-    def input_type(self, stream = None) :
+    def input_type(self, stream=None):
         '''Get the InputType for DaVinci.'''
         stream = self._stream(stream)
-        if stream.lower().endswith('.mdst') :
+        if stream.lower().endswith('.mdst'):
             return 'MDST'
         return 'DST'
 
-    def davinci_config(self, stream = None) :
+    def davinci_config(self, stream=None):
         '''Get the InputType, DataType, and RootInTES for DaVinci.'''
-        return dict(InputType = self.input_type(stream),
-                    DataType = self.datatype,
-                    RootInTES = self.root_in_TES(stream))
+        return dict(InputType=self.input_type(stream),
+                    DataType=self.datatype,
+                    RootInTES=self.root_in_TES(stream))
 
-    def decision_name(self) :
+    def decision_name(self):
         '''Get the decision name in the Stripping SelReports.'''
         return 'Stripping' + self.name + 'Decision'
 
-    def decision_filter_config(self) :
+    def decision_filter_config(self):
         '''Get the config for a LoKi__HDRFilter on this line.'''
         decname = self.decision_name()
-        return dict(Code = 'HLT_PASS({0!r})'.format(decname),
-                    Location = '/Event/Strip/Phys/DecReports',
-                    RootInTES = '/Event')
+        return dict(Code='HLT_PASS({0!r})'.format(decname),
+                    Location='/Event/Strip/Phys/DecReports',
+                    RootInTES='/Event')
diff --git a/Phys/StrippingNeuroBayes/options/TestBhh.py b/Phys/StrippingNeuroBayes/options/TestBhh.py
index 6cae795b862b20f794a458a792d07676f9313233..1fd6003a61c187efe3312fbd4275699feccbcc6f 100644
--- a/Phys/StrippingNeuroBayes/options/TestBhh.py
+++ b/Phys/StrippingNeuroBayes/options/TestBhh.py
@@ -8,28 +8,22 @@
 # granted to it by virtue of its status as an Intergovernmental Organization  #
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
-from os import environ
 from Configurables import AuditorSvc, ChronoAuditor
 from Configurables import LoKi__HDRFilter
 from Configurables import CondDB
 from Configurables import LoKi__Hybrid__TupleTool
-from Configurables import DecayTreeTuple
-from Configurables import CombineParticles
+from Configurables import DecayTreeTuple, CombineParticles
+from Configurables import MessageSvc, EventSelector
 from Configurables import DaVinci
 from PhysSelPython.Wrappers import SelectionSequence
-from PhysSelPython.Wrappers import MergedSelection
 from PhysSelPython.Wrappers import Selection, DataOnDemand
 from Configurables import StrippingNBBhh
-from Gaudi.Configuration import *
-
-from GaudiKernel.SystemOfUnits import MeV, GeV
 
 
 ########################################################################
 #
 # Bs -> KK
 #
-from Configurables import CombineParticles
 Bhh = CombineParticles("Bhh")
 Bhh.DecayDescriptor = "B_s0 -> K+ K-"
 Bhh.DaughtersCuts = {
diff --git a/Phys/StrippingNeuroBayes/options/TestNeuroBayes.py b/Phys/StrippingNeuroBayes/options/TestNeuroBayes.py
index 67095d7692cd5c7a25201f7760822ec830f8d421..a55c127041d6a6746369f684f0cbfc32f8dfe376 100644
--- a/Phys/StrippingNeuroBayes/options/TestNeuroBayes.py
+++ b/Phys/StrippingNeuroBayes/options/TestNeuroBayes.py
@@ -8,28 +8,23 @@
 # granted to it by virtue of its status as an Intergovernmental Organization  #
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
-from os import environ
 from Configurables import AuditorSvc, ChronoAuditor
 from Configurables import LoKi__HDRFilter
 from Configurables import CondDB
 from Configurables import LoKi__Hybrid__TupleTool
 from Configurables import DecayTreeTuple
+from Configurables import MessageSvc, EventSelector
 from PhysSelPython.Wrappers import SelectionSequence
-from PhysSelPython.Wrappers import MergedSelection
 from PhysSelPython.Wrappers import Selection, DataOnDemand
 from Configurables import StrippingNBMuMu
 from Configurables import CombineParticles
 from Configurables import DaVinci
-from Gaudi.Configuration import *
-
-from GaudiKernel.SystemOfUnits import MeV, GeV
 
 
 ########################################################################
 #
 # J/psi -> mu mu
 #
-from Configurables import CombineParticles
 JPsi = CombineParticles("JPsi")
 JPsi.DecayDescriptor = "J/psi(1S) -> mu+ mu-"
 JPsi.DaughtersCuts = {"mu+": "(TRCHI2DOF<10) & (ISMUON)"}
diff --git a/Phys/StrippingSelections/tests/CI/DataAuthentication.py b/Phys/StrippingSelections/tests/CI/DataAuthentication.py
new file mode 100644
index 0000000000000000000000000000000000000000..c57608fc2bf3de3254bbfee9175d1b068c5f7345
--- /dev/null
+++ b/Phys/StrippingSelections/tests/CI/DataAuthentication.py
@@ -0,0 +1,83 @@
+#!/#usr/bin/env python
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+import argparse
+import apd as apd
+import xml.etree.ElementTree as ET
+
+###########################################################
+#                                                         #
+# The function of this script is to add authentication    #
+# tokens to the paths in the file catalog xml file.       #
+# This is necessary for the CI to have access to the data #
+#                                                         #
+###########################################################
+
+
+########################################################
+# Functions to do all of the dirty authentication work #
+########################################################
+
+def append_token(pfn):
+    print("Appending token for '{}' ".format(pfn))
+    token = apd.auth(pfn) # Replace the pfn with the tokened pfns.
+    return token
+
+# Use this guy to process the pfn, obstaining the mdf prepend for the xrootd protocol, and then putting it back
+def process_pfn(string):
+    if string.startswith("mdf:"):
+        temp_string = string[4:]
+    else:
+        temp_string = string
+    new_string = append_token(temp_string)
+    if string.startswith("mdf:"):
+        new_string = "mdf:" + new_string
+    return new_string
+
+
+def replace_elements_in_xml(file_path):
+    # Load XML file
+    tree = ET.parse(file_path)
+    root = tree.getroot()
+    # Iterate over each old element and its corresponding replacement
+    for element in root.iter('pfn'):
+        element.set('name', process_pfn(element.get('name')))
+
+    # Modify the pool catalog file
+    xml_string = (
+        '<?xml version="1.0" encoding="UTF-8" standalone="no" ?>\n' +
+        '<!DOCTYPE POOLFILECATALOG SYSTEM "InMemory">\n' +
+        ET.tostring(root).decode("utf-8")
+    )
+    with open(file_path, "wt") as fh:
+        fh.write(xml_string)
+
+    print("XML file '{}' modified and saved as '{}'.".format(file_path, file_path))
+
+
+def main():
+    # Data
+    for year in ["2016", "2017", "2018"]:
+        if year == "2016":
+            data_XML_file = "Phys/StrippingSelections/tests/data/Reco16_DataType2016_Run174858.xml"
+        elif year == "2017":
+            data_XML_file = "Phys/StrippingSelections/tests/data/Reco17_DataType2017_Run195969.xml"
+        elif year == "2018":
+            data_XML_file = "Phys/StrippingSelections/tests/data/Reco18_DataType2018_Run214741.xml"
+        else:
+            raise NotImplementedError(year)
+    
+        # Create a new XML file to use in the test
+        replace_elements_in_xml(data_XML_file)
+
+
+if __name__ =='__main__':
+        main()
diff --git a/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py b/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
index af1b895603f4a5c72667e9ef1e02e8f4dec8d277..a95cd35b99bba6028cabfbee4d6f4ab5ea7c39fe 100755
--- a/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
+++ b/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSelections.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -10,14 +10,37 @@
 ###############################################################################
 # $Id: $
 # Test your line(s) of the stripping
-#  
-# NOTE: Please make a copy of this file for your testing, and do NOT change this one!
+# To be ran like: echo -n year WG | ./run gaudirun.py TestMyWGfromSelections.py 
+# NOTE: Liaisons should not edit this file.  If your WG or year are not attributed, please open an issue in Stripping
 #
+import sys
 
 from Gaudi.Configuration import *
 from Configurables import DaVinci
 from StrippingConf.Configuration import StrippingConf
 
+# Pipe in arguments with : echo -n year WG | ./run gaudirun.py TestMyWGfromSelections.py
+arguments = {"year": "2016", "WG": "SL"} # Put in some default values for testing purposes
+arglist = []
+if not sys.stdin.isatty():
+    for line in sys.stdin:
+        for word in line.split():
+            arglist.append(word)
+# Assign these values to the needed keys.
+for i in range(len(arglist)):
+    if i == 0:
+        arguments["year"] = arglist[i]  # set the first value to 'year'
+    elif i == 1:
+        arguments["WG"] = arglist[i]  # set the second value to 'WG'
+
+# Do a check that we are using valid attributes before continuing:
+#if not argumets["year"] in ["2016", "2018"]:
+#    print("ERROR: Invalid year for this test")
+#    break
+#if not argumets["WG"] in ["B2CC", "BandQ", "SL", "RD", "BnoC", "QEE", "B2OC", "Calib", "Charm", "IFT", "MiniBias"]:
+#    print("ERROR: Invalid WG for this test")
+#    break
+
 #
 #Fix for TrackEff lines
 #
@@ -25,8 +48,9 @@ from Configurables import DecodeRawEvent
 DecodeRawEvent().setProp("OverrideInputs",4.2)
 
 # Specify the name of your configuration
-my_wg='B2CC' #FOR LIAISONS
-
+year = arguments["year"]
+my_wg = arguments["WG"] #FOR LIAISONS
+print("Year is " + year + " and my_wg is " + my_wg)
 from Configurables import RootCnvSvc
 RootCnvSvc().GlobalCompression = "ZLIB:1"
 
@@ -148,5 +172,33 @@ TimingAuditor().TIMER.NameSize = 60
 MessageSvc().Format = "% F%60W%S%7W%R%T %0W%M"
 
 # Data
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+if year == "2016":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858_DV.py")
+elif year == "2017":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969_DV.py")
+elif year == "2018":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+else:
+    raise NotImplementedError(year)
+
+
+# Modify the input PFNs from the TestFileDB to be LFNs
+def pfn_to_lfn(pfn):
+    prefix = "root://eoslhcb.cern.ch//eos/lhcb/cern-swtest"
+    if not pfn.startswith(prefix):
+        raise NotImplementedError(pfn)
+    lfn = pfn[len(prefix):]
+    if lfn.startswith("/lhcb/data"):
+        lfn = "/lhcb/LHCb" + lfn[len("/lhcb/data"):]
+    return "LFN:" + lfn
+
+
+from Gaudi.Configuration import EventSelector
+from GaudiConf import IOHelper
+IOHelper().inputFiles([
+    pfn_to_lfn(IOHelper().undressFile(x))
+    for x in EventSelector().Input
+], clear=True)
diff --git a/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSettings.py b/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSettings.py
index b6af23d5e354205cad21f5876dda04b6b01333c2..4a98d8c9e17390a589327a2af276f1e67a75ab11 100755
--- a/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSettings.py
+++ b/Phys/StrippingSelections/tests/liaisons/TestMyWGfromSettings.py
@@ -11,16 +11,33 @@
 # $Id: $
 # Test your line(s) of the stripping by taking the dictionaries from StrippingSettings
 #  
-# NOTE: Please make a copy of this file for your testing, and do NOT change this one!
-#
+# To be ran like: echo -n year WG | ./run gaudirun.py TestMyWGfromSettings.py 
+# NOTE: Liaisons should not edit this file.  If your WG or year are not attributed, please open an issue in Stripping
 
 from Gaudi.Configuration import *
 from Configurables import DaVinci
 from StrippingConf.Configuration import StrippingConf
 
+# Pipe in arguments with : echo -n year WG | ./run gaudirun.py TestMyWGfromSettings.py
+arguments = {"year": "2016", "WG": "BandQ"} # Put in some default values for testing purposes
+arglist = []
+if not sys.stdin.isatty():
+    for line in sys.stdin:
+        for word in line.split():
+            arglist.append(word)
+# Assign these values to the needed keys.
+for i in range(len(arglist)):
+    if i == 0:
+        arguments["year"] = arglist[i]  # set the first value to 'year'
+    elif i == 1:
+        arguments["WG"] = arglist[i]  # set the second value to 'WG'
+
 # Specify the name of your configuration
-my_wg='B2OC' #FOR LIAISONS
-stripping='stripping34r0p2'
+stripping="stripping34r0p2"
+year = arguments["year"]
+my_wg = arguments["WG"] #FOR LIAISONS
+print("Year is " + year + " and my_wg is " + my_wg)
+
 
 from Configurables import RootCnvSvc
 RootCnvSvc().GlobalCompression = "ZLIB:1"
@@ -162,6 +179,17 @@ TimingAuditor().TIMER.NameSize = 60
 #importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco15aLead15_Run168665_PbAr.py")
 #importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco15aLead15_Run168665_PbAr_DV.py")
 
-# pp
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+# Data (pp)
+if year == "2016":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858_DV.py")
+elif year == "2017":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969_DV.py")
+elif year == "2018":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+else:
+    raise NotImplementedError(year)
+
+
diff --git a/Phys/StrippingSelections/tests/users/TestMyStrippingLine.py b/Phys/StrippingSelections/tests/users/TestMyStrippingLine.py
index 24bbec1e847938b35b0ff0b49186efa5d347bac7..f71c2feadd737d1349eb0d48d2235c257e17117a 100755
--- a/Phys/StrippingSelections/tests/users/TestMyStrippingLine.py
+++ b/Phys/StrippingSelections/tests/users/TestMyStrippingLine.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -11,15 +11,32 @@
 # $Id: $
 # Test your line(s) of the stripping
 #  
-# NOTE: Please make a copy of this file for your testing, and do NOT change this one!
-#
+# To be ran like: echo -n year confname | ./run gaudirun.py -T $STRIPPINGSELECTIONSROOT/tests/users/TestMyStrippingLine.py 
+# NOTE: Liaisons should not edit this file.  If your WG or year are not attributed, please open an issue in Stripping
 
 from Gaudi.Configuration import *
 from Configurables import DaVinci
 from StrippingConf.Configuration import StrippingConf
 
+# Pipe in arguments with : echo -n year WG | ./run gaudirun.py TestMyStrippingLine.py
+arguments = {"year": "2016", "confname": "Beauty2Charm"} # Put in some default values for testing purposes
+arglist = []
+if not sys.stdin.isatty():
+    for line in sys.stdin:
+        for word in line.split():
+            arglist.append(word)
+# Assign these values to the needed keys.
+for i in range(len(arglist)):
+    if i == 0:
+        arguments["year"] = arglist[i]  # set the first value to 'year'
+    elif i == 1:
+        arguments["confname"] = arglist[i]  # set the second value to 'WG'
+
 # Specify the name of your configuration
-confname='Beauty2Charm' #FOR USERS 
+year = arguments["year"]
+confname = arguments["confname"] #FOR LIAISONS
+print("Year is " + year + " and confname is " + confname)
+
    
 from Configurables import RootCnvSvc
 RootCnvSvc().GlobalCompression = "ZLIB:1"
@@ -158,6 +175,16 @@ MessageSvc().Format = "% F%60W%S%7W%R%T %0W%M"
 #importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18Lead18_217952_PbNe.py")
 #importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18Lead18_217952_PbNe_DV.py")
 
-## pp
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
-importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+# Data (pp)
+if year == "2016":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco16_DataType2016_Run174858_DV.py")
+elif year == "2017":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco17_DataType2017_Run195969_DV.py")
+elif year == "2018":
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741.py")
+    importOptions("$STRIPPINGSELECTIONSROOT/tests/data/Reco18_DataType2018_Run214741_DV.py")
+else:
+    raise NotImplementedError(year)
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2CC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2CC.py
new file mode 100644
index 0000000000000000000000000000000000000000..df999713339cd0bcd04f32320cec7517f428719c
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2CC.py
@@ -0,0 +1,19 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for B2CC WG                                                 ##
+##  Contact person: Jie Wu               (j.wu@cern.ch)                       ##
+################################################################################
+
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2OC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2OC.py
new file mode 100644
index 0000000000000000000000000000000000000000..d1a2e7b7fa23ca27e2b290840846c8a784372cc1
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_B2OC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+#########################################################################################################
+##                          S T R I P P I N G  28r2p2                                                  ##
+##                                                                                                     ##
+##  Configuration for B2OC WG                                                                          ##
+##  Contact person: Linxuan Zhu (linxuan.zhu@cern.ch)                                                  ##
+#########################################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BandQ.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BandQ.py
new file mode 100644
index 0000000000000000000000000000000000000000..7eab6f8788f5c4416f59d6942b4149766055e8ed
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BandQ.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for B&Q WG                                                  ##
+##  Contact person: Shuqi Sheng (shuqi.sheng@cern.ch)                         ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BnoC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BnoC.py
new file mode 100644
index 0000000000000000000000000000000000000000..1e73dec1941f606ecfc26961edc2ef0f6e5f5b6a
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_BnoC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for Charmless B decays (BnoC)                               ##
+##  Contact person: Ganrong Wang   (ganrong.wang@cern.ch)                    ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Calib.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Calib.py
new file mode 100644
index 0000000000000000000000000000000000000000..4f6604d4f63a7a6593f9a91bdb8e1dbcf428e239
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Calib.py
@@ -0,0 +1,17 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for Calib WG                                                ##
+##  Contact person: Louis Henry      (louis.henry@cern.ch)                    ##
+################################################################################
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Charm.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Charm.py
new file mode 100644
index 0000000000000000000000000000000000000000..759f4f0ebef538abf99beff2691d1127ebc2e0b2
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Charm.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for Charm WG                                                ##
+##  Contact person: Sergio Jaimes     (sergio.jaimes@cern.ch)                 ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_IFT.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_IFT.py
new file mode 100644
index 0000000000000000000000000000000000000000..0ab802eb5699a5424c134662172d2a19cf2ba47c
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_IFT.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for IFT WG                                                  ##
+##  Contact person: Hendrik Jage     (hendrik.jage@cern.ch)                   ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_QEE.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_QEE.py
new file mode 100644
index 0000000000000000000000000000000000000000..5977cecf5999a0ed83bf5a719b155de19f536c17
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_QEE.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for QEE WG                                                  ##
+##  Contact person: Xiaolin Wange (xiaolin.wang@cern.ch)                      ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_RD.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_RD.py
new file mode 100644
index 0000000000000000000000000000000000000000..7448f6d48bbb8512a5d15f9a1938171bf6891377
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_RD.py
@@ -0,0 +1,20 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for Rare Decays (RD) WG                                     ##
+##  Contact person: Matthew Birch (matthew.birch@cern.ch)                     ##
+##                  Yunxuan Song  (yunxuan.song@cern.ch)                      ##
+##                  Yingao Tang   (yingao.tang@cern.ch)                       ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Semileptonic.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Semileptonic.py
new file mode 100644
index 0000000000000000000000000000000000000000..c2fe61e911878c9afe7d744a5cbab29318bc7fd0
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/LineConfigDictionaries_Semileptonic.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+ 
+################################################################################
+##                          S T R I P P I N G  28r2p2                         ##
+##                                                                            ##
+##  Configuration for Semileptonic WG                                         ##
+##  Contact person: Fabian Christoph Glaser (fabian.christoph.glaser@cern.ch) ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/__init__.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..5276ee9f7ec053cf0dbd3011eb3a3674bf45f821
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping28r2p2/__init__.py
@@ -0,0 +1,21 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+__all__ = ['LineConfigDictionaries_B2OC',
+           'LineConfigDictionaries_B2CC',
+           'LineConfigDictionaries_Semileptonic',
+           'LineConfigDictionaries_RD',
+           'LineConfigDictionaries_BnoC',
+           'LineConfigDictionaries_Calib',
+           'LineConfigDictionaries_Charm',
+           'LineConfigDictionaries_QEE',
+           'LineConfigDictionaries_BandQ',
+           'LineConfigDictionaries_IFT'
+           ]
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2CC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2CC.py
new file mode 100644
index 0000000000000000000000000000000000000000..0135cc485e7bc2f7d7859ff6cd40d14e628bc47b
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2CC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for B2CC WG                                                 ##
+##  Contact person: Jie Wu               (j.wu@cern.ch)                       ##
+################################################################################
+
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2OC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2OC.py
new file mode 100644
index 0000000000000000000000000000000000000000..eb0a59570caeb2dedee6070a676bdefa7145ed22
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_B2OC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+#########################################################################################################
+##                          S T R I P P I N G  29r2p3                                                  ##
+##                                                                                                     ##
+##  Configuration for B2OC WG                                                                          ##
+##  Contact person: Linxuan Zhu (linxuan.zhu@cern.ch)                                                  ##
+#########################################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BandQ.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BandQ.py
new file mode 100644
index 0000000000000000000000000000000000000000..f604b277dfbbd78e400be197ee62c560954abe76
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BandQ.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for B&Q WG                                                  ##
+##  Contact person: Shuqi Sheng (shuqi.sheng@cern.ch)                         ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BnoC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BnoC.py
new file mode 100644
index 0000000000000000000000000000000000000000..59c1f0561f01f3fe075ed6a8ef12116600fa203b
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_BnoC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for Charmless B decays (BnoC)                               ##
+##  Contact person: Ganrong Wang   (ganrong.wang@cern.ch)                    ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Calib.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Calib.py
new file mode 100644
index 0000000000000000000000000000000000000000..2c7329b25f6512b9831c994a61be7406f6e14a54
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Calib.py
@@ -0,0 +1,17 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for Calib WG                                                ##
+##  Contact person: Louis Henry      (louis.henry@cern.ch)                    ##
+################################################################################
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Charm.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Charm.py
new file mode 100644
index 0000000000000000000000000000000000000000..d992d617d5ca7128baa78ee9ab4d28ff5a991852
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Charm.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for Charm WG                                                ##
+##  Contact person: Sergio Jaimes     (sergio.jaimes@cern.ch)                 ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_IFT.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_IFT.py
new file mode 100644
index 0000000000000000000000000000000000000000..5c07082bc8ead26dbf8496cf66ef85f13a810ea5
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_IFT.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for IFT WG                                                  ##
+##  Contact person: Hendrik Jage     (hendrik.jage@cern.ch)                   ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_QEE.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_QEE.py
new file mode 100644
index 0000000000000000000000000000000000000000..4e3d480374712dd9fbdfc88d8761f56596ef41f9
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_QEE.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for QEE WG                                                  ##
+##  Contact person: Xiaolin Wange (xiaolin.wang@cern.ch)                      ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_RD.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_RD.py
new file mode 100644
index 0000000000000000000000000000000000000000..cd11651bdb840182eebb3f84e9b3ee489e38ef52
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_RD.py
@@ -0,0 +1,20 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for Rare Decays (RD) WG                                     ##
+##  Contact person: Matthew Birch (matthew.birch@cern.ch)                     ##
+##                  Yunxuan Song  (yunxuan.song@cern.ch)                      ##
+##                  Yingao Tang   (yingao.tang@cern.ch)                       ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Semileptonic.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Semileptonic.py
new file mode 100644
index 0000000000000000000000000000000000000000..bab109ee93eac678f241abcc96fc49e7af4eebd9
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/LineConfigDictionaries_Semileptonic.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+ 
+################################################################################
+##                          S T R I P P I N G  29r2p3                         ##
+##                                                                            ##
+##  Configuration for Semileptonic WG                                         ##
+##  Contact person: Fabian Christoph Glaser (fabian.christoph.glaser@cern.ch) ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/__init__.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..5276ee9f7ec053cf0dbd3011eb3a3674bf45f821
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping29r2p3/__init__.py
@@ -0,0 +1,21 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+__all__ = ['LineConfigDictionaries_B2OC',
+           'LineConfigDictionaries_B2CC',
+           'LineConfigDictionaries_Semileptonic',
+           'LineConfigDictionaries_RD',
+           'LineConfigDictionaries_BnoC',
+           'LineConfigDictionaries_Calib',
+           'LineConfigDictionaries_Charm',
+           'LineConfigDictionaries_QEE',
+           'LineConfigDictionaries_BandQ',
+           'LineConfigDictionaries_IFT'
+           ]
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2CC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2CC.py
new file mode 100644
index 0000000000000000000000000000000000000000..ecb6c4b06a708b050892c3ad22b3bf191bae26b3
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2CC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+################################################################################
+##                          S T R I P P I N G  3 4 r 0 p 3                    ##
+##                                                                            ##
+##  Configuration for B2CC WG                                                 ##
+##  Contact person: Jie Wu               (j.wu@cern.ch)                       ##
+################################################################################
+
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2OC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2OC.py
new file mode 100644
index 0000000000000000000000000000000000000000..c0ba9d0be21acd2d9f85cda5a5466ca420ccedd3
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_B2OC.py
@@ -0,0 +1,17 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+#########################################################################################################
+##                          S T R I P P I N G  3 4 r 0 p 3                                             ##
+##                                                                                                     ##
+##  Configuration for B2OC WG                                                                          ##
+##  Contact person: Linxuan Zhu (linxuan.zhu@cern.ch)                                                  ##
+#########################################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BandQ.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BandQ.py
new file mode 100644
index 0000000000000000000000000000000000000000..d430c59868c00e01b175a7ec074b85c7eea5bb32
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BandQ.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  3 4 r 0 p 3                    ##
+##                                                                            ##
+##  Configuration for B&Q WG                                                  ##
+##  Contact person: Shuqi Sheng (shuqi.sheng@cern.ch)                         ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BnoC.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BnoC.py
new file mode 100644
index 0000000000000000000000000000000000000000..f641e0b4040cb3889fecca36029bc01cb3d6de44
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_BnoC.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  34r0p3                         ##
+##                                                                            ##
+##  Configuration for Charmless B decays (BnoC)                               ##
+##  Contact person: Ganrong Wang   (ganrong.wang@cern.ch)                    ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Calib.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Calib.py
new file mode 100644
index 0000000000000000000000000000000000000000..3fc3d2a158bdfd425eb7646c4c027b188c0ff1e1
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Calib.py
@@ -0,0 +1,17 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  34r0p3                         ##
+##                                                                            ##
+##  Configuration for Calib WG                                                ##
+##  Contact person: Louis Henry      (louis.henry@cern.ch)                    ##
+################################################################################
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Charm.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Charm.py
new file mode 100644
index 0000000000000000000000000000000000000000..a40c913843f3cb8b5be69855f648dd25b7bd0f67
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Charm.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  34r0p3                         ##
+##                                                                            ##
+##  Configuration for Charm WG                                                ##
+##  Contact person: Sergio Jaimes     (sergio.jaimes@cern.ch)                 ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_IFT.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_IFT.py
new file mode 100644
index 0000000000000000000000000000000000000000..d23843d68f3df95df23f5d06196a3ec13526d20a
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_IFT.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2021 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  34r0p3                         ##
+##                                                                            ##
+##  Configuration for IFT WG                                                  ##
+##  Contact person: Hendrik Jage     (hendrik.jage@cern.ch)                   ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_QEE.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_QEE.py
new file mode 100644
index 0000000000000000000000000000000000000000..28d9b43888db3fc17f7887c3425e62763f67916c
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_QEE.py
@@ -0,0 +1,17 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+################################################################################
+##                          S T R I P P I N G  3 4 r 0 p 3                    ##
+##                                                                            ##
+##  Configuration for QEE WG                                                  ##
+##  Contact person: Xiaolin Wange (xiaolin.wang@cern.ch)                      ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_RD.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_RD.py
new file mode 100644
index 0000000000000000000000000000000000000000..28c96a5b657646e07aa92af3e7044bad91d6c115
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_RD.py
@@ -0,0 +1,20 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+
+################################################################################
+##                          S T R I P P I N G  3 4 r 0 p 3                    ##
+##                                                                            ##
+##  Configuration for Rare Decays (RD) WG                                     ##
+##  Contact person: Matthew Birch (matthew.birch@cern.ch)                     ##
+##                  Yunxuan Song  (yunxuan.song@cern.ch)                      ##
+##                  Yingao Tang   (yingao.tang@cern.ch)                       ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Semileptonic.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Semileptonic.py
new file mode 100644
index 0000000000000000000000000000000000000000..53d9a0deff65f704f2e37964e29a44738806a227
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/LineConfigDictionaries_Semileptonic.py
@@ -0,0 +1,18 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+ 
+################################################################################
+##                          S T R I P P I N G  34r0p3                         ##
+##                                                                            ##
+##  Configuration for Semileptonic WG                                         ##
+##  Contact person: Fabian Christoph Glaser (fabian.christoph.glaser@cern.ch) ##
+################################################################################
+
diff --git a/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/__init__.py b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/__init__.py
new file mode 100644
index 0000000000000000000000000000000000000000..5276ee9f7ec053cf0dbd3011eb3a3674bf45f821
--- /dev/null
+++ b/Phys/StrippingSettings/python/StrippingSettings/Stripping34r0p3/__init__.py
@@ -0,0 +1,21 @@
+###############################################################################
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
+#                                                                             #
+# This software is distributed under the terms of the GNU General Public      #
+# Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
+#                                                                             #
+# In applying this licence, CERN does not waive the privileges and immunities #
+# granted to it by virtue of its status as an Intergovernmental Organization  #
+# or submit itself to any jurisdiction.                                       #
+###############################################################################
+__all__ = ['LineConfigDictionaries_B2OC',
+           'LineConfigDictionaries_B2CC',
+           'LineConfigDictionaries_Semileptonic',
+           'LineConfigDictionaries_RD',
+           'LineConfigDictionaries_BnoC',
+           'LineConfigDictionaries_Calib',
+           'LineConfigDictionaries_Charm',
+           'LineConfigDictionaries_QEE',
+           'LineConfigDictionaries_BandQ',
+           'LineConfigDictionaries_IFT'
+           ]
diff --git a/Phys/StrippingTCK/options/hltconfig.py b/Phys/StrippingTCK/options/hltconfig.py
index bc5b1bf4c4058dbc6adeecea1e5e55935272a76a..1bd3aca05739e7bf347b679c1c921679211ace1c 100644
--- a/Phys/StrippingTCK/options/hltconfig.py
+++ b/Phys/StrippingTCK/options/hltconfig.py
@@ -8,9 +8,8 @@
 # granted to it by virtue of its status as an Intergovernmental Organization  #
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
+from Gaudi.Configuration import EventSelector
 from Configurables import DaVinci
-from Gaudi.Configuration import *
-
 from Configurables import HltGenConfig, ConfigTarFileAccessSvc
 
 confsvc = ConfigTarFileAccessSvc(File='config.tar', Mode='ReadWrite')
diff --git a/Phys/StrippingTCK/python/Sandbox.py b/Phys/StrippingTCK/python/Sandbox.py
index dca14d6c0232acced5b516988676211864e9049f..64bc2b380497cc5be1418ceea5bff8c563f7b361 100755
--- a/Phys/StrippingTCK/python/Sandbox.py
+++ b/Phys/StrippingTCK/python/Sandbox.py
@@ -18,7 +18,7 @@ def execInSandbox(fun, *args, **kwargs):
         try:
             # TODO: catch errors, and signal parent about them...
             w.send(fun(*args, **kwargs))
-        except Exception, e:
+        except Exception, e:  # noqa
             w.send(e)
 
     p = Process(target=worker, args=args, kwargs=kwargs)
diff --git a/Phys/StrippingTCK/python/utils.py b/Phys/StrippingTCK/python/utils.py
index e5440b53396fa9675cc41ecf5f7c8b52acf71588..64858bdf451f38d81de3367680a3d7c9adfa1650 100755
--- a/Phys/StrippingTCK/python/utils.py
+++ b/Phys/StrippingTCK/python/utils.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -8,15 +8,19 @@
 # granted to it by virtue of its status as an Intergovernmental Organization  #
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
+from __future__ import print_function
+from pprint import pprint
+import os
 import GaudiPython
-from Gaudi.Configuration import *
-from Configurables import ConfigStackAccessSvc, ConfigDBAccessSvc, ConfigTarFileAccessSvc, ConfigZipFileAccessSvc, ConfigFileAccessSvc, PropertyConfigSvc
+from Gaudi.Configuration import DEBUG, ERROR
+from Configurables import ApplicationMgr
+from Configurables import (ConfigStackAccessSvc, ConfigDBAccessSvc,
+                           ConfigZipFileAccessSvc, PropertyConfigSvc)
 
 # pick the default config access svc
 from Configurables import ConfigTarFileAccessSvc as ConfigAccessSvc
 
 from Sandbox import execInSandbox
-from pprint import pprint
 
 # add some decoration...
 GaudiPython.gbl.Gaudi.Math.MD5.__str__ = GaudiPython.gbl.Gaudi.Math.MD5.str
@@ -78,14 +82,13 @@ def tck2id(x, cas):
 def _orphanScan(cas=defaultCas):
     treeNodeDict = dict()
     leafNodeDict = dict()
-    import os
     dir = None
     if 'Directory' in cas.getProperties():
         dir = cas.getProp('Directory')
     if not dir and 'Directory' in cas.getDefaultProperties():
         dir = cas.getDefaultProperty('Directory')
     for root, dirs, files in os.walk(dir):
-        print 'checking ' + root
+        print('checking ' + root)
         import fnmatch
         for d in fnmatch.filter(dirs, 'CVS'):
             dirs.remove(d)
@@ -100,8 +103,8 @@ def _orphanScan(cas=defaultCas):
                 updateDict(treeNodeDict, f)
     info = getConfigurations(cas)
     for (k, v) in info.iteritems():
-        print '\n\n'
-        print k
+        print('\n\n')
+        print(k)
         v.printSimple()
         id = v.info['id']
         tree = execInSandbox(_getConfigTree, id, cas)
@@ -114,14 +117,14 @@ def _orphanScan(cas=defaultCas):
             updateDict(treeNodeDict,  node.digest, k)
             if node.leaf:
                 updateDict(leafNodeDict, node.leaf.digest, k)
-    print 'leafNodes orphans: '
+    print('leafNodes orphans: ')
     for (k, v) in leafNodeDict.iteritems():
         if not v:
-            print k
-    print 'treeNodes orphans: '
+            print(k)
+    print('treeNodes orphans: ')
     for (k, v) in treeNodeDict.iteritems():
         if not v:
-            print k
+            print(k)
 
 
 def _digest(x, cas):
@@ -136,14 +139,14 @@ class _TreeNodeCache:
     svc = None
 
     def __init__(self, svc=None):
-        if type(_TreeNodeCache.ncache) is type(None):
-            if type(svc) is type(None):
+        if _TreeNodeCache.ncache is None:
+            if svc is None:
                 raise RuntimeWarning(
                     'oops... no svc during singleton creation')
             _TreeNodeCache.ncache = dict()
             _TreeNodeCache.lcache = dict()
             _TreeNodeCache.svc = svc
-        elif svc and svc != TreeNodeCache.svc:
+        elif svc and svc != _TreeNodeCache.svc:
             raise RuntimeWarning(
                 'oops... already have a different svc during singleton access ')
 
@@ -176,7 +179,7 @@ def _parseL0settings(settings):
 
 def _parseL0setting(setting):
     import re
-    p = re.compile('([^ ]+) *= *\[(.+)\]')
+    p = re.compile('([^ ]+) *= *\[(.+)\]')  # noqa
     val = {}
     for s in setting:
         m = p.match(s)
@@ -193,7 +196,7 @@ def _parseL0setting(setting):
             else:
                 value = [value]
             #  and get rid of the [] again...
-            value = [re.sub('\[(.*)\]', r'\1', i.strip()) for i in value]
+            value = [re.sub('\[(.*)\]', r'\1', i.strip()) for i in value]  # noqa
         val.update({key: value})
     return val
 
@@ -202,13 +205,12 @@ def dumpL0(id, cas=defaultCas):
     tree = execInSandbox(_getConfigTree, id, cas)
     l0s = [i for i in tree if i.leaf and i.leaf.type == 'L0DUConfigProvider']
     for i in l0s:
-        from pprint import pprint
-        print '%s TCK = %s %s' % (20*'*', i.leaf.props['TCK'], 20 * '*')
-        print '%s Channels %s' % (20*'*', 20 * '*')
+        print('%s TCK = %s %s' % (20*'*', i.leaf.props['TCK'], 20 * '*'))
+        print('%s Channels %s' % (20*'*', 20 * '*'))
         pprint(_parseL0settings(eval(i.leaf.props['Channels'])))
-        print '%s Conditions %s' % (19*'*', 19 * '*')
+        print('%s Conditions %s' % (19*'*', 19 * '*'))
         pprint(_parseL0settings(eval(i.leaf.props['Conditions'])))
-        print 100*'*'
+        print(100*'*')
 
 
 def getL0Prescales(id, cas=defaultCas):
@@ -265,7 +267,7 @@ def _createTCKEntries(d, cas):
 #                        raise KeyError('requested L0TCK %s not known by L0DUMultiConfigProvider in config %s; known L0TCKs: %s' % ( l0tck, id, cfg.props['registerTCK'] ))
 #                    elif cfg.type == 'L0DUConfigProvider' and l0tck != cfg.props['TCK'] :
 #                        raise KeyError('requested L0TCK %s not known by L0DUConfigProvider in config %s; known L0TCK: %s' % ( l0tck, id, cfg.props['TCK'] ))
-        print 'creating mapping TCK: 0x%08x -> ID: %s' % (tck, id)
+        print('creating mapping TCK: 0x%08x -> ID: %s' % (tck, id))
         ref = cas.readConfigTreeNode(id)
         alias = TCK(ref.get(), tck)
         cas.writeConfigTreeNodeAlias(alias)
@@ -292,7 +294,7 @@ def _getConfigurations(cas=defaultCas):
         for k in info.values():
             if k.info['id'] == id:
                 k.update({'TAG': tag})
-    print info
+    print(info)
     return info
 
 
@@ -346,8 +348,8 @@ def _copyTree(svc, nodeRef, prefix):
     leafRef = node.leaf()
     if (leafRef.valid()):
         leaf = svc.readPropertyConfig(leafRef)
-        print prefix + leaf.name()
-        newRef = svc.writePropertyConfig(leaf.get())
+        print(prefix + leaf.name())
+        _ = svc.writePropertyConfig(leaf.get())  # new ref
         # TODO: check validity...
     for i in node.nodes():
         _copyTree(svc, i, prefix+'   ')
@@ -362,11 +364,11 @@ def _copy(source, target):
     s = appMgr.service(csvc.getFullName(), 'IConfigAccessSvc')
     for label in ['TOPLEVEL/', 'TCK/', 'ALIAS/']:
         for i in s.configTreeNodeAliases(alias(label)):
-            print '\n\n copying tree ' + str(i.alias()) + '\n\n'
+            print('\n\n copying tree ' + str(i.alias()) + '\n\n')
             _copyTree(s, i.ref(), ' ')
-            print '\n\n writing alias ' + str(i.alias()) + '\n\n'
+            print('\n\n writing alias ' + str(i.alias()) + '\n\n')
             s.writeConfigTreeNodeAlias(i)
-    print 'done copying...'
+    print('done copying...')
 
 
 def _lookupProperty(table, algname, property):
@@ -407,12 +409,12 @@ class Configuration:
 
     def printSimple(self, prefix='      '):
         if not self.info['TCK']:
-            print prefix + '%10s : %s : %s' % ('<NONE>', self.info['id'], self.info['label'])
+            print(prefix + '%10s : %s : %s' % ('<NONE>', self.info['id'], self.info['label']))
         else:
             for tck in self.info['TCK']:
                 if type(tck) == int:
                     tck = '0x%08x' % tck
-                print prefix + '%10s : %s : %s' % (tck, self.info['id'], self.info['label'])
+                print(prefix + '%10s : %s : %s' % (tck, self.info['id'], self.info['label']))
 
     def PVSS(self):
         for tck in self.info['TCK']:
@@ -458,7 +460,7 @@ class Tree(object):
     def prnt(self):
         s = ' --> ' + str(self.leaf.digest) if self.leaf else ''
         indent = self.depth*'   '
-        print indent + str(self.digest) + (30-len(indent))*' ' + s
+        print(indent + str(self.digest) + (30-len(indent))*' ' + s)
         for i in self.nodes:
             i.prnt()
     # define in order traversal
@@ -481,21 +483,22 @@ def diff(lhs, rhs, cas=defaultCas):
     setr = set(table[rhs].keys())
     onlyInLhs = setl - setr
     if len(onlyInLhs) > 0:
-        print 'only in ' + lhs + ': '
+        print('only in ' + lhs + ': ')
         for i in onlyInLhs:
-            print '   ' + i
+            print('   ' + i)
     onlyInRhs = setr - setl
     if len(onlyInRhs) > 0:
-        print 'only in ' + rhs + ': '
+        print('only in ' + rhs + ': ')
         for i in onlyInRhs:
-            print '   ' + i
+            print('   ' + i)
     for i in setl & setr:
         (l, r) = (table[lhs][i], table[rhs][i])
         if l.digest != r.digest:
             from difflib import unified_diff
-            print ''.join(unified_diff(l.fmt(), r.fmt(),
+            print(''.join(unified_diff(l.fmt(), r.fmt(),
                                        l.fqn(), r.fqn(),
                                        lhs, rhs, n=0))
+                  )
 
 
 def createTCKEntries(d, cas=defaultCas):
@@ -511,21 +514,11 @@ def listComponents(id, cas=defaultCas):
     for i in tree:
         if i.leaf:
             s = i.depth*3*' ' + i.leaf.name
-            print s + (80-len(s))*' ' + str(i.leaf.digest)
-
-
-def getAlgorithms(id, cas=defaultCas):
-    tree = getConfigTree(id, cas)
-    x = ''
-    for i in tree:
-        if i.leaf and i.leaf.kind == 'IAlgorithm':
-            s = i.depth*3*' ' + i.leaf.name
-            x = x + s + (80-len(s))*' ' + str(i.leaf.digest) + '\n'
-    return x
+            print(s + (80-len(s))*' ' + str(i.leaf.digest))
 
 
 def listAlgorithms(id, cas=defaultCas):
-    print getAlgorithms(id, cas)
+    print(getAlgorithms(id, cas))
 
 
 def getStreams(id, cas=defaultCas):
@@ -542,7 +535,7 @@ def getStreams(id, cas=defaultCas):
 
 
 def listStreams(id, cas=defaultCas):
-    print getStreams(id, cas)
+    print(getStreams(id, cas))
 
 
 def getLines(id, stream=None, cas=defaultCas):
@@ -568,7 +561,7 @@ def getLines(id, stream=None, cas=defaultCas):
 
 
 def listLines(id, stream=None, cas=defaultCas):
-    print getLines(id, stream, cas)
+    print(getLines(id, stream, cas))
 
 
 def getLineProperties(id, linename='', cas=defaultCas):
@@ -617,7 +610,7 @@ def getLineProperties(id, linename='', cas=defaultCas):
 
 
 def listLineProperties(id, linename='', cas=defaultCas):
-    print getLineProperties(id, linename, cas)
+    print(getLineProperties(id, linename, cas))
 
 
 def getProperties(id, algname='', property='', cas=defaultCas):
@@ -666,9 +659,9 @@ def listProperties(id, algname='', property='', cas=defaultCas):
             if matchProp and not matchProp(k):
                 continue
             if first:
-                print '\n   Requested Properties for ' + i.leaf.fullyQualifiedName
+                print('\n   Requested Properties for ' + i.leaf.fullyQualifiedName)
                 first = False
-            print "      '" + k + "\':" + v
+            print("      '" + k + "\':" + v)
 
 
 def orphanScan(cas=defaultCas):
@@ -767,7 +760,7 @@ def dump(id, properties=None,  lines=None, cas=defaultCas):
             if _tab+25 < len1(line):
                 line += '\n'+(_tab+25)*' '
             line += '%-15s : %s' % (k, v)
-        print line
+        print(line)
 
 
 def getConfigTree(id, cas=defaultCas):
@@ -798,13 +791,13 @@ def getHlt1Decisions(id, cas=defaultCas):
 
 def printConfigurations(info):
     for i in info.itervalues():
-        print i.info
+        print(i.info)
     for release in sorted(set([i['release'] for i in info.itervalues()])):
-        print release
+        print(release)
         confInRelease = [
             i for i in info.itervalues() if i['release'] == release]
         for hlttype in sorted(set([i['hlttype'] for i in confInRelease])):
-            print '    ' + hlttype
+            print('    ' + hlttype)
             [i.printSimple('      ')
              for i in confInRelease if i['hlttype'] == hlttype]
 
diff --git a/Phys/StrippingUtils/python/StrippingUtils/LineBuilderTests.py b/Phys/StrippingUtils/python/StrippingUtils/LineBuilderTests.py
index b26d5d8a455f3b6d524584ecaab2d65f570abd5d..08a4508469fcb260fc63d20615eba6ab04ffef4f 100644
--- a/Phys/StrippingUtils/python/StrippingUtils/LineBuilderTests.py
+++ b/Phys/StrippingUtils/python/StrippingUtils/LineBuilderTests.py
@@ -10,9 +10,10 @@
 ###############################################################################
 """Test suite for testing line builders
 """
+from __future__ import print_function
 
 __all__ = ('test_line_builder',
-           'test__build_many_instances',
+           'test_build_many_instances',
            'test_second_instance_does_not_overwrite_lines',
            'test_default_raises',
            'test_single_constructor_argument_raises',
@@ -35,7 +36,7 @@ def test_line_builder(builderType, conf_dict):
     Run all tests on a line builder, given a configuration dictionary.
     All line builders should pass this test.
     """
-    print 'test_line_builder', builderType.__name__, '...'
+    print('test_line_builder' + builderType.__name__ + '...')
     test_default_raises(builderType)
     test_single_constructor_argument_raises(builderType, conf_dict)
     test_duplicate_name_raises(builderType, conf_dict)
@@ -46,7 +47,7 @@ def test_line_builder(builderType, conf_dict):
 
 
 def test_build_many_instances(builderType, conf_dict):
-    print 'test_make_many_instances', builderType.__name__, '...'
+    print('test_make_many_instances' + builderType.__name__ + '...')
     """
     Test that an arbitrary number of instances can be instantiated with different names.
     Access the lines of each instance to catch on-demand line building.
@@ -54,16 +55,16 @@ def test_build_many_instances(builderType, conf_dict):
     baseName = builderType.__name__
     for n in '0123456789':
         b = builderType(baseName + n, conf_dict)
-        lines = b.lines()
+        _ = b.lines()
         test_linebuilder_instance(b)
 
 
 def test_second_instance_does_not_overwrite_lines(builderType, conf_dict):
-    print 'test_second_instance_does_not_overwrite_lines', builderType.__name__, '...'
+    print('test_second_instance_does_not_overwrite_lines' + builderType.__name__ + '...')
     b0 = builderType(builderType.__name__+'FirstBuilder', conf_dict)
     b0lines = b0.lines()
     b1 = builderType(builderType.__name__+'SecondBuilder', conf_dict)
-    assert b0.lines() == b0lines
+    assert b1.lines() == b0lines
 
 
 def test_linebuilder_instance(b):
@@ -76,30 +77,30 @@ def test_linebuilder_instance(b):
 
 
 def test_duplicate_name_raises(builderType, conf_dict):
-    print 'test_duplicate_name_raises', builderType.__name__, '...'
+    print('test_duplicate_name_raises' + builderType.__name__ + '...')
     name = builderType.__name__+'Instance'
-    b0 = builderType(name, conf_dict)
+    _ = builderType(name, conf_dict)
     raises(Exception, builderType, name, conf_dict)
 
 
 def test_default_raises(builderType):
-    print 'test_default_raises', builderType.__name__, '...'
+    print('test_default_raises' + builderType.__name__ + '...')
     raises(Exception, builderType)
 
 
 def test_single_constructor_argument_raises(builderType, conf_dict):
-    print 'test_single_constructor_argument_raises', builderType.__name__, '...'
+    print('test_single_constructor_argument_raises' + builderType.__name__ + '...')
     raises(Exception, builderType, conf_dict)
     raises(Exception, builderType, 'SomeCrazyName')
 
 
 def test_configuration_not_dictlike_raises(builderType, conf_dict):
-    print 'test_configuration_not_dictlike_raises', builderType.__name__, '...'
+    print('test_configuration_not_dictlike_raises' + builderType.__name__ + '...')
     raises(AttributeError, builderType, 'TestBadConfDict', conf_dict)
 
 
 def test_bad_configuration_raises(builderType, good_conf_dict):
-    print 'test_bad_configuration_raises', builderType.__name__, '...'
+    print('test_bad_configuration_raises' + builderType.__name__ + '...')
     assert hasattr(good_conf_dict, 'keys')
     assert hasattr(good_conf_dict, '__getitem__')
     bad_conf_dict = deepcopy(good_conf_dict)
@@ -123,7 +124,7 @@ def test_line_location(line, allowEmptyLocation=True):
 
 
 def test_lines(builder):
-    print 'test_lines', type(builder).__name__, '...'
+    print('test_lines' + type(builder).__name__ + '...')
     lines = builder.lines()
     for line in lines:
         test_line(line)
@@ -136,7 +137,7 @@ def test_cannot_modify_lines(builder):
     check that no modification ocurrs. Else, all is good. Check that there
     is no change anyway.
     """
-    print 'test_cannot_modify_lines', type(builder).__name__, '...'
+    print('test_cannot_modify_lines' + type(builder).__name__ + '...')
     orig_lines = builder.lines()
     mod_lines = builder.lines()
     try:
@@ -153,14 +154,14 @@ def test_line_locations(builder, allowEmptyLocation=True):
     StrippingXYZ, StrippingABC, .. is .../XYZ .../ABC, etc.
     If allowEmptyLocation = True accept empty strings.
     """
-    print 'test_line_locations', type(builder).__name__, '...'
+    print('test_line_locations' + type(builder).__name__ + '...')
     lines = builder.lines()
     for line in lines:
         test_line_location(line, allowEmptyLocation)
 
 
 def test_lineNames_method(builder):
-    names = [l.name() for l in builder.lines()]
+    names = [line.name() for line in builder.lines()]
     for name in names:
         assert name in builder.lineNames()
 
diff --git a/Phys/StrippingUtils/python/StrippingUtils/Utils.py b/Phys/StrippingUtils/python/StrippingUtils/Utils.py
index f4395e8ff21551574fd98e10f0fe5d8407e04257..1ad48b293fe0b5720e5762f83bcbfbd652ffc4c9 100644
--- a/Phys/StrippingUtils/python/StrippingUtils/Utils.py
+++ b/Phys/StrippingUtils/python/StrippingUtils/Utils.py
@@ -11,6 +11,7 @@
 '''
 Helpers for construction of Stripping Selections
 '''
+from __future__ import print_function
 __author__ = "Juan Palacios juan.palacios@cern.ch"
 __date__ = "30/06/2010"
 
@@ -25,10 +26,9 @@ import inspect
 import os
 import subprocess
 from os import environ
-from pprint import *
-from Gaudi.Configuration import *
-from StrippingConf.Configuration import StrippingLine
 from pprint import pformat
+from Gaudi.Configuration import log
+from StrippingConf.Configuration import StrippingLine
 
 
 def checkConfig(reference_keys, configuration):
@@ -182,7 +182,7 @@ class MasterLineBuilder(LineBuilder):
         self._name = name
 
         if not issubclass(SlaveBuilderClass, LineBuilder):
-            raise TypeError, "The slave class must inherit from a LineBuilder"
+            raise TypeError, "The slave class must inherit from a LineBuilder"  # noqa
 
         self.__configuration_keys__ = SlaveBuilderClass.__configuration_keys__
 
@@ -312,7 +312,7 @@ def getBuilderAndConfFromModule(confModule):
         if conf['BUILDERTYPE'] in lineBuilders.keys():
             buildersConf[name] = conf
         else:
-            print '[WARNING] The LinBuilder %s is not defined in the module %s' % (conf['BUILDERTYPE'], confModule.__name__)
+            print('[WARNING] The LinBuilder %s is not defined in the module %s' % (conf['BUILDERTYPE'], confModule.__name__))  # noqa
 
     return lineBuilder, buildersConf
 
diff --git a/README.md b/README.md
index 1b6b08b1dc302570ab25d70c1f2eb610930a21b3..d0e3238dff69168ec9fb6dc531d9a80f70d39304 100644
--- a/README.md
+++ b/README.md
@@ -6,6 +6,16 @@ Before creating a merge request, please consider the following guidelines:
 
 We will propagate those changes to master if relevant for the upgrade or run2-patches if appropriate.
 
-Please contact the Stripping managers if you are unsure which target branch to choose. 
+Please contact the Stripping coordinators if you are unsure which target branch to choose. 
 
 For new campaigns, we will inform you of the dedicated branches.
+
+# 2023 Run 2 Incremental Restripping Campaign
+
+The 2023 incremental restripping campaign workflow has been simplified for production:
+
+- Analysers should branch from their PAWGs ```PAWG_2018-patches``` development branch, and do developments there.
+- When ready, these developments are merged to the PAWGs development branch, overseen by liaisons.
+- Incremental merges of the development branches to the production branch of ```2018-patches``` will be done by the stripping coordinators.
+
+Further details can be found in the training item https://indico.cern.ch/event/1274062/#b-513813-stripping-liaisons-tr
diff --git a/StrippingSys/tests/options/configurables.py b/StrippingSys/tests/options/configurables.py
index b72c31c05d9b2f8829ea18f1c261ef4bbc763052..bafd1a38cdc855d70f8f02ed3a97b643cd0e17ff 100644
--- a/StrippingSys/tests/options/configurables.py
+++ b/StrippingSys/tests/options/configurables.py
@@ -1,5 +1,5 @@
 ###############################################################################
-# (c) Copyright 2000-2019 CERN for the benefit of the LHCb Collaboration      #
+# (c) Copyright 2000-2023 CERN for the benefit of the LHCb Collaboration      #
 #                                                                             #
 # This software is distributed under the terms of the GNU General Public      #
 # Licence version 3 (GPL Version 3), copied verbatim in the file "COPYING".   #
@@ -8,27 +8,27 @@
 # granted to it by virtue of its status as an Intergovernmental Organization  #
 # or submit itself to any jurisdiction.                                       #
 ###############################################################################
+from __future__ import print_function
 import Configurables
 
-success_list=[]
-fail_list=[]
+success_list = []
+fail_list = []
 
 for conf in sorted(Configurables.__all__):
     try:
-        print "# " + conf
+        print("# " + conf)
         exec("Configurables.%s()" % conf)
         success_list.append(conf)
-    except:
+    except:  # noqa
         import sys
         import traceback
         traceback.print_exc(file=sys.stdout)
         fail_list.append(conf)
 
-print "== successful =="
-print len(success_list)
-print success_list
-print "== failed =="
-print len(fail_list)
-print fail_list
-print "== done =="
-
+print("== successful ==")
+print(len(success_list))
+print(success_list)
+print("== failed ==")
+print(len(fail_list))
+print(fail_list)
+print("== done ==")