eDSP  0.0.1
A cross-platform DSP library written in C++.
logger.hpp
Go to the documentation of this file.
1 /*
2 * eDSP, A cross-platform Digital Signal Processing library written in modern C++.
3 * Copyright (C) 2018 Mohammed Boujemaoui Boulaghmoudi, All rights reserved.
4 *
5 * This program is free software: you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License as published by the Free
7 * Software Foundation, either version 3 of the License, or (at your option)
8 * any later version.
9 *
10 * This program is distributed in the hope that it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 *
15 * You should have received a copy of the GNU General Public License along width
16 * this program. If not, see <http://www.gnu.org/licenses/>
17 *
18 * Filename: logger.hpp
19 * Author: Mohammed Boujemaoui
20 * Date: 07/10/18
21 */
22 
23 #ifndef EDSP_LOGGER_HPP
24 #define EDSP_LOGGER_HPP
25 
26 #include <edsp/thirdparty/spdlog/spdlog.h>
27 #include <edsp/thirdparty/spdlog/sinks/stdout_color_sinks.h>
28 #include <edsp/thirdparty/spdlog/sinks/basic_file_sink.h>
29 #include <edsp/thirdparty/termcolor/termcolor.hpp>
31 #include <type_traits>
32 #include <sstream>
33 
34 namespace edsp { inline namespace core {
35 
36  inline namespace internal {
37  struct logger_impl;
38  }
39 
40  class logger {
41  public:
46  enum levels {
47  trace = 0,
49  info,
53  off
54  };
55 
60  inline static void set_default_level(levels type);
61 
66  inline static levels default_level();
67 
72  inline static void set_default_path(const std::string& path);
73 
80  inline static const std::string& default_path();
81 
86  inline static void set_default_name(const std::string& name);
87 
92  inline static const std::string& default_name();
93 
98  inline static void set_pattern(const std::string& pattern);
99 
108  inline logger(const edsp::string_view& name, const edsp::string_view& file,
109  levels message_type = levels::trace);
110 
117  inline explicit logger(const edsp::string_view& name, levels message_type = levels::trace);
118 
124  inline explicit logger(levels message_type = levels::trace);
125 
129  inline ~logger();
130 
135  inline void set_level(levels type);
136 
141  inline levels level();
142 
147  inline logger& space();
148 
153  inline const std::string& name() const;
154 
159  inline std::string str() const;
160 
161  // clang-format off
162  using logger_manipulator = std::function<edsp::core::logger&(edsp::core::logger&)>;
163  inline logger& operator<<(logger_manipulator manipulator);
164  inline logger& operator<<(std::uint8_t);
165  inline logger& operator<<(std::uint16_t);
166  inline logger& operator<<(std::uint32_t);
167  inline logger& operator<<(std::uint64_t);
168  inline logger& operator<<(std::int8_t);
169  inline logger& operator<<(std::int16_t);
170  inline logger& operator<<(std::int32_t);
171  inline logger& operator<<(std::int64_t);
172  inline logger& operator<<(float);
173  inline logger& operator<<(double);
174  inline logger& operator<<(const char*);
175 
176  template <typename Char>
177  inline logger& operator<<(const std::basic_string<Char>& str);
178 
179  template <typename Char>
180  inline logger& operator<<(const edsp::basic_string_view<Char>& str);
181  // clang-format on
182 
183  private:
190  static spdlog::level::level_enum& global_level() {
191  static spdlog::level::level_enum LEVEL = spdlog::level::trace;
192  return LEVEL;
193  }
194 
201  static std::string& global_path() {
202  static std::string FILE{};
203  return FILE;
204  }
205 
212  static std::string& global_name() {
213  static std::string NAME = "console";
214  return NAME;
215  }
216 
217  private:
218  friend struct internal::logger_impl;
219  std::shared_ptr<spdlog::logger> logger_{nullptr};
220  logger::levels type_{levels::info};
221  std::stringstream msg_;
222  };
223 
224  inline namespace internal {
225  struct logger_impl {
226  inline static logger& tab(logger& stream) {
227  return stream << '\t';
228  }
229 
230  inline static logger& endl(logger& stream) {
231  return stream << '\n';
232  }
233 
234  inline static logger& red(logger& stream) {
235  stream.msg_ << termcolor::colorize;
236  stream.msg_ << termcolor::red;
237  return stream;
238  }
239 
240  inline static logger& yellow(logger& stream) {
241  stream.msg_ << termcolor::colorize;
242  stream.msg_ << termcolor::yellow;
243  return stream;
244  }
245 
246  inline static logger& blue(logger& stream) {
247  stream.msg_ << termcolor::colorize;
248  stream.msg_ << termcolor::blue;
249  return stream;
250  }
251 
252  inline static logger& cyan(logger& stream) {
253  stream.msg_ << termcolor::colorize;
254  stream.msg_ << termcolor::cyan;
255  return stream;
256  }
257 
258  inline static logger& white(logger& stream) {
259  stream.msg_ << termcolor::colorize;
260  stream.msg_ << termcolor::white;
261  return stream;
262  }
263 
264  inline static logger& magenta(logger& stream) {
265  stream.msg_ << termcolor::colorize;
266  stream.msg_ << termcolor::magenta;
267  return stream;
268  }
269 
270  inline static logger& green(logger& stream) {
271  stream.msg_ << termcolor::colorize;
272  stream.msg_ << termcolor::green;
273  return stream;
274  }
275 
276  inline static logger& grey(logger& stream) {
277  stream.msg_ << termcolor::colorize;
278  stream.msg_ << termcolor::grey;
279  return stream;
280  }
281 
282  inline static logger& bold(logger& stream) {
283  stream.msg_ << termcolor::colorize;
284  stream.msg_ << termcolor::bold;
285  return stream;
286  }
287 
288  inline static logger& endc(logger& stream) {
289  stream.msg_ << termcolor::nocolorize;
290  stream.msg_ << termcolor::reset;
291  return stream;
292  }
293 
294  inline static logger& reset(logger& stream) {
295  stream.msg_ << termcolor::reset;
296  return stream;
297  }
298  };
299  } // namespace internal
300 
306  inline logger& tab(logger& stream) {
307  return logger_impl::tab(stream);
308  }
309 
316  inline logger& endl(logger& stream) {
317  return logger_impl::endl(stream);
318  }
319 
325  inline logger& red(logger& stream) {
326  return logger_impl::red(stream);
327  }
328 
334  inline logger& yellow(logger& stream) {
335  return logger_impl::yellow(stream);
336  }
337 
343  inline logger& blue(logger& stream) {
344  return logger_impl::blue(stream);
345  }
346 
347 
353  inline logger& cyan(logger& stream) {
354  return logger_impl::cyan(stream);
355  }
356 
362  inline logger& white(logger& stream) {
363  return logger_impl::white(stream);
364  }
365 
371  inline logger& magenta(logger& stream) {
372  return logger_impl::magenta(stream);
373  }
374 
380  inline logger& green(logger& stream) {
381  return logger_impl::green(stream);
382  }
383 
389  inline logger& grey(logger& stream) {
390  return logger_impl::grey(stream);
391  }
392 
398  inline logger& bold(logger& stream) {
399  return logger_impl::bold(stream);
400  }
401 
407  inline logger& endc(logger& stream) {
408  return logger_impl::endc(stream);
409  }
410 
416  inline logger& reset(logger& stream) {
417  return logger_impl::reset(stream);
418  }
419 
420  logger::logger(const edsp::string_view& name, const edsp::string_view& file, logger::levels message_type) :
421  type_(message_type),
422  msg_() {
423  logger_ = spdlog::get(name.data());
424  if (!logger_) {
425  logger_ = spdlog::basic_logger_mt(name.data(), file.data());
426  }
427  }
428 
429  logger::logger(const edsp::string_view& name, logger::levels message_type) : type_(message_type), msg_() {
430  logger_ = spdlog::get(name.data());
431  if (!logger_) {
432  logger_ = spdlog::stdout_color_mt(name.data());
433  }
434  }
435 
436  logger::logger(logger::levels message_type) : type_(message_type), msg_() {
437  const auto& name = global_name();
438  logger_ = spdlog::get(name);
439  if (!logger_) {
440  const auto& path = global_path();
441  if (path.empty()) {
442  logger_ = spdlog::stdout_color_mt(name);
443  } else {
444  logger_ = spdlog::basic_logger_mt(name, path);
445  }
446  }
448  }
449 
451  edsp::endc(*this);
452  switch (type_) {
453  case levels::trace:
454  logger_->trace(msg_.str());
455  break;
456  case levels::debug:
457  logger_->debug(msg_.str());
458  break;
459  case levels::info:
460  logger_->info(msg_.str());
461  break;
462  case levels::warning:
463  logger_->warn(msg_.str());
464  break;
465  case levels::critical:
466  logger_->critical(msg_.str());
467  break;
468  case levels::error:
469  logger_->error(msg_.str());
470  break;
471  default:
472  break;
473  }
474  }
475 
477  msg_ << ' ';
478  return *this;
479  }
480 
482  switch (global_level()) {
483  case spdlog::level::trace:
484  return levels::trace;
485  case spdlog::level::debug:
486  return levels::debug;
487  case spdlog::level::info:
488  return levels::info;
489  case spdlog::level::warn:
490  return levels::warning;
491  case spdlog::level::critical:
492  return levels::critical;
493  case spdlog::level::err:
494  return levels::error;
495  default:
496  return levels::off;
497  }
498  }
499 
501  auto& LEVEL = global_level();
502  switch (type) {
503  case levels::trace:
504  LEVEL = spdlog::level::trace;
505  break;
506  case levels::debug:
507  LEVEL = spdlog::level::debug;
508  break;
509  case levels::info:
510  LEVEL = spdlog::level::info;
511  break;
512  case levels::warning:
513  LEVEL = spdlog::level::warn;
514  break;
515  case levels::critical:
516  LEVEL = spdlog::level::critical;
517  break;
518  case levels::error:
519  LEVEL = spdlog::level::err;
520  break;
521  default:
522  LEVEL = spdlog::level::off;
523  break;
524  }
525  }
526 
528  switch (type) {
529  case levels::trace:
530  logger_->set_level(spdlog::level::trace);
531  break;
532  case levels::debug:
533  logger_->set_level(spdlog::level::debug);
534  break;
535  case levels::info:
536  logger_->set_level(spdlog::level::info);
537  break;
538  case levels::warning:
539  logger_->set_level(spdlog::level::warn);
540  break;
541  case levels::critical:
542  logger_->set_level(spdlog::level::critical);
543  break;
544  case levels::error:
545  logger_->set_level(spdlog::level::err);
546  break;
547  default:
548  logger_->set_level(spdlog::level::off);
549  break;
550  }
551  }
552 
554  switch (logger_->level()) {
555  case spdlog::level::trace:
556  return levels::trace;
557  case spdlog::level::debug:
558  return levels::debug;
559  case spdlog::level::info:
560  return levels::info;
561  case spdlog::level::warn:
562  return levels::warning;
563  case spdlog::level::critical:
564  return levels::critical;
565  case spdlog::level::err:
566  return levels::error;
567  default:
568  return levels::off;
569  }
570  }
571 
572  const std::string& logger::name() const {
573  return logger_->name();
574  }
575 
576  void logger::set_default_path(const std::string& path) {
577  global_path() = path;
578  }
579 
580  const std::string& logger::default_path() {
581  return global_path();
582  }
583 
584  const std::string& logger::default_name() {
585  return global_name();
586  }
587 
588  void logger::set_default_name(const std::string& name) {
589  global_name() = name;
590  }
591 
593  return manipulator(*this);
594  }
595 
596  std::string logger::str() const {
597  return msg_.str();
598  }
599 
600  template <typename Char>
601  logger& logger::operator<<(const std::basic_string<Char>& str) {
602  msg_ << str.data();
603  return space();
604  }
605 
606  template <typename Char>
607  logger& logger::operator<<(const edsp::basic_string_view<Char>& str) {
608  msg_ << str.data();
609  return space();
610  }
611 
612  logger& logger::operator<<(std::uint8_t value) {
613  msg_ << value;
614  return space();
615  }
616 
617  logger& logger::operator<<(std::uint16_t value) {
618  msg_ << value;
619  return space();
620  }
621 
622  logger& logger::operator<<(std::uint32_t value) {
623  msg_ << value;
624  return space();
625  }
626 
627  logger& logger::operator<<(std::uint64_t value) {
628  msg_ << value;
629  return space();
630  }
631 
632  logger& logger::operator<<(std::int8_t value) {
633  msg_ << value;
634  return space();
635  }
636 
637  logger& logger::operator<<(std::int16_t value) {
638  msg_ << value;
639  return space();
640  }
641 
642  logger& logger::operator<<(std::int32_t value) {
643  msg_ << value;
644  return space();
645  }
646 
647  logger& logger::operator<<(std::int64_t value) {
648  msg_ << value;
649  return space();
650  }
651 
652  logger& logger::operator<<(float value) {
653  msg_ << value;
654  return space();
655  }
656 
657  logger& logger::operator<<(double value) {
658  msg_ << value;
659  return space();
660  }
661 
662  logger& logger::operator<<(const char* str) {
663  msg_ << str;
664  return space();
665  }
666 
667  void logger::set_pattern(const std::string& pattern) {
668  spdlog::set_pattern(pattern);
669  }
670 
671 }} // namespace edsp::core
672 
673 #define eTrace() edsp::logger(edsp::logger::levels::trace)
674 #define eInfo() edsp::logger(edsp::logger::levels::info)
675 #define eDebug() edsp::logger(edsp::logger::levels::debug)
676 #define eWarning() edsp::logger(edsp::logger::levels::warning)
677 #define eCritical() edsp::logger(edsp::logger::levels::critical)
678 #define eError() edsp::logger(edsp::logger::levels::error)
679 
680 #endif //EDSP_LOGGER_HPP
logger & green(logger &stream)
Updates the logger output color to green.
Definition: logger.hpp:380
std::function< edsp::core::logger &(edsp::core::logger &)> logger_manipulator
Definition: logger.hpp:162
Definition: logger.hpp:48
Definition: logger.hpp:51
std::string str() const
Returns the current string buffer.
Definition: logger.hpp:596
~logger()
Default destructor.
Definition: logger.hpp:450
static void set_pattern(const std::string &pattern)
Updates the pattern of the displayed messages.
Definition: logger.hpp:667
static const std::string & default_path()
Returns the current file path of the default logger.
Definition: logger.hpp:580
logger & yellow(logger &stream)
Updates the logger output color to yellow.
Definition: logger.hpp:334
static void set_default_level(levels type)
Updates the minimum level to be logged.
Definition: logger.hpp:500
logger & space()
Writes an space character to the stream and returns a reference to the stream.
Definition: logger.hpp:476
levels level()
Returns the default level.
Definition: logger.hpp:553
static const std::string & default_name()
Returns the name of the default logger.
Definition: logger.hpp:584
Definition: logger.hpp:49
logger & white(logger &stream)
Updates the logger output color to white.
Definition: logger.hpp:362
const std::string & name() const
Returns the name of the logger.
Definition: logger.hpp:572
logger(const edsp::string_view &name, const edsp::string_view &file, levels message_type=levels::trace)
Constructs a logger to record log messages of message_type for the file.
Definition: logger.hpp:420
static void set_default_name(const std::string &name)
Updates the name of the default logger.
Definition: logger.hpp:588
logger & blue(logger &stream)
Updates the logger output color to blue.
Definition: logger.hpp:343
logger & magenta(logger &stream)
Updates the logger output color to magenta.
Definition: logger.hpp:371
logger & red(logger &stream)
Updates the logger output color to red.
Definition: logger.hpp:325
logger & grey(logger &stream)
Updates the logger output color to grey.
Definition: logger.hpp:389
logger & endl(logger &stream)
Inserts the end line character (&#39; &#39;) to the current streaming.
Definition: logger.hpp:316
logger & bold(logger &stream)
Updates the logger output text style to bold style.
Definition: logger.hpp:398
logger & cyan(logger &stream)
Updates the logger output color to cyan.
Definition: logger.hpp:353
Definition: logger.hpp:40
logger & reset(logger &stream)
Resets the logger to default configuration.
Definition: logger.hpp:416
logger & operator<<(logger_manipulator manipulator)
Definition: logger.hpp:592
static levels default_level()
Returns the default level.
Definition: logger.hpp:481
Definition: logger.hpp:52
Definition: logger.hpp:50
levels
Definition: logger.hpp:46
static void set_default_path(const std::string &path)
Updates the default file path of the file holding the default logger.
Definition: logger.hpp:576
logger & tab(logger &stream)
Inserts the tabular character (&#39;&#39;) to the current streaming.
Definition: logger.hpp:306
logger & endc(logger &stream)
End of color, styled streaming.
Definition: logger.hpp:407
void set_level(levels type)
Updates the minimum level to be logged.
Definition: logger.hpp:527
Definition: amplifier.hpp:29
logger & operator<<(logger &stream, fft_lib lib)
Definition: library_info.hpp:38