Public Member Functions | Private Attributes | List of all members
WireCell::Main Class Reference

#include <Main.h>

Public Member Functions

 Main ()
 
 ~Main ()
 
int cmdline (int argc, char *argv[])
 
void add_app (const std::string &tn)
 
void add_config (const std::string &filename)
 
void add_var (const std::string &name, const std::string &value)
 
void add_code (const std::string &name, const std::string &value)
 
void add_path (const std::string &dirname)
 
void add_plugin (const std::string &libname)
 
void add_logsink (const std::string &log, const std::string &level="")
 Add a log sink, reserved names 'stdout' and 'stderr' or a filename. More...
 
void set_loglevel (const std::string &log, const std::string &level="")
 
void initialize ()
 
void operator() ()
 Run any and all application components once. More...
 

Private Attributes

ConfigManager m_cfgmgr
 
std::vector< std::stringm_plugins
 
std::vector< std::stringm_apps
 
std::vector< std::stringm_cfgfiles
 
std::vector< std::stringm_load_path
 
Persist::externalvars_t m_extvars
 
Persist::externalvars_t m_extcode
 
Log::logptr_t l
 

Detailed Description

Definition at line 23 of file Main.h.

Constructor & Destructor Documentation

Main::Main ( )

Definition at line 27 of file Main.cxx.

28  : l(Log::logger("main"))
29 {
30 }
logptr_t logger(std::string name)
Definition: Logging.cxx:71
Log::logptr_t l
Definition: Main.h:90
Main::~Main ( )

Definition at line 32 of file Main.cxx.

33 {
34 }

Member Function Documentation

void Main::add_app ( const std::string tn)

Individual setup methods called by cmdline() or called explicitly by external application/frameork: Add an IApplication component to execute as a type:name string.

Definition at line 142 of file Main.cxx.

143 {
144  m_apps.push_back(tn);
145 }
std::vector< std::string > m_apps
Definition: Main.h:88
void Main::add_code ( const std::string name,
const std::string value 
)

Bind external configuration code (in Jsonnet language) to a variable so that its may be referenced the configuration files (via std.extVar())

Definition at line 173 of file Main.cxx.

174 {
175  m_extcode[name] = value;
176 }
static QCString name
Definition: declinfo.cpp:673
Persist::externalvars_t m_extcode
Definition: Main.h:89
const GenericPointer< typename T::ValueType > T2 value
Definition: pointer.h:1225
void Main::add_config ( const std::string filename)

Append a top-level JSON/Jsonnet configuration file to the configuration sequence.

Definition at line 163 of file Main.cxx.

164 {
165  m_cfgfiles.push_back(filename);
166 }
std::vector< std::string > m_cfgfiles
Definition: Main.h:88
string filename
Definition: train.py:213
void Main::add_logsink ( const std::string log,
const std::string level = "" 
)

Add a log sink, reserved names 'stdout' and 'stderr' or a filename.

Definition at line 147 of file Main.cxx.

148 {
149  if (log == "stdout") {
150  Log::add_stdout(true, level);
151  return;
152  }
153  if (log == "stderr") {
154  Log::add_stderr(true, level);
155  return;
156  }
158 }
void add_stdout(bool color=true, std::string level="")
Definition: Logging.cxx:48
void add_stderr(bool color=true, std::string level="")
Definition: Logging.cxx:59
void log(source_loc source, level::level_enum lvl, const char *fmt, const Args &...args)
Definition: spdlog.h:165
void add_file(std::string filename, std::string level="")
Definition: Logging.cxx:42
void Main::add_path ( const std::string dirname)

Add an element to the configuration path in which configuration files may be found.

Definition at line 178 of file Main.cxx.

179 {
180  m_load_path.push_back(dirname);
181 }
std::vector< std::string > m_load_path
Definition: Main.h:88
void Main::add_plugin ( const std::string libname)

Add a plugin library in which components may be found. The libname may lack the initial "lib" prefix and file extension.

Definition at line 137 of file Main.cxx.

138 {
139  m_plugins.push_back(libname);
140 }
std::vector< std::string > m_plugins
Definition: Main.h:88
void Main::add_var ( const std::string name,
const std::string value 
)

Bind an external scalar value to a variable so that it may be referenced in the configuration files (via std.extVar()).

Definition at line 168 of file Main.cxx.

169 {
170  m_extvars[name] = value;
171 }
static QCString name
Definition: declinfo.cpp:673
const GenericPointer< typename T::ValueType > T2 value
Definition: pointer.h:1225
Persist::externalvars_t m_extvars
Definition: Main.h:89
int Main::cmdline ( int  argc,
char *  argv[] 
)

Single-point entry to Wire Cell.

Pass in literal command line arguments and return a return code. See wire-cell --help for args.

Or, one can use subsequent methods for more fine-grained setup and execution.

Definition at line 38 of file Main.cxx.

39 {
40  po::options_description desc("Options");
41  desc.add_options()
42  ("help,h", "wire-cell [options] [arguments]")
43  ("logsink,l", po::value< vector<string> >(),"log sink, filename or 'stdout' or 'stderr', if added ':level' then set a log level for the sink")
44  ("loglevel,L", po::value< vector<string> >(),"set lowest log level for a log in form 'name:level' or just 'level' for all (level one of critical,error,warn,info,debug,trace)")
45  ("app,a", po::value< vector<string> >(),"application component to invoke")
46  ("config,c", po::value< vector<string> >(),"provide a configuration file")
47  ("plugin,p", po::value< vector<string> >(),"specify a plugin as name[:lib]")
48 // ("jsonpath,j", po::value< vector<string> >(),"specify a JSON path=value")
49  ("ext-str,V", po::value< vector<string> >(),"specify a Jsonnet external variable=value")
50  ("ext-code,C", po::value< vector<string> >(),"specify a Jsonnet external variable=code")
51  ("path,P", po::value< vector<string> >(),"add to JSON/Jsonnet search path")
52  ;
53 
54  po::variables_map opts;
55  po::store(po::parse_command_line(argc, argv, desc), opts);
56  po::notify(opts);
57 
58  if (opts.count("help")) {
59  std::cout << desc << "\n";
60  return 1;
61  }
62 
63  if (opts.count("config")) {
64  for (auto fname : opts["config"].as< vector<string> >()) {
66  }
67  }
68 
69  if (opts.count("path")) {
70  for (auto path : opts["path"].as< vector<string> >()) {
71  add_path(path);
72  }
73  }
74 
75  // Get any external variables
76  if (opts.count("ext-str")) {
77  for (auto vev : opts["ext-str"].as< vector<string> >()) {
78  auto vv = String::split(vev, "=");
79  add_var(vv[0], vv[1]);
80  }
81  }
82  // And any external code
83  if (opts.count("ext-code")) {
84  for (auto vev : opts["ext-code"].as< vector<string> >()) {
85  auto vv = String::split(vev, "=");
86  add_code(vv[0], vv[1]);
87  }
88  }
89  // fixme: these aren't yet supported.
90  // if (opts.count("jsonpath")) {
91  // jsonpath_vars = opts["jsonpath"].as< vector<string> >();
92  // }
93 
94 
95  if (opts.count("plugin")) {
96  for (auto plugin : opts["plugin"].as< vector<string> >()) {
97  add_plugin(plugin);
98  }
99  }
100  if (opts.count("app")) {
101  for (auto app : opts["app"].as< vector<string> >()) {
102  add_app(app);
103  }
104  }
105  if (opts.count("logsink")) {
106  for (auto ls : opts["logsink"].as< vector<string> >()) {
107  auto ll = String::split(ls, ":");
108  if (ll.size() == 1) {
109  add_logsink(ll[0]);
110  }
111  if (ll.size() == 2) {
112  add_logsink(ll[0], ll[1]);
113  }
114  }
115  }
116 
117  if (opts.count("loglevel")) {
118  for (auto ll : opts["loglevel"].as< vector<string> >()) {
119  auto lal = String::split(ll, ":");
120  if (lal.size() == 2) {
121  set_loglevel(lal[0], lal[1]);
122  }
123  else{
124  set_loglevel("", lal[0]);
125  }
126  }
127  }
128 
129  // Maybe make this cmdline configurable. For now, set all
130  // backends the same.
131  Log::set_pattern("[%H:%M:%S.%03e] %L [%^%=8n%$] %v");
132 
133  return 0;
134 }
void add_code(const std::string &name, const std::string &value)
Definition: Main.cxx:173
void add_logsink(const std::string &log, const std::string &level="")
Add a log sink, reserved names &#39;stdout&#39; and &#39;stderr&#39; or a filename.
Definition: Main.cxx:147
void set_pattern(std::string pattern, std::string which="")
Definition: Logging.cxx:100
format_arg_store< context, Args... > as
Definition: format.h:3345
void add_config(const std::string &filename)
Definition: Main.cxx:163
void add_path(const std::string &dirname)
Definition: Main.cxx:178
void add_var(const std::string &name, const std::string &value)
Definition: Main.cxx:168
void add_app(const std::string &tn)
Definition: Main.cxx:142
const GenericPointer< typename T::ValueType > T2 value
Definition: pointer.h:1225
opts
Definition: ECLAPI.py:240
void add_plugin(const std::string &libname)
Definition: Main.cxx:137
std::vector< std::string > split(const std::string &in, const std::string &delim=":")
Definition: String.cxx:5
void set_loglevel(const std::string &log, const std::string &level="")
Definition: Main.cxx:159
void Main::initialize ( )

Call once after all setup has been done and before running.

Definition at line 184 of file Main.cxx.

185 {
186  for (auto filename : m_cfgfiles) {
187  l->info("loading config file {} ...", filename);
189  Json::Value one = p.load(filename); // throws
190  m_cfgmgr.extend(one);
191  l->info("...done");
192  }
193 
194 
195  // Find if we have our special configuration entry
196  int ind = m_cfgmgr.index("wire-cell");
197  Configuration main_cfg = m_cfgmgr.pop(ind);
198  if (! main_cfg.isNull()) {
199  for (auto plugin : get< vector<string> >(main_cfg, "data.plugins")) {
200  l->info("config requests plugin: \"{}\"", plugin);
201  m_plugins.push_back(plugin);
202  }
203  for (auto app : get< vector<string> >(main_cfg, "data.apps")) {
204  l->info("config requests app: \"{}\"", app);
205  m_apps.push_back(app);
206  }
207  }
208 
209 
210  // Load any plugin shared libraries requested by user.
212  for (auto plugin : m_plugins) {
213  string pname, lname;
214  std::tie(pname, lname) = String::parse_pair(plugin);
215  l->info("adding plugin: \"{}\"", plugin);
216  if (lname.size()) {
217  l->info("\t from library \"{}\"", lname);
218  }
219  pm.add(pname, lname);
220  }
221 
222 
223  // Apply any user configuration. This is a two step. First, just
224  // assure all the components referenced in the configuration
225  // sequence can be instantiated. Then, find them again and
226  // actually configure them. This way, any problems fails fast.
227 
228  for (auto c : m_cfgmgr.all()) {
229  if (c.isNull()) {
230  continue; // allow and ignore any totally empty configurations
231  }
232  if (c["type"].isNull()) {
233  l->critical("all configuration must have a type attribute, got: {}", c);
234  THROW(ValueError() << errmsg{"got configuration sequence element lacking a type"});
235  }
236  string type = get<string>(c, "type");
237  string name = get<string>(c, "name");
238  l->info("constructing component: \"{}\":\"{}\"", type, name);
239  auto iface = Factory::lookup<Interface>(type, name); // throws
240  }
241  for (auto c : m_apps) {
242  l->info("constructing app: \"{}\"",c);
243  Factory::lookup_tn<IApplication>(c);
244  }
245  for (auto c : m_cfgmgr.all()) {
246  if (c.isNull()) {
247  continue; // allow and ignore any totally empty configurations
248  }
249  string type = get<string>(c, "type");
250  string name = get<string>(c, "name");
251  l->info("configuring component: \"{}\":\"{}\"", type, name);
252  auto cfgobj = Factory::find_maybe<IConfigurable>(type, name); // doesn't throw.
253  if (!cfgobj) {
254  continue;
255  }
256 
257  // Get component's hard-coded default config, update it with
258  // anything the user may have provided and apply it.
259  Configuration cfg = cfgobj->default_configuration();
260  cfg = update(cfg, c["data"]);
261  cfgobj->configure(cfg); // throws
262  }
263 }
static QCString name
Definition: declinfo.cpp:673
std::vector< std::string > m_cfgfiles
Definition: Main.h:88
Configuration update(Configuration &a, Configuration &b)
Merge dictionary b into a, return a.
boost::error_info< struct tag_errmsg, std::string > errmsg
Definition: Exceptions.h:54
std::pair< std::string, std::string > parse_pair(const std::string &in, const std::string &delim=":")
Definition: String.cxx:15
std::vector< std::string > m_plugins
Definition: Main.h:88
cfg
Definition: dbjson.py:29
Persist::externalvars_t m_extcode
Definition: Main.h:89
string filename
Definition: train.py:213
static PluginManager & instance()
void extend(Configuration more)
Extend current list of configuration objects with more.
Configuration all() const
Return top-level, aggregate configuration.
Definition: ConfigManager.h:37
std::vector< std::string > m_apps
Definition: Main.h:88
GenericValue< UTF8<> > Value
GenericValue with UTF8 encoding.
Definition: document.h:2106
#define THROW(e)
Definition: Exceptions.h:25
Thrown when a wrong value has been encountered.
Definition: Exceptions.h:37
std::vector< std::string > m_load_path
Definition: Main.h:88
int index(const std::string &type, const std::string &name="") const
p
Definition: test.py:223
std::string type(const T &t)
Definition: Type.h:20
ConfigManager m_cfgmgr
Definition: Main.h:87
Json::Value Configuration
Definition: Configuration.h:50
Plugin * add(const std::string &plugin_name, const std::string &libname="")
Add a plugin. If libname is not given, try to derive it.
Persist::externalvars_t m_extvars
Definition: Main.h:89
Log::logptr_t l
Definition: Main.h:90
Configuration pop(int ind)
Remove configuration at given index and return it.
void Main::operator() ( void  )

Run any and all application components once.

Definition at line 265 of file Main.cxx.

266 {
267  // Find all IApplications to execute
268  vector<IApplication::pointer> app_objs;
269  for (auto component : m_apps) {
270  string type, name;
271  std::tie(type,name) = String::parse_pair(component);
272  auto a = Factory::find<IApplication>(type,name); // throws
273  app_objs.push_back(a);
274  }
275  l->debug("executing {} apps:", m_apps.size());
276  for (size_t ind=0; ind < m_apps.size(); ++ind) {
277  auto aobj = app_objs[ind];
278  l->debug("executing app: \"{}\"", m_apps[ind]);
279  aobj->execute(); // throws
280  }
281 }
static QCString name
Definition: declinfo.cpp:673
std::pair< std::string, std::string > parse_pair(const std::string &in, const std::string &delim=":")
Definition: String.cxx:15
std::vector< std::string > m_apps
Definition: Main.h:88
const GenericPointer< typename T::ValueType > T2 T::AllocatorType & a
Definition: pointer.h:1124
std::string type(const T &t)
Definition: Type.h:20
Log::logptr_t l
Definition: Main.h:90
void Main::set_loglevel ( const std::string log,
const std::string level = "" 
)

Set a minimum level to emit a message for a given log. (levels: critical, error, warn, info, debug, trace).

Definition at line 159 of file Main.cxx.

160 {
162 }
void set_level(std::string level, std::string which="")
Definition: Logging.cxx:90
void log(source_loc source, level::level_enum lvl, const char *fmt, const Args &...args)
Definition: spdlog.h:165

Member Data Documentation

Log::logptr_t WireCell::Main::l
private

Definition at line 90 of file Main.h.

std::vector<std::string> WireCell::Main::m_apps
private

Definition at line 88 of file Main.h.

std::vector<std::string> WireCell::Main::m_cfgfiles
private

Definition at line 88 of file Main.h.

ConfigManager WireCell::Main::m_cfgmgr
private

Definition at line 87 of file Main.h.

Persist::externalvars_t WireCell::Main::m_extcode
private

Definition at line 89 of file Main.h.

Persist::externalvars_t WireCell::Main::m_extvars
private

Definition at line 89 of file Main.h.

std::vector<std::string> WireCell::Main::m_load_path
private

Definition at line 88 of file Main.h.

std::vector<std::string> WireCell::Main::m_plugins
private

Definition at line 88 of file Main.h.


The documentation for this class was generated from the following files: