ATLAS Offline Software
AsgComponentConfig.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3 */
4 
6 
7 
8 
9 //
10 // includes
11 //
12 
14 
15 #include <AsgTools/AsgToolConfig.h>
16 #include <regex>
17 
18 #ifdef XAOD_STANDALONE
19 
20 #include <AsgTools/AsgComponent.h>
22 #include <AsgTools/AsgTool.h>
23 #include <AsgTools/AnaToolHandle.h>
24 #include <TInterpreter.h>
25 #include <boost/format.hpp>
26 
27 #else
28 
29 #include "Gaudi/Interfaces/IOptionsSvc.h"
30 #include <GaudiKernel/ServiceHandle.h>
31 
32 #endif
33 
34 //
35 // method implementations
36 //
37 
38 namespace asg
39 {
40  namespace
41  {
48  std::string makeArrayName (const std::string& name, std::size_t index)
49  {
50  return name + "@" + std::to_string (index);
51  }
52  }
53 
54 
56  AsgComponentConfig (const std::string& val_typeAndName)
57  {
58  setTypeAndName (val_typeAndName);
59  }
60 
61 
62 
64  empty () const noexcept
65  {
66  return
67  m_type.empty() && m_name.empty() &&
68  m_privateTools.empty() && m_propertyValues.empty();
69  }
70 
71 
72 
73  const std::string& AsgComponentConfig ::
74  type () const noexcept
75  {
76  return m_type;
77  }
78 
79 
80 
82  setType (const std::string& val_type)
83  {
84  m_type = val_type;
85  }
86 
87 
88 
89  const std::string& AsgComponentConfig ::
90  name () const noexcept
91  {
92  return m_name;
93  }
94 
95 
96 
98  setName (const std::string& val_name)
99  {
100  m_name = val_name;
101  }
102 
103 
104 
106  typeAndName () const
107  {
108  if (m_name == m_type)
109  return m_name;
110  return m_type + "/" + m_name;
111  }
112 
113 
114 
116  setTypeAndName (const std::string& val_typeAndName)
117  {
118  const auto split = val_typeAndName.find ('/');
119  if (split == std::string::npos)
120  {
121  setType (val_typeAndName);
122  setName (val_typeAndName);
123  } else
124  {
125  setType (val_typeAndName.substr (0,split));
126  setName (val_typeAndName.substr (split+1));
127  }
128  }
129 
130 
131 
133  setPropertyFromString (const std::string& name,
134  const std::string& value)
135  {
136  auto split = name.find ('.');
137  if (split == std::string::npos)
138  {
140  } else
141  {
142  auto subtool = accessSubtool (name, split);
143  subtool.config->setPropertyFromString (subtool.name, value);
144  }
145  }
146 
147 
148 
150  createPrivateTool (const std::string& name,
151  const std::string& toolType)
152  {
153  return addPrivateTool (name, AsgComponentConfig(toolType + "/" + name));
154  }
155 
156 
157 
159  createPrivateToolInArray (const std::string& name,
160  const std::string& toolType)
161  {
162  return addPrivateToolInArray (name, AsgComponentConfig(toolType + "/" + name));
163  }
164 
165 
166 
168  addPrivateTool (const std::string& name,
169  AsgComponentConfig toolConfig)
170  {
171  using namespace msgComponentConfig;
172 
173  auto split = name.find ('.');
174  if (split == std::string::npos)
175  {
176  toolConfig.setName (name);
177  m_privateTools[name] = {std::move(toolConfig), ""};
178  return StatusCode::SUCCESS;
179  } else
180  {
181  auto subtool = accessSubtool (name, split);
182  return subtool.config->addPrivateTool (subtool.name, std::move (toolConfig));
183  }
184  }
185 
186 
187 
189  addPrivateToolInArray (const std::string& name,
190  AsgComponentConfig toolConfig)
191  {
192  using namespace msgComponentConfig;
193 
194  auto split = name.find ('.');
195  if (split == std::string::npos)
196  {
197  auto& arrayData = m_toolArrays[name];
198  auto myname = makeArrayName (name, arrayData.size());
199  toolConfig.setName (myname);
200  m_privateTools[myname] = {std::move(toolConfig), name};
201  arrayData.push_back (myname);
202  return myname;
203  } else
204  {
205  auto subtool = accessSubtool (name, split);
206  return subtool.prefix + subtool.config
207  ->addPrivateToolInArray (subtool.name, std::move (toolConfig));
208  }
209  }
210 
211 
212 
214  checkTypeName (bool nestedNames) const
215  {
216  using namespace msgComponentConfig;
217 
218  std::regex typeExpr ("[A-Za-z_][A-Za-z0-9_]*(::[A-Za-z_][A-Za-z0-9_]*)*");
219  if (!std::regex_match (m_type, typeExpr))
220  {
221  ANA_MSG_ERROR ("type \"" << m_type << "\" does not match format expression");
222  return StatusCode::FAILURE;
223  }
224  std::regex nameExpr;
225  if (nestedNames)
226  nameExpr = std::regex ("[A-Za-z_][A-Za-z0-9_]*(\\.[A-Za-z_][A-Za-z0-9_]*)*(@[0-9]+)?");
227  else
228  nameExpr = std::regex ("[A-Za-z_][A-Za-z0-9_]*(@[0-9]+)?");
229  if (!std::regex_match (m_name, nameExpr))
230  {
231  ANA_MSG_ERROR ("name \"" << m_name << "\" does not match format expression");
232  return StatusCode::FAILURE;
233  }
234  return StatusCode::SUCCESS;
235  }
236 
237 
238 
240  accessSubtool (const std::string& name, std::size_t split)
241  {
243  auto subtool = m_privateTools.find (name.substr (0, split));
244  if (subtool == m_privateTools.end())
245  throw std::runtime_error ("trying to access unknown private tool: " + name.substr (0, split));
246  result.config = &(subtool->second.m_config);
247  result.prefix = name.substr (0, split + 1);
248  result.name = name.substr (split + 1);
249  return result;
250  }
251 
252 
253 
254 #ifdef XAOD_STANDALONE
255  namespace
256  {
270  constexpr bool noDictionaryFactories = false;
271 
272  StatusCode createComponent (std::unique_ptr<AsgComponent>& component,
273  const std::string& type,
274  const std::string& name,
275  const std::string& newCommand)
276  {
277  using namespace msgComponentConfig;
278 
279  const auto *factory = getComponentFactory (type);
280  if (factory)
281  {
282  ANA_MSG_DEBUG ("using registered factory for type " << type);
283  component = (*factory) (name);
284  if (component == nullptr)
285  {
286  ANA_MSG_ERROR ("factory for type " << type << " returned a null pointer");
287  return StatusCode::FAILURE;
288  }
289  return StatusCode::SUCCESS;
290  }
291 
292  if (noDictionaryFactories)
293  {
294  ANA_MSG_ERROR ("no component factory for type " << type << " (dictionary factories disabled)");
295  return StatusCode::FAILURE;
296  }
297 
298  ANA_MSG_DEBUG ("using dictionary as factory for type " << type);
299 
300  // Load the ROOT dictionary, this is needed to be able to
301  // instantiate the component below, i.e. the code below won't load
302  // dictionaries not already loaded
303  TClass* componentClass = TClass::GetClass (type.c_str());
304  if (!componentClass)
305  {
306  ATH_MSG_ERROR ("Unable to load class dictionary for type " << type);
307  return StatusCode::FAILURE;
308  }
309 
310  AsgComponent *comp = reinterpret_cast<AsgComponent*>
311  (gInterpreter->Calc(("dynamic_cast<asg::AsgComponent*>(" + (boost::format (newCommand) % type % name).str() + ")").c_str()));
312  if (comp == nullptr)
313  {
314  ANA_MSG_ERROR ("failed to create component of type " << type);
315  ANA_MSG_ERROR ("make sure you created a dictionary for your component");
316  return StatusCode::FAILURE;
317  }
318  component.reset (comp);
319 
320  return StatusCode::SUCCESS;
321  }
322  }
323 
324 
325 
326  template<> StatusCode AsgComponentConfig ::
327  makeComponentExpert<AsgComponent> (std::unique_ptr<AsgComponent>& component,
328  const std::string& newCommand,
329  bool nestedNames, std::string prefix) const
330  {
331  using namespace msgComponentConfig;
332 
333  ANA_CHECK (checkTypeName (nestedNames));
334 
335  std::string name = prefix + m_name;
336 
337  if (!createComponent (component, m_type, name, newCommand).isSuccess())
338  return StatusCode::FAILURE;
339 
340  for (auto& toolInfo : m_privateTools)
341  {
342  ToolHandle<AsgTool> th (toolInfo.first, component.get());
343  std::shared_ptr<void> mycleanup;
344  if (AsgToolConfig(toolInfo.second.m_config).makeTool (th, mycleanup).isFailure())
345  {
346  ANA_MSG_ERROR ("failed to create subtool \"" << toolInfo.first << "\" on component \"" << component->name() << "\"");
347  return StatusCode::FAILURE;
348  }
349  component->addCleanup (mycleanup);
350  if (toolInfo.second.m_propName.empty())
351  {
352  if (component->setProperty (toolInfo.first, th->name()).isFailure())
353  {
354  ANA_MSG_ERROR ("failed to set ToolHandle property \"" << toolInfo.first << "\" on component \"" << component->name() << "\"");
355  return StatusCode::FAILURE;
356  }
357  }
358  }
359 
360  for (const auto& toolArray : m_toolArrays)
361  {
362  std::vector<std::string> valueArray;
363  for (const auto& tool : toolArray.second)
364  valueArray.emplace_back (component->name() + "." + tool);
365  std::string valueString;
366  ANA_CHECK (asg::detail::GetCastStringHelper<std::vector<std::string>>::get (valueArray, valueString));
367  ANA_CHECK (component->setProperty (toolArray.first, valueString));
368  }
369 
370  for (auto& property : m_propertyValues)
371  {
372  ANA_CHECK (component->setProperty (property.first, property.second));
373  }
374 
375  ANA_MSG_DEBUG ("Created component of type " << m_type);
376  return StatusCode::SUCCESS;
377  }
378 
379 
380 
381 #else
382 
383 
384 
386  configureComponentExpert (const std::string& prefix,
387  bool nestedNames) const
388  {
389  using namespace msgComponentConfig;
390 
391  ANA_CHECK (checkTypeName (nestedNames));
392 
393  ServiceHandle<Gaudi::Interfaces::IOptionsSvc> joSvc("JobOptionsSvc","AsgComponentConfig");
394  ANA_CHECK (joSvc.retrieve());
395 
396  for (const auto& tool : m_privateTools)
397  {
398  ANA_CHECK (tool.second.m_config.configureComponentExpert (prefix + m_name + ".", true));
399  if (tool.second.m_propName.empty())
400  {
401  std::string toolPath = prefix + m_name + "." + tool.first;
402  joSvc->set (toolPath, tool.second.m_config.typeAndName());
403  }
404  }
405 
406  for (const auto& toolArray : m_toolArrays)
407  {
408  std::vector<std::string> valueArray;
409  for (const auto& tool : toolArray.second)
410  {
411  auto toolConfig = m_privateTools.find (tool);
412  if (toolConfig == m_privateTools.end())
413  {
414  ANA_MSG_ERROR ("Couldn't find private tool with name \"" << tool << "\"");
415  ANA_MSG_ERROR ("This is an internal inconsistency!");
416  return StatusCode::FAILURE;
417  }
418  valueArray.push_back (toolConfig->second.m_config.typeAndName());
419  }
420  std::string valueString = Gaudi::Utils::toString (valueArray);
421  std::string propertyPath = prefix + m_name + "." + toolArray.first;
422  joSvc->set (propertyPath, valueString);
423  }
424 
425  for (const auto& property : m_propertyValues)
426  {
427  std::string propertyPath = prefix + m_name + "." + property.first;
428  joSvc->set (propertyPath, property.second);
429  }
430 
431  return StatusCode::SUCCESS;
432  }
433 
434 #endif
435 }
plotting.yearwise_luminosity_vs_mu.comp
comp
Definition: yearwise_luminosity_vs_mu.py:23
asg::AsgComponentConfig
an object that stores the configuration for an AsgComponent and is able to create one from it
Definition: AsgComponentConfig.h:35
get_generator_info.result
result
Definition: get_generator_info.py:21
asg::AsgComponentConfig::setType
void setType(const std::string &val_type)
set the value of type
Definition: AsgComponentConfig.cxx:82
vtune_athena.format
format
Definition: vtune_athena.py:14
AsgComponentConfig.h
index
Definition: index.py:1
asg::AsgComponentConfig::empty
bool empty() const noexcept
whether all properties are unset
Definition: AsgComponentConfig.cxx:64
asg::AsgComponentConfig::m_propertyValues
std::map< std::string, std::string > m_propertyValues
the map of property values
Definition: AsgComponentConfig.h:291
asg
Definition: DataHandleTestTool.h:28
asg::AsgComponentConfig::m_name
std::string m_name
the value of name
Definition: AsgComponentConfig.h:281
ANA_MSG_ERROR
#define ANA_MSG_ERROR(xmsg)
Macro printing error messages.
Definition: Control/AthToolSupport/AsgMessaging/AsgMessaging/MessageCheck.h:294
athena.value
value
Definition: athena.py:124
ANA_CHECK
#define ANA_CHECK(EXP)
check whether the given expression was successful
Definition: Control/AthToolSupport/AsgMessaging/AsgMessaging/MessageCheck.h:324
const
bool const RAWDATA *ch2 const
Definition: LArRodBlockPhysicsV0.cxx:560
asg::AsgComponentConfig::m_toolArrays
std::map< std::string, std::vector< std::string > > m_toolArrays
the map of (private) tool handle arrays to manage, and the tools they contain
Definition: AsgComponentConfig.h:288
PrepareReferenceFile.regex
regex
Definition: PrepareReferenceFile.py:43
asg::AsgComponentConfig::AsgComponentConfig
AsgComponentConfig()=default
standard constructor
asg::AsgComponentConfig::m_type
std::string m_type
the value of type
Definition: AsgComponentConfig.h:278
python.TriggerHandler.th
th
Definition: TriggerHandler.py:295
Amg::toString
std::string toString(const Translation3D &translation, int precision=4)
GeoPrimitvesToStringConverter.
Definition: GeoPrimitivesToStringConverter.h:40
ATH_MSG_ERROR
#define ATH_MSG_ERROR(x)
Definition: AthMsgStreamMacros.h:33
asg::AsgComponentConfig::checkTypeName
StatusCode checkTypeName(bool nestedNames) const
check that the type and name members have the correct format
Definition: AsgComponentConfig.cxx:214
EL::StatusCode
::StatusCode StatusCode
StatusCode definition for legacy code.
Definition: PhysicsAnalysis/D3PDTools/EventLoop/EventLoop/StatusCode.h:22
python.CaloAddPedShiftConfig.str
str
Definition: CaloAddPedShiftConfig.py:42
AsgToolConfig.h
checkCorrelInHIST.prefix
dictionary prefix
Definition: checkCorrelInHIST.py:391
asg::AsgComponentConfig::addPrivateToolInArray
std::string addPrivateToolInArray(const std::string &name, AsgComponentConfig toolConfig)
the array version of addPrivateTool
Definition: AsgComponentConfig.cxx:189
asg::AsgComponentConfig::type
const std::string & type() const noexcept
the type of the component
Definition: AsgComponentConfig.cxx:74
AnaToolHandle.h
asg::AsgComponentConfig::createPrivateToolInArray
std::string createPrivateToolInArray(const std::string &name, const std::string &toolType)
the array version of createPrivateTool
Definition: AsgComponentConfig.cxx:159
asg::AsgComponentConfig::setTypeAndName
void setTypeAndName(const std::string &val_typeAndName)
set type and name at the same time
Definition: AsgComponentConfig.cxx:116
name
std::string name
Definition: Control/AthContainers/Root/debug.cxx:240
ActsTrk::to_string
std::string to_string(const DetectorType &type)
Definition: GeometryDefs.h:34
AtlCoolConsole.tool
tool
Definition: AtlCoolConsole.py:452
AsgComponent.h
asg::AsgComponentConfig::configureComponentExpert
StatusCode configureComponentExpert(const std::string &prefix, bool nestedNames) const
add component configuration to configuration service (expert only)
Definition: AsgComponentConfig.cxx:386
asg::AsgComponentConfig::AccessSubtoolData
access the configuration for the given subtool
Definition: AsgComponentConfig.h:309
asg::AsgComponentConfig::setName
void setName(const std::string &val_name)
set the value of name
Definition: AsgComponentConfig.cxx:98
asg::AsgComponentConfig::typeAndName
std::string typeAndName() const
get type and name at the same time
Definition: AsgComponentConfig.cxx:106
get
T * get(TKey *tobj)
get a TObject* from a TKey* (why can't a TObject be a TKey?)
Definition: hcg.cxx:127
asg::AsgComponentConfig::setPropertyFromString
void setPropertyFromString(const std::string &name, const std::string &value)
set a given property from a string value
Definition: AsgComponentConfig.cxx:133
python.DualUseConfig.createComponent
def createComponent(typeName, instanceName, componentType)
Definition: DualUseConfig.py:16
asg::AsgComponentConfig::name
const std::string & name() const noexcept
the name of the component
Definition: AsgComponentConfig.cxx:90
AsgComponentFactories.h
AsgTool.h
asg::AsgComponentConfig::addPrivateTool
StatusCode addPrivateTool(const std::string &name, AsgComponentConfig toolConfig)
add a private tool from the given configuration
Definition: AsgComponentConfig.cxx:168
asg::AsgComponentConfig::accessSubtool
AccessSubtoolData accessSubtool(const std::string &name, std::size_t split)
Definition: AsgComponentConfig.cxx:240
Trk::split
@ split
Definition: LayerMaterialProperties.h:38
asg::AsgComponentConfig::createPrivateTool
StatusCode createPrivateTool(const std::string &name, const std::string &toolType)
create a private tool of the given name and type
Definition: AsgComponentConfig.cxx:150
ServiceHandle< Gaudi::Interfaces::IOptionsSvc >
asg::AsgComponentConfig::m_privateTools
std::map< std::string, details::AsgComponentPrivateToolConfig > m_privateTools
the map of (private) tools to create
Definition: AsgComponentConfig.h:284
ANA_MSG_DEBUG
#define ANA_MSG_DEBUG(xmsg)
Macro printing debug messages.
Definition: Control/AthToolSupport/AsgMessaging/AsgMessaging/MessageCheck.h:288