1.问题
java中,log4j库非常好用,支持性也非常广泛。c++中,是否也有类似的库?最好能够夸语言互通。
2.方案
一般优秀的库,其他语言应该都会借鉴,实现不同语言版本。通过搜索,c++的log有好几个版本,比如log4cpp,log4cxx,log4cplus等。本文采用log4cxx库,因为它是log4j同源的。
2.1.环境准备
- ubuntu 20.0.4
- gcc gcc 10.2.0(可以用自带的gcc版本)
- 下载log4cxx:http://logging.apache.org/log4cxx/download.html
- 下载apr和apr-util:http://apr.apache.org/download.cgi
- 下载expat:https://github.com/libexpat/libexpat/releases
2.2编译
2.2.1.编译apr
tar xvf apr-1.7.0.tar.gz
cd arp-1.7.0
./configure--prefix=/usr/local
make
make install
2.2.2. 编译apr-util
tar apr-util-1.6.1.tar.gz
cd apr-util-1.6.1
./configure--prefix=/usr/local
make
make install
2.2.3.编译expat
由于log4cxx支持xml格式输出,使用到了expat库。因此还需要编译expat。
tar expat-2.2.10.tar.gz
cd expat-2.2.10
./configure--prefix=/usr/local
make
make install
2.2.4.编译log4cxx
log4cxx不容易编译,不通的版本可能遇到的问题比较多,没有configure文件可以用,还是通过官网的帮助查到,需要先执行./autogen.sh
生成configure文件。可以参见:https://logging.apache.org/log4cxx/latest_stable/building/autotools.html
tar xvf apache-log4cxx-0.11.0.tar.gz
cd apache-log4cxx-0.11.0
./autogen.sh
./configure --prefix=/usr/local --with-apr=/usr/local --with-apr-util=/usr/local
make
make install
2.3.测试
设置环境信息,~/.bashrc
文件末尾增加以下一行内容:
LD_LIBRARY_PATH=/usr/local/lib
export LD_LIBRARY_PATH
写一个简单的程序测试下。代码如下:
#include <log4cxx/logger.h>
#include <log4cxx/logstring.h>
#include <log4cxx/xml/domconfigurator.h>
#include <log4cxx/mdc.h>
#include <log4cxx/ndc.h>
int main(int argc, char *argv[])
{
using namespace log4cxx;
// 读取配置文件
xml::DOMConfigurator::configure("log4cxx.xml");
// 建立两个logger
LoggerPtr logger = Logger::getLogger("root");
MDC::put("key", "value");
MDC::put("key2", "value2");
NDC::push("context 1");
NDC::push("context 2");
LOG4CXX_DEBUG(logger, "this is debug log");
logger->debug("this is an other log");
NDC::clear();
MDC::clear();
return 0;
}
编译指令:
g++ -o testlog4cxx testlog4cxx.cpp -L/usr/local/log4cxx/lib -llog4cxx -lexpat -I/usr/local/log4cxx/include
配置文件log4cxx.xml:
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
<log4j:configuration debug="false" xmlns:log4j='http://jakarta.apache.org/log4j/'>
<appender name="FILE" class="org.apache.log4j.RollingFileAppender">
<param name="threshold" value="debug" />
<param name="file" value="output.xml" />
<param name="maxBackupIndex" value="5" />
<param name="append" value="true" />
<layout class="org.apache.log4j.xml.XMLLayout">
<param name="LocationInfo" value="true" />
<param name="Properties" value="true" />
</layout>
</appender>
<root>
<level value="DEBUG" />
<appender-ref ref="FILE" />
</root>
</log4j:configuration>
output.xml文件输出为:
<log4j:event logger="root" timestamp="1610720619219" level="DEBUG" thread="0x7f42a1460b80">
<log4j:message><![CDATA[this is trace log]]></log4j:message>
<log4j:NDC><![CDATA[context 1 context 2]]></log4j:NDC>
<log4j:locationInfo class="" method="main" file="/home/xxx/code/cpp/c++20/testlog4cxx.cpp" line="25"/>
<log4j:properties>
<log4j:data name="key" value="value"/>
<log4j:data name="key2" value="value2"/>
</log4j:properties>
</log4j:event>
<log4j:event logger="root" timestamp="1610720619220" level="DEBUG" thread="0x7f42a1460b80">
<log4j:message><![CDATA[Sample debug message]]></log4j:message>
<log4j:NDC><![CDATA[context 1 context 2]]></log4j:NDC>
<log4j:locationInfo class="?" method="?" file="?" line="-1"/>
<log4j:properties>
<log4j:data name="key" value="value"/>
<log4j:data name="key2" value="value2"/>
</log4j:properties>
</log4j:event>
3.讨论
log4cxx编译很容易遇到问题,上述的编译过程只是记录,由于当时没有几时记录,也许不能一次性通过。不过,遇到问题大家通过搜索也能解决。
如果你用的是Ubtunu系统,也可以直接使用apt-get进行安装,只是可能不是最新的版本。
sudo apt-get install liblog4cxx-dev
find /usr -name '*log4cxx*'
/usr/lib/x86_64-linux-gnu/liblog4cxx.so.10
/usr/lib/x86_64-linux-gnu/liblog4cxx.so.10.0.0
/usr/lib/x86_64-linux-gnu/liblog4cxx.a
/usr/lib/x86_64-linux-gnu/liblog4cxx.so
/usr/lib/x86_64-linux-gnu/pkgconfig/liblog4cxx.pc
/usr/share/lintian/overrides/liblog4cxx10v5
/usr/share/lintian/overrides/liblog4cxx-dev
/usr/share/doc/liblog4cxx10v5
/usr/share/doc/liblog4cxx-dev
/usr/include/log4cxx
/usr/include/log4cxx/log4cxx.h
/usr/include/log4cxx/private/log4cxx_private.h
log4cxx和log4j是同源的,也是apache的开源项目,相比java来说,c++版本使用起来可能比较复杂一些。之余java和c++版本的库能否互通,比如c++版本提供日志服务器,客户端可以是java的,也可以是c++的,还没有尝试,有时间测试验证下。
网友评论