Program Listing for File Logging.hpp

Return to documentation for file (include/lvr2/util/Logging.hpp)

#ifndef LOGGING
#define LOGGING

#include <cstdint>
#include <sstream>
#include <iostream>
#include <memory>

/* Forward declaration for logging backend */
namespace spdlog
{
    struct logger;
}

namespace spdmon
{
    struct Progress;
}

namespace lvr2
{

enum class LogLevel: uint8_t {
    trace,
    debug,
    info,
    warning,
    error
};


class Logger
{
private:

    Logger();

public:

    static Logger& get()
    {
        static Logger inst;
        return inst;
    }

    Logger(Logger const&) = delete;

    void operator=(Logger const&) = delete;

    void print();

    void flush();

    template<typename T>
    void append(const T& token)
    {
        m_buffer << token;
    }

    void setLogLevel(const LogLevel& level)
    {
        m_level = level;
    }

private:
    std::shared_ptr<spdlog::logger> m_logger;

    LogLevel                        m_level;

    std::stringstream               m_buffer;
};

class Monitor
{
public:

    Monitor(const LogLevel& level, const std::string& text, const size_t& max, size_t width = 0);

    void operator++();

    ~Monitor()
    {
        this->terminate();
    }

    void terminate();

private:
    std::shared_ptr<spdmon::Progress> m_monitor;

    std::string m_prefixText;
};

// Marker structs for log levels
struct LoggerEndline{};
struct LoggerError{};
struct LoggerWarning{};
struct LoggerTrace{};
struct LoggerInfo{};
struct LoggerDebug{};

inline constexpr LoggerEndline endl;

inline constexpr LoggerError error;

inline constexpr LoggerWarning warning;

inline constexpr LoggerTrace trace;

inline constexpr LoggerInfo info;

inline constexpr LoggerDebug debug;

// Alias for logger singleton
using logout = Logger;

template<typename T>
inline Logger& operator<<(Logger& log, const T& s)
{
    log.append(s);
    return log;
}

template<>
inline Logger& operator<<(Logger& log, const LoggerEndline& /* endl */)
{
    log.print();
    return log;
}

inline Logger& operator<<(Logger& log, const LoggerError& /* err */)
{
    log.setLogLevel(LogLevel::error);
    return log;
}

inline Logger& operator<<(Logger& log, const LoggerWarning& /* warn */)
{
    log.setLogLevel(LogLevel::warning);
    return log;
}

inline Logger& operator<<(Logger& log, const LoggerTrace& /* trace */)
{
    log.setLogLevel(LogLevel::trace);
    return log;
}

inline Logger& operator<<(Logger& log, const LoggerDebug& /* trace */)
{
    log.setLogLevel(LogLevel::debug);
    return log;
}

inline Logger& operator<<(Logger& log, const LoggerInfo& /* info */)
{
    log.setLogLevel(LogLevel::info);
    return log;
}


} // namespace lvr2



#endif // LOGGING