9 #include "quill/core/Attributes.h" 10 #include "quill/core/Common.h" 11 #include "quill/core/LogLevel.h" 12 #include "quill/core/LoggerBase.h" 13 #include "quill/core/PatternFormatterOptions.h" 14 #include "quill/core/Spinlock.h" 19 #include <initializer_list> 22 #include <string_view> 47 QUILL_NODISCARD
LoggerBase* get_logger(std::string
const& logger_name)
const 50 LoggerBase* logger = _find_logger(logger_name);
55 QUILL_NODISCARD std::vector<LoggerBase*> get_all_loggers()
const 59 std::vector<LoggerBase*> loggers;
61 for (
auto const& elem : _loggers)
64 if (elem->is_valid_logger())
66 loggers.push_back(elem.get());
74 QUILL_NODISCARD
LoggerBase* get_valid_logger(std::string_view exclude_logger_substr = {})
const 79 for (
auto const& elem : _loggers)
82 if (elem->is_valid_logger())
85 if (exclude_logger_substr.empty() ||
86 elem->get_logger_name().find(exclude_logger_substr) == std::string::npos)
98 QUILL_NODISCARD
LoggerBase* get_valid_logger(std::vector<std::string>
const& exclude_logger_substrs)
const 101 for (
auto const& elem : _loggers)
103 if (elem->is_valid_logger())
105 bool excluded =
false;
106 for (
auto const& exclude_substr : exclude_logger_substrs)
108 if (!exclude_substr.empty() && elem->get_logger_name().find(exclude_substr) != std::string::npos)
125 QUILL_NODISCARD
size_t get_number_of_loggers()
const noexcept
128 return _loggers.size();
134 template <
typename TCallback>
139 for (
auto const& elem : _loggers)
152 template <
typename TLogger>
153 LoggerBase* create_or_get_logger(std::string
const& logger_name, std::vector<std::shared_ptr<Sink>> sinks,
159 LoggerBase* logger_ptr = _find_logger(logger_name);
164 std::unique_ptr<LoggerBase> new_logger{
165 new TLogger{logger_name,
static_cast<std::vector<std::shared_ptr<Sink>
>&&>(sinks),
166 pattern_formatter_options, clock_source, user_clock}};
168 _insert_logger(
static_cast<std::unique_ptr<LoggerBase>&&
>(new_logger));
173 logger_ptr = _find_logger(logger_name);
175 if (logger_ptr && _env_log_level)
181 QUILL_ASSERT(logger_ptr,
"logger_ptr is nullptr in LoggerManager::get_logger()");
183 "logger is not valid in LoggerManager::get_logger()");
188 template <
typename TLogger>
193 return get_logger(logger_name);
196 return create_or_get_logger<TLogger>(logger_name, source_logger->_sinks, source_logger->_pattern_formatter_options,
197 source_logger->_clock_source, source_logger->_user_clock);
204 _has_invalidated_loggers.store(
true, std::memory_order_release);
208 template <
typename TCheckQueuesEmpty>
209 void cleanup_invalidated_loggers(TCheckQueuesEmpty check_queues_empty, std::vector<std::string>& removed_loggers)
211 if (_has_invalidated_loggers.load(std::memory_order_acquire))
213 _has_invalidated_loggers.store(
false, std::memory_order_release);
216 for (
auto it = _loggers.begin(); it != _loggers.end();)
218 if (!it->get()->is_valid_logger())
221 if (!check_queues_empty())
225 _has_invalidated_loggers.store(
true, std::memory_order_release);
229 removed_loggers.push_back(it->get()->get_logger_name());
230 it = _loggers.erase(it);
242 QUILL_NODISCARD
bool has_invalidated_loggers()
const noexcept
244 return _has_invalidated_loggers.load(std::memory_order_acquire);
247 QUILL_ATTRIBUTE_COLD
void parse_log_level_from_env()
249 constexpr
char const* field =
"QUILL_LOG_LEVEL";
251 std::string log_level;
253 #if defined(_MSC_VER) 256 bool const ok = ::getenv_s(&len, buf,
sizeof(buf), field) == 0;
261 #else // revert to getenv 262 char* buf = ::getenv(field);
269 if (!log_level.empty())
271 _env_log_level = std::make_unique<LogLevel>(loglevel_from_string(log_level));
281 void _insert_logger(std::unique_ptr<LoggerBase> logger)
283 auto search_it = std::lower_bound(_loggers.begin(), _loggers.end(), logger->get_logger_name(),
284 [](std::unique_ptr<LoggerBase>
const& a, std::string
const& b)
285 {
return a->get_logger_name() < b; });
287 _loggers.insert(search_it,
static_cast<std::unique_ptr<LoggerBase>&&
>(logger));
291 QUILL_NODISCARD
LoggerBase* _find_logger(std::string
const& target)
const noexcept
293 auto search_it = std::lower_bound(_loggers.begin(), _loggers.end(), target,
294 [](std::unique_ptr<LoggerBase>
const& a, std::string
const& b)
295 {
return a->get_logger_name() < b; });
297 return (search_it != std::end(_loggers) && search_it->get()->get_logger_name() == target)
303 std::vector<std::unique_ptr<LoggerBase>> _loggers;
304 std::unique_ptr<LogLevel> _env_log_level;
306 std::atomic<bool> _has_invalidated_loggers{
false};
Base class for sinks.
Definition: Sink.h:40
QUILL_NODISCARD bool is_valid_logger() const noexcept
Checks if the logger is valid.
Definition: LoggerBase.h:110
void for_each_logger(TCallback cb) const
For backend use only.
Definition: LoggerManager.h:135
Setups a signal handler to handle fatal signals.
Definition: BackendManager.h:24
Definition: Spinlock.h:18
Definition: LoggerBase.h:35
void set_log_level(LogLevel new_log_level)
Set the log level of the logger.
Definition: LoggerBase.h:135
Definition: Spinlock.h:58
Base class that provides a timestamp for log statements based on a user-provided clock source...
Definition: UserClockSource.h:25
Definition: LoggerManager.h:33
void mark_invalid()
This function sets the logger's validity flag to false, indicating that the logger is no longer valid...
Definition: LoggerBase.h:104