28 #include <boost/program_options.hpp>
29 #include <boost/algorithm/string/predicate.hpp>
84 namespace po = boost::program_options;
85 namespace fs = boost::filesystem;
86 using namespace SourceXtractor;
87 using namespace Euclid::Configuration;
99 m_list.push_back(group);
108 m_list.push_back(source);
125 ::setenv(
"LC_ALL",
"C", 1);
139 std::make_shared<SourceWithOnDemandPropertiesFactory>(task_provider);
141 std::make_shared<SourceGroupWithOnDemandPropertiesFactory>(task_provider);
148 bool config_initialized =
false;
154 : plugin_manager { task_factory_registry, output_registry,
config_manager_id, plugin_path, plugin_list } {
161 if (!config_initialized) {
173 plugin_manager.loadPlugins();
174 task_factory_registry->reportConfigDependencies(config_manager);
175 segmentation_factory.reportConfigDependencies(config_manager);
176 partition_factory.reportConfigDependencies(config_manager);
177 grouping_factory.reportConfigDependencies(config_manager);
178 deblending_factory.reportConfigDependencies(config_manager);
179 measurement_factory.reportConfigDependencies(config_manager);
180 output_factory.reportConfigDependencies(config_manager);
182 config_parameters.add(config_manager.closeRegistration());
183 config_initialized =
true;
185 return config_parameters;
190 auto options = getConfigParameters();
193 "List the possible output properties for the given input parameters and exit");
195 "Show the columns created for each property");
197 "Show the columns created for each property, for the given configuration");
199 "Dump parameters with default values into a configuration file");
200 progress_printer_factory.addOptions(options);
203 po::positional_options_description p;
204 p.add(
"python-arg", -1);
210 template <
typename T>
212 out << opt.long_name() <<
'=' << boost::any_cast<T>(default_value) <<
std::endl;
216 template <
typename T>
219 if (values.empty()) {
220 out << opt.long_name() <<
'=' <<
std::endl;
223 for (
const auto& v : values)
224 out << opt.long_name() <<
'=' << v <<
std::endl;
232 {
typeid(bool), &writeDefault<bool>},
233 {
typeid(int), &writeDefault<int>},
234 {
typeid(double), &writeDefault<double>},
238 decltype(printers)::const_iterator printer;
240 auto config_parameters = getConfigParameters();
241 for (
const auto& p : config_parameters.options()) {
242 boost::any default_value;
245 if (!p->semantic()->apply_default(default_value)) {
248 else if ((printer = printers.find(default_value.type())) == printers.end()) {
249 std::cout <<
'#' << p->long_name() <<
"=<Unknown type " << default_value.type().name() <<
'>' <<
std::endl;
252 printer->second(
std::cout, *p, default_value);
270 for (
auto& name : output_registry->getOutputPropertyNames()) {
277 output_registry->printPropertyColumnMap();
288 if (args.
find(
"config-file") != args.
end()) {
289 auto cfg_file = args.
at(
"config-file").as<fs::path>();
290 if (cfg_file !=
"" && !fs::exists(cfg_file)) {
291 throw Elements::Exception() <<
"The configuration file '" << cfg_file <<
"' does not exist";
296 progress_printer_factory.configure(args);
297 auto progress_mediator = progress_printer_factory.createProgressMediator();
301 config_manager.initialize(args);
304 auto memory_config = config_manager.getConfiguration<
MemoryConfig>();
306 memory_config.getTileSize(), memory_config.getTileMaxMemory());
310 task_factory_registry->configure(config_manager);
311 task_factory_registry->registerPropertyInstances(*output_registry);
313 segmentation_factory.configure(config_manager);
314 partition_factory.configure(config_manager);
315 grouping_factory.configure(config_manager);
316 deblending_factory.configure(config_manager);
317 measurement_factory.configure(config_manager);
318 output_factory.configure(config_manager);
325 auto detection_image = config_manager.getConfiguration<
DetectionImageConfig>().getDetectionImage();
326 auto detection_image_path = config_manager.getConfiguration<
DetectionImageConfig>().getDetectionImagePath();
327 auto weight_image = config_manager.getConfiguration<
WeightImageConfig>().getWeightImage();
328 bool is_weight_absolute = config_manager.getConfiguration<
WeightImageConfig>().isWeightAbsolute();
329 auto weight_threshold = config_manager.getConfiguration<
WeightImageConfig>().getWeightThreshold();
331 auto detection_image_coordinate_system = config_manager.getConfiguration<
DetectionImageConfig>().getCoordinateSystem();
333 auto detection_image_saturation = config_manager.getConfiguration<
DetectionImageConfig>().getSaturation();
335 auto segmentation = segmentation_factory.createSegmentation();
339 auto prefetcher = std::make_shared<Prefetcher>(multithreading_config.getThreadPool());
342 auto partition = partition_factory.getPartition();
343 auto source_grouping = grouping_factory.createGrouping();
344 prefetcher->requestProperties(source_grouping->requiredProperties());
350 prefetcher->requestProperties(deblending->requiredProperties());
352 auto sorter = std::make_shared<Sorter>();
356 segmentation->Observable<ProcessSourcesEvent>::addObserver(prefetcher);
357 prefetcher->Observable<ProcessSourcesEvent>::addObserver(source_grouping);
358 partition->addObserver(prefetcher);
360 source_grouping->addObserver(deblending);
361 deblending->addObserver(measurement);
362 measurement->addObserver(sorter);
363 sorter->addObserver(output);
365 segmentation->Observable<SegmentationProgress>::addObserver(progress_mediator->getSegmentationObserver());
367 deblending->addObserver(progress_mediator->getDeblendingObserver());
368 measurement->addObserver(progress_mediator->getMeasurementObserver());
373 std::make_shared<DetectionIdCheckImage>());
376 measurement->addObserver(
377 std::make_shared<SourceIdCheckImage>());
380 measurement->addObserver(
381 std::make_shared<GroupIdCheckImage>());
384 measurement->addObserver(
385 std::make_shared<MoffatCheckImage>());
388 auto interpolation_gap = config_manager.getConfiguration<
DetectionImageConfig>().getInterpolationGap();
389 auto detection_frame = std::make_shared<DetectionImageFrame>(detection_image, weight_image,
390 weight_threshold, detection_image_coordinate_system, detection_image_gain,
391 detection_image_saturation, interpolation_gap);
392 detection_frame->setLabel(boost::filesystem::basename(detection_image_path));
395 auto background_model = background_analyzer->analyzeBackground(detection_frame->getOriginalImage(), weight_image,
402 detection_frame->setBackgroundLevel(background_model.getLevelMap(), background_model.getMedianRms());
404 if (weight_image !=
nullptr) {
405 if (is_weight_absolute) {
406 detection_frame->setVarianceMap(weight_image);
409 detection_frame->setVarianceMap(scaled_image);
412 detection_frame->setVarianceMap(background_model.getVarianceMap());
417 const auto& background_config = config_manager.getConfiguration<
BackgroundConfig>();
420 if (background_config.isBackgroundLevelAbsolute()) {
422 detection_image->getWidth(), detection_image->getHeight(), background_config.getBackgroundLevel());
424 detection_frame->setBackgroundLevel(background, 0.);
428 if (background_config.isDetectionThresholdAbsolute()) {
429 detection_frame->setDetectionThreshold(background_config.getDetectionThreshold());
436 measurement->startThreads();
440 segmentation->processFrame(detection_frame);
443 logger.error() <<
"Failed to process the frame! " << e.
what();
444 measurement->waitForThreads();
449 measurement->waitForThreads();
458 size_t n_writen_rows = output->flush();
460 progress_mediator->done();
462 if (n_writen_rows > 0) {
463 logger.info() << n_writen_rows <<
" sources detected";
465 logger.info() <<
"NO SOURCES DETECTED";
477 m_plugin_path(plugin_path), m_plugin_list(plugin_list) {
485 auto options = config_manager.closeRegistration();
487 options.add_options()(
"*", po::value<std::vector<std::string>>());
493 config_manager.initialize(args);
494 auto& conf = config_manager.getConfiguration<
PluginConfig>();
496 m_plugin_list = conf.getPluginList();
510 for (
int i = 0; i < argc; ++i) {
512 if (option ==
"--config-file") {
516 if (boost::starts_with(option,
"--config-file=")) {
519 if (option ==
"--plugin-directory") {
520 plugin_options_input.
emplace_back(
"--plugin-directory");
523 if (boost::starts_with(option,
"--plugin-directory=")) {
526 if (option ==
"--plugin") {
530 if (boost::starts_with(option,
"--plugin=")) {
543 if (local_env[
"ELEMENTS_CONF_PATH"].empty()) {
544 local_env[
"ELEMENTS_CONF_PATH"] =
".:/etc";
546 local_env[
"ELEMENTS_CONF_PATH"] =
".:" + local_env[
"ELEMENTS_CONF_PATH"] +
":/etc";
563 plugin_options_input.emplace_back(
"--log-level");
564 plugin_options_input.emplace_back(
"ERROR");
567 int argc_tmp = plugin_options_input.size();
569 for (
unsigned int i = 0; i < plugin_options_input.size(); ++i) {
570 auto& option_str = plugin_options_input[i];
571 argv_tmp[i] = option_str.
data();
575 plugin_options_program.run(argc_tmp, const_cast<char **>(argv_tmp.
data()));
586 logger.fatal() <<
"Unknown exception type!";
587 logger.fatal() <<
"Please, report this as a bug";
T set_terminate(T...args)
std::list< std::shared_ptr< SourceWithOnDemandProperties > > m_list
PluginManager plugin_manager
SEMain(const std::string &plugin_path, const std::vector< std::string > &plugin_list)
std::string & m_plugin_path
static ConfigManager & getInstance(long id)
void printDefaults()
Print a configuration file populated with defaults.
static void onTerminate() noexcept
std::pair< po::options_description, po::positional_options_description > defineProgramArguments() override
Return the arguments that the program accepts.
std::list< std::shared_ptr< SourceGroupInterface > > m_list
PluginOptionsMain(std::string &plugin_path, std::vector< std::string > &plugin_list)
virtual void handleMessage(const std::shared_ptr< SourceWithOnDemandProperties > &source) override
po::options_description config_parameters
boost::program_options::options_description defineSpecificProgramOptions() override
Elements::ExitCode mainMethod(std::map< std::string, po::variable_value > &args) override
long getUniqueManagerId()
std::underlying_type< ExitCode >::type ExitCodeType
po::options_description getConfigParameters()
static void writeDefaultMultiple(std::ostream &out, const po::option_description &opt, const boost::any &default_value)
Print a multiple-value option.
static void writeDefault(std::ostream &out, const po::option_description &opt, const boost::any &default_value)
Print a simple option.
Elements::ExitCode mainMethod(std::map< std::string, boost::program_options::variable_value > &args) override
virtual void handleMessage(const std::shared_ptr< SourceGroupInterface > &group) override
static Logging getLogger(const std::string &name="")
std::vector< std::string > & m_plugin_list
#define CREATE_MANAGER_WITH_ARGS(MANAGER, ELEMENTS_PROGRAM,...)