c++boostboost-logboost-logging

Error compiling code for creating boost.log format


I am trying to compile following code with gcc 7.3.0 on Ubuntu 18.04 LTS with option -std=c++14:

auto createLogFormatter()
{
    boost::log::expressions::stream_type stream;
    stream  << boost::log::expressions::format_date_time<boost::posix_time::ptime>("TimeStamp", "%Y-%m-%d %H:%M:%S  ")
            << boost::log::expressions::attr<int>("Severity")
            << " " // ERROR HERE
            << boost::log::expressions::attr<boost::log::attributes::current_thread_id::value_type>("ThreadID")
            << " "
            << boost::log::expressions::smessage;
    return stream;
}

And getting strange error:

Log.cpp:51:13: error: no match for ‘operator<<’ (operand types are ‘boost::log::v2_mt_posix::expressions::aux::make_output_actor<boost::phoenix::actor<boost::log::v2_mt_posix::expressions::aux::attribute_output_terminal<boost::phoenix::actor<boost::proto::exprns_::basic_expr<boost::proto::tagns_::tag::terminal, boost::proto::argsns_::term<boost::phoenix::argument<2> >, 0> >, boost::posix_time::ptime, boost::log::v2_mt_posix::fallback_to_none, boost::log::v2_mt_posix::aux::light_function<void(boost::log::v2_mt_posix::basic_formatting_ostream<char>&, const boost::posix_time::ptime&)> > >, boost::log::v2_mt_posix::expressions::attribute_actor<int, boost::log::v2_mt_posix::fallback_to_none, void, boost::phoenix::actor>, int, false>::type {aka boost::phoenix::actor<boost::log::v2_mt_posix::expressions::aux::attribute_output_terminal<boost::phoenix::actor<boost::log::v2_mt_posix::expressions::aux::attribute_output_terminal<boost::phoenix::actor<boost::proto::exprns_::basic_expr<boost::proto::tagns_::tag::terminal, boost::proto::argsns_::term<boost::phoenix::argument<2> >, 0> >, boost::posix_time::ptime, boost::log::v2_mt_posix::fallback_to_none, boost::log::v2_mt_posix::aux::light_function<void(boost::log::v2_mt_posix::basic_formatting_ostream<char>&, const boost::posix_time::ptime&)> > >, int, boost::log::v2_mt_posix::fallback_to_none, boost::log::v2_mt_posix::to_log_fun<void> > >}’ and ‘const char [2]’)
     stream  << boost::log::expressions::format_date_time<boost::posix_time::ptime>("TimeStamp", "%Y-%m-%d %H:%M:%S  ")
     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
             << boost::log::expressions::attr<int>("Severity")
             ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
             << " "
             ^~~~~~

According to Boost examples here, such thing should work:

    expr::stream
        << expr::attr< unsigned int >("LineID")
        << ": <" << logging::trivial::severity
        << "> " << expr::smessage

But I am getting such error. What I am doing wrong?


Solution

  • The compiler error is likely caused by a missing include. Lambda expression operators are provided by Boost.Phoenix in boost/phoenix/operator.hpp. Or you can just include boost/log/expressions.hpp, which provides all Boost.Log expression nodes as well as operators.

    But besides that, your createLogFormatter function is incorrect as it discards the whole formatter expression. You should not be creating and returning a stream object, it is only a terminal that starts the formatter expression. You need to return the function object that is created as a result of the lambda expression.

    auto createLogFormatter()
    {
        auto fmt = stream  << boost::log::expressions::format_date_time<boost::posix_time::ptime>("TimeStamp", "%Y-%m-%d %H:%M:%S  ")
                << boost::log::expressions::attr<int>("Severity")
                << " " // ERROR HERE
                << boost::log::expressions::attr<boost::log::attributes::current_thread_id::value_type>("ThreadID")
                << " "
                << boost::log::expressions::smessage;
        return fmt;
    }
    

    If you want to have a stable return type, you can use boost::log::formatter to wrap the expression.