File indexing completed on 2025-07-05 09:14:47
0001
0002
0003
0004
0005
0006 #pragma once
0007 #include <JANA/JApplication.h>
0008 #include <JANA/Components/JComponentFwd.h>
0009 #include <JANA/Utils/JTypeInfo.h>
0010
0011 namespace jana::components {
0012
0013 template <typename T>
0014 class JComponent::ParameterRef : public JComponent::ParameterBase {
0015
0016 T* m_data;
0017
0018 public:
0019 ParameterRef(JComponent* owner, std::string name, T& slot, std::string description="", bool is_shared=false) {
0020 owner->RegisterParameter(this);
0021 this->m_name = name;
0022 this->m_description = description;
0023 this->m_is_shared = is_shared;
0024 m_data = &slot;
0025 }
0026
0027 void SetRef(T* slot) { m_data = slot; }
0028
0029 const T& operator()() { return *m_data; }
0030 const T& operator*() { return *m_data; }
0031
0032 protected:
0033
0034 void Init(JParameterManager& parman, const std::string& prefix) override {
0035 if (m_is_shared || prefix.empty()) {
0036 parman.SetDefaultParameter(this->m_name, *m_data, this->m_description);
0037 }
0038 else {
0039 parman.SetDefaultParameter(prefix + ":" + this->m_name, *m_data, this->m_description);
0040 }
0041 }
0042 void Wire(const std::map<std::string, std::string>& isolated, const std::map<std::string, std::string>& shared) override {
0043 if (m_is_shared) {
0044 auto it = shared.find(this->m_name);
0045 if (it != shared.end()) {
0046 const auto& value_str = it->second;
0047 JParameterManager::Parse(value_str, *m_data);
0048 }
0049 }
0050 else {
0051 auto it = isolated.find(this->m_name);
0052 if (it != isolated.end()) {
0053 const auto& value_str = it->second;
0054 JParameterManager::Parse(value_str, *m_data);
0055 }
0056 }
0057 }
0058 };
0059
0060 template <typename T>
0061 class JComponent::Parameter : public JComponent::ParameterBase {
0062
0063 T m_data;
0064
0065 public:
0066 Parameter(JComponent* owner, std::string name, T default_value, std::string description="", bool is_shared=false) {
0067 owner->RegisterParameter(this);
0068 this->m_name = name;
0069 this->m_description = description;
0070 this->m_is_shared = is_shared;
0071 m_data = default_value;
0072 }
0073
0074 const T& operator()() { return m_data; }
0075 const T& operator*() { return m_data; }
0076
0077 protected:
0078
0079 void Init(JParameterManager& parman, const std::string& prefix) override {
0080 if (m_is_shared || prefix.empty()) {
0081 parman.SetDefaultParameter(this->m_name, m_data, this->m_description);
0082 }
0083 else {
0084 parman.SetDefaultParameter(prefix + ":" + this->m_name, m_data, this->m_description);
0085 }
0086 }
0087 void Wire(const std::map<std::string, std::string>& isolated, const std::map<std::string, std::string>& shared) override {
0088 if (m_is_shared) {
0089 auto it = shared.find(this->m_name);
0090 if (it != shared.end()) {
0091 const auto& value_str = it->second;
0092 JParameterManager::Parse(value_str, m_data);
0093 }
0094 }
0095 else {
0096 auto it = isolated.find(this->m_name);
0097 if (it != isolated.end()) {
0098 const auto& value_str = it->second;
0099 JParameterManager::Parse(value_str, m_data);
0100 }
0101 }
0102 }
0103 };
0104
0105
0106 template <typename ServiceT>
0107 class JComponent::Service : public JComponent::ServiceBase {
0108
0109 std::shared_ptr<ServiceT> m_data;
0110
0111 public:
0112
0113 Service(JComponent* owner) {
0114 owner->RegisterService(this);
0115 }
0116
0117 ServiceT& operator()() {
0118 if (m_data == nullptr) {
0119 throw JException("Attempted to access a Service which hasn't been attached to this Component yet!");
0120 }
0121 return *m_data;
0122 }
0123
0124 ServiceT* operator->() {
0125 if (m_data == nullptr) {
0126 throw JException("Attempted to access a Service which hasn't been attached to this Component yet!");
0127 }
0128 return m_data.get();
0129 }
0130
0131 protected:
0132
0133 void Fetch(JApplication* app) {
0134 m_data = app->GetService<ServiceT>();
0135 }
0136 };
0137
0138
0139 template <typename F>
0140 inline void JComponent::CallWithJExceptionWrapper(std::string func_name, F func) {
0141 try {
0142 func();
0143 }
0144 catch (JException& ex) {
0145 if (ex.function_name.empty()) ex.function_name = func_name;
0146 if (ex.type_name.empty()) ex.type_name = m_type_name;
0147 if (ex.instance_name.empty()) ex.instance_name = m_prefix;
0148 if (ex.plugin_name.empty()) ex.plugin_name = m_plugin_name;
0149 throw ex;
0150 }
0151 catch (std::exception& e) {
0152 auto ex = JException(e.what());
0153 ex.exception_type = JTypeInfo::demangle_current_exception_type();
0154 ex.nested_exception = std::current_exception();
0155 ex.function_name = func_name;
0156 ex.type_name = m_type_name;
0157 ex.instance_name = m_prefix;
0158 ex.plugin_name = m_plugin_name;
0159 throw ex;
0160 }
0161 catch (...) {
0162 auto ex = JException("Unknown exception");
0163 ex.exception_type = JTypeInfo::demangle_current_exception_type();
0164 ex.nested_exception = std::current_exception();
0165 ex.function_name = func_name;
0166 ex.type_name = m_type_name;
0167 ex.instance_name = m_prefix;
0168 ex.plugin_name = m_plugin_name;
0169 throw ex;
0170 }
0171 }
0172
0173
0174 }
0175
0176