logbacklog4jlog4j2 全是以同一个人为首的团伙搞出来的(日志专业户!),这几个各有所长,log4j性能相对最差,log4j2性能不错,但是目前跟mybatis有些犯冲(log4j2的当前版本,已经将AbstractLoggerWrapper更名成ExtendedLoggerWrapper,但是mybatis 2.3.7依赖的仍然是旧版本的log4j2,所以mybatis使用log4j2会报错),说到日志,还要注意另一外项目SLF4J( java的世界里,记日志的组件真是多!),SLF4J只一个接口标准,并不提供实现(就好象JSF/JPA 与 RichFaces/Hibernate的关系类似),而LogBack是SLF4J的一个实现,下面介绍logback的基本用法

一、基本用法

1.1 maven依赖项

         <!-- log -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency> <dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.1.2</version>
</dependency> <dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.1.2</version>
</dependency>

1.2 配置文件logback.xml

 <?xml version="1.0" encoding="UTF-8" ?>
<configuration scan="true" scanPeriod="1800 seconds"
debug="false"> <property name="USER_HOME" value="logs" />
<property scope="context" name="FILE_NAME" value="mylog-logback" /> <timestamp key="byDay" datePattern="yyyy-MM-dd" /> <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender> <appender name="file"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${USER_HOME}/${FILE_NAME}.log</file> <rollingPolicy class="ch.qos.logback.core.rolling.FixedWindowRollingPolicy">
<fileNamePattern>${USER_HOME}/${byDay}/${FILE_NAME}-${byDay}-%i.log.zip
</fileNamePattern>
<minIndex>1</minIndex>
<maxIndex>10</maxIndex>
</rollingPolicy> <triggeringPolicy
class="ch.qos.logback.core.rolling.SizeBasedTriggeringPolicy">
<maxFileSize>5MB</maxFileSize>
</triggeringPolicy>
<encoder>
<pattern>%-4relative [%thread] %-5level %logger{35} - %msg%n
</pattern>
</encoder> </appender> <logger name="com.cnblogs.yjmyzz.App2" level="debug" additivity="true">
<appender-ref ref="file" />
<!-- <appender-ref ref="STDOUT" /> -->
</logger> <root level="info">
<appender-ref ref="STDOUT" />
</root>
</configuration>

1.3 示例程序
跟前面log4j2的示例程序几乎完全一样:

 package com.cnblogs.yjmyzz;

 import org.slf4j.*;

 public class App2 {

     static Logger logger = LoggerFactory.getLogger(App2.class);

     public static void main(String[] args) {
for (int i = 0; i < 100000; i++) {
logger.trace("trace message " + i);
logger.debug("debug message " + i);
logger.info("info message " + i);
logger.warn("warn message " + i);
logger.error("error message " + i);
}
System.out.println("Hello World! 2");
}
}

运行后,会在当前目录下创建logs目录,生成名为mylog-logback.log的日志文件,该文件体积>5M后,会自动创建 yyyy-mm-dd的目录,将历史日志打包生成类似:mylog-logback-2014-09-24-1.log.zip 的压缩包,每天最多保留10个

二、与spring -mvc的集成 

2.1 maven依赖项

注:${springframework.version},我用的是3.2.8.RELEASE 版本

 <!-- Spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${springframework.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-expression</artifactId>
<version>${springframework.version}</version>
</dependency> <!-- logback -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency> <dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.1.2</version>
</dependency> <dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.1.2</version>
</dependency> <!-- Servlet -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
<scope>provided</scope>
</dependency>

2.2 web.xml里增加下面的内容

 <!-- logback-begin -->
<context-param>
<param-name>logbackConfigLocation</param-name>
<param-value>classpath:logback.xml</param-value>
</context-param>
<listener>
<listener-class>com.cnblogs.yjmyzz.util.LogbackConfigListener</listener-class>
</listener>
<!-- logback-end -->

其中com.cnblogs.yjmyzz.util.LogbackConfigListener 是自己开发的类,代码如下:(从网上掏来的)

注:该处理方式同样适用于struts 2.x

 package com.cnblogs.yjmyzz.util;

 import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener; public class LogbackConfigListener implements ServletContextListener { public void contextInitialized(ServletContextEvent event) {
LogbackWebConfigurer.initLogging(event.getServletContext());
} public void contextDestroyed(ServletContextEvent event) {
LogbackWebConfigurer.shutdownLogging(event.getServletContext());
}
}

LogbackConfigListener

 package com.cnblogs.yjmyzz.util;

 import java.io.FileNotFoundException;

 import javax.servlet.ServletContext;

 import org.springframework.util.ResourceUtils;
import org.springframework.util.SystemPropertyUtils;
import org.springframework.web.util.WebUtils; public abstract class LogbackWebConfigurer { /** Parameter specifying the location of the logback config file */
public static final String CONFIG_LOCATION_PARAM = "logbackConfigLocation"; /**
* Parameter specifying the refresh interval for checking the logback config
* file
*/
public static final String REFRESH_INTERVAL_PARAM = "logbackRefreshInterval"; /** Parameter specifying whether to expose the web app root system property */
public static final String EXPOSE_WEB_APP_ROOT_PARAM = "logbackExposeWebAppRoot"; /**
* Initialize logback, including setting the web app root system property.
*
* @param servletContext
* the current ServletContext
* @see WebUtils#setWebAppRootSystemProperty
*/
public static void initLogging(ServletContext servletContext) {
// Expose the web app root system property.
if (exposeWebAppRoot(servletContext)) {
WebUtils.setWebAppRootSystemProperty(servletContext);
} // Only perform custom logback initialization in case of a config file.
String location = servletContext
.getInitParameter(CONFIG_LOCATION_PARAM);
if (location != null) {
// Perform actual logback initialization; else rely on logback's
// default initialization.
try {
// Return a URL (e.g. "classpath:" or "file:") as-is;
// consider a plain file path as relative to the web application
// root directory.
if (!ResourceUtils.isUrl(location)) {
// Resolve system property placeholders before resolving
// real path.
location = SystemPropertyUtils
.resolvePlaceholders(location);
location = WebUtils.getRealPath(servletContext, location);
} // Write log message to server log.
servletContext.log("Initializing logback from [" + location
+ "]"); // Initialize without refresh check, i.e. without logback's
// watchdog thread.
LogbackConfigurer.initLogging(location); } catch (FileNotFoundException ex) {
throw new IllegalArgumentException(
"Invalid 'logbackConfigLocation' parameter: "
+ ex.getMessage());
}
}
} /**
* Shut down logback, properly releasing all file locks and resetting the
* web app root system property.
*
* @param servletContext
* the current ServletContext
* @see WebUtils#removeWebAppRootSystemProperty
*/
public static void shutdownLogging(ServletContext servletContext) {
servletContext.log("Shutting down logback");
try {
LogbackConfigurer.shutdownLogging();
} finally {
// Remove the web app root system property.
if (exposeWebAppRoot(servletContext)) {
WebUtils.removeWebAppRootSystemProperty(servletContext);
}
}
} /**
* Return whether to expose the web app root system property, checking the
* corresponding ServletContext init parameter.
*
* @see #EXPOSE_WEB_APP_ROOT_PARAM
*/
private static boolean exposeWebAppRoot(ServletContext servletContext) {
String exposeWebAppRootParam = servletContext
.getInitParameter(EXPOSE_WEB_APP_ROOT_PARAM);
return (exposeWebAppRootParam == null || Boolean
.valueOf(exposeWebAppRootParam));
} }

LogbackWebConfigurer

 package com.cnblogs.yjmyzz.util;

 import java.io.File;
import java.io.FileNotFoundException;
import java.net.URL; import org.slf4j.LoggerFactory;
import org.springframework.util.ResourceUtils;
import org.springframework.util.SystemPropertyUtils; import ch.qos.logback.classic.LoggerContext;
import ch.qos.logback.classic.joran.JoranConfigurator;
import ch.qos.logback.core.joran.spi.JoranException; public abstract class LogbackConfigurer { /** Pseudo URL prefix for loading from the class path: "classpath:" */
public static final String CLASSPATH_URL_PREFIX = "classpath:"; /** Extension that indicates a logback XML config file: ".xml" */
public static final String XML_FILE_EXTENSION = ".xml"; private static LoggerContext lc = (LoggerContext) LoggerFactory
.getILoggerFactory();
private static JoranConfigurator configurator = new JoranConfigurator(); /**
* Initialize logback from the given file location, with no config file
* refreshing. Assumes an XML file in case of a ".xml" file extension, and a
* properties file otherwise.
*
* @param location
* the location of the config file: either a "classpath:"
* location (e.g. "classpath:mylogback.properties"), an absolute
* file URL (e.g.
* "file:C:/logback.properties), or a plain absolute path in the file system (e.g. "
* C:/logback.properties")
* @throws FileNotFoundException
* if the location specifies an invalid file path
*/
public static void initLogging(String location)
throws FileNotFoundException {
String resolvedLocation = SystemPropertyUtils
.resolvePlaceholders(location);
URL url = ResourceUtils.getURL(resolvedLocation);
if (resolvedLocation.toLowerCase().endsWith(XML_FILE_EXTENSION)) {
// DOMConfigurator.configure(url);
configurator.setContext(lc);
lc.reset();
try {
configurator.doConfigure(url);
} catch (JoranException ex) {
throw new FileNotFoundException(url.getPath());
}
lc.start();
}
// else {
// PropertyConfigurator.configure(url);
// }
} /**
* Shut down logback, properly releasing all file locks.
* <p>
* This isn't strictly necessary, but recommended for shutting down logback
* in a scenario where the host VM stays alive (for example, when shutting
* down an application in a J2EE environment).
*/
public static void shutdownLogging() {
lc.stop();
} /**
* Set the specified system property to the current working directory.
* <p>
* This can be used e.g. for test environments, for applications that
* leverage logbackWebConfigurer's "webAppRootKey" support in a web
* environment.
*
* @param key
* system property key to use, as expected in logback
* configuration (for example: "demo.root", used as
* "${demo.root}/WEB-INF/demo.log")
* @see org.springframework.web.util.logbackWebConfigurer
*/
public static void setWorkingDirSystemProperty(String key) {
System.setProperty(key, new File("").getAbsolutePath());
} }

LogbackConfigurer

2.3 JBOSS EAP 6+ 的特殊处理

jboss 默认已经集成了sf4j模块,会与上面新加的3个类有冲突,app启动时会报错:

java.lang.ClassCastException: org.slf4j.impl.Slf4jLoggerFactory cannot be cast to ch.qos.logback.classic.LoggerContext

所以,需要手动排除掉jboss默认的slf4j模块,在web-inf下创建名为jboss-deployment-structure.xml的文件,内容如下:

 <?xml version="1.0" encoding="UTF-8"?>
<jboss-deployment-structure>
<deployment>
<exclusions>
<module name="org.slf4j" />
<module name="org.slf4j.impl" />
<module name="org.slf4j.jcl-over-slf4j" />
<module name="org.slf4j.ext" />
</exclusions>
</deployment>
</jboss-deployment-structure>

2.4 最后将logback.xml放到resouces目录下即可(打包后,会自动复制到classpath目录下)

logback + slf4j + jboss + spring mvc的更多相关文章

  1. Spring MVC集成slf4j-logback

    转自: Spring MVC集成slf4j-logback 1.  Spring MVC集成slf4j-log4j 关于slf4j和log4j的相关介绍和用法,网上有很多文章可供参考,但是关于logb ...

  2. mybatis 3.2.7 与 spring mvc 3.x、logback整合

    github上有一个Mybatis-Spring的项目,专门用于辅助完成mybatis与spring的整合,大大简化了整合难度,使用步骤: 准备工作: maven依赖项: <properties ...

  3. Java日志框架-Spring中使用Logback(Spring/Spring MVC)

    继上一篇文章http://www.cnblogs.com/EasonJim/p/7800880.html中所集成的是基于Java的普通项目,如果要在Spring和Spring MVC上集成,需要做如下 ...

  4. jboss developers studio 快速创建 spring mvc 项目

    1. 2. 部署运行 还有一个 rest very good !! ps:其实就是 一个 jboss 的 spring mvc maven 原型

  5. IntelliJ IDEA 13.x 下使用Hibernate + Spring MVC + JBoss 7.1.1

    从2004年开始做.NET到现在.直到最近要做一些JAVA的项目,如果说100个人写一篇关于.NET的文章,估计这10个人写的内容都是一样.但是如果说10个人写Java的文章,那真的是10个人10种写 ...

  6. spring boot 1.x完整学习指南(含各种常见问题servlet、web.xml、maven打包,spring mvc差别及解决方法)

    spring boot 入门 关于版本的选择,spring boot 2.0开始依赖于 Spring Framework 5.1.0,而spring 5.x和之前的版本差距比较大,而且应该来说还没有广 ...

  7. Spring MVC教程——检视阅读

    Spring MVC教程--检视阅读 参考 Spring MVC教程--一点--蓝本 Spring MVC教程--c语言中午网--3.0版本太老了 Spring MVC教程--易百--4.0版本不是通 ...

  8. spring mvc+ELK从头开始搭建日志平台

    最近由于之前协助前公司做了点力所能及的事情,居然收到了一份贵重的端午礼物,是给我女儿的一个乐高积木,整个有7大包物件,我花了接近一天的时间一砖一瓦的组织起来,虽然很辛苦但是能够从过程中体验到乐趣.这次 ...

  9. 使用Maven创建一个Spring MVC Web 项目

    使用Maven创建java web 项目(Spring MVC)用到如下工具: 1.Maven 3.2 2.IntelliJ IDEA 13 3.JDK 1.7 4.Spring 4.1.1 rele ...

随机推荐

  1. Helpful Tool

    Remote Connectivity Analyzer(Online) https://testconnectivity.microsoft.com/ https://technet.microso ...

  2. #研发解决方案介绍#Recsys-Evaluate(推荐评测)

    郑昀 基于刘金鑫文档 最后更新于2014/12/1 关键词:recsys.推荐评测.Evaluation of Recommender System.piwik.flume.kafka.storm.r ...

  3. 【JSP】JSP基础学习记录(四)—— Servlet

    序: 众所周知JSP的基础也就是Servlet,如果单纯用Servlet类来响应用户的HTTP请求可以吗?答案是肯定的.JSP中的9个内置对象只是自动帮我们初始化的,没有他们一样可以实现web.只是工 ...

  4. 表单和iframe的使用

    图片热点: 规划出图片上的一个区域,可以做出超链接,直接点击图片区域就可以完成跳转的效果.示例: 网页划区: 在一个网页里,规划出一个区域用来展示另一个网页的内容.示例: 网页的拼接: 在一个网络页面 ...

  5. C#读取XML文件

    --硬盘Xml文件存储路径:d:\xmlFile\Testxml.xml xml文件内容: <Root> <Tab> <ID>245575913</ID> ...

  6. Java设计模式 - 适配器模式

    概念: 将一个类的接口,转换成客户期望的另一个接口.适配器模式让原来接口不兼容的类可以在一起工作. 解决的问题: 提供类似于中间人的作用:把原本不兼容.不能一起工作的接口组合在一起,使得它们能够在一起 ...

  7. 烂泥:【解决】VMware Workstation中安装ESXI5.0双网卡问题

    本文由秀依林枫提供友情赞助,首发于烂泥行天下. 由于需要做ESXI相关的实验,所以就在自己的机器上利用VM虚拟ESXI进行实验.因为此次实验是需要两块网卡的,所以就在创建ESXI虚拟机时添加了两块网卡 ...

  8. file

    用来测试文件类型 $file [] filename -b列出辨识结果时,但不显示文件名称 -L如果文件是符号链接,那么直接解读其指向的文件 -z:如果文件是压缩文件,尝试去解读压缩文件的内容 $fi ...

  9. Linux磁盘管理之设备文件详解04

    Linux一切接文件,除了普通文件和目录文件,还包括一些其它的特殊文件:块设备文件.字符设备文件.套接字文件.链接文件等.今天这里主要说一下常见的块设备文件和字符设备文件,这2类是最常见的设备文件类. ...

  10. js 读取 cookie

    (新摘未验证)// 将document.cookie的值以名/值对组成的一个对象返回 // 假设储存cookie的值的时候是采用encodeURIComponent()函数编码的 function g ...