`
长安春雪
  • 浏览: 22799 次
  • 性别: Icon_minigender_1
  • 来自: 西安
文章分类
社区版块
存档分类
最新评论

利用数据库对Log4j日志进行管理(可写入用户名)

阅读更多

LOG 4J 日志管理
            ——基于DBCP和Mysql















版本:V1.0

日期:2009-10-2

作者:孙欢欢(shh-cc@163.com)


目录
1.DBCP配置 2
1.1  准备 mysql 的 jdbc 驱动程序 2
1.2  安装 Tomcat 默认全部装在 D:\tomcat6.0 2
1.3  以 TOMCAT_HOME 代替个版本的安装目录 2
1.4  将 jdbc 驱动mysql-connector-java-5.0.8-bin.jar,和commons-dbcp.jar,commons-pool-1.4.jar放入 TOMCAT_HOME\ common\lib\ 下面 2
1.6  配置 tomcat 数据源时的各种参数的详细介绍 2
1.7  其他设置。 2
1.8 在server.xml<GlobalNamingResources> </GlobalNamingResources>之间添 2
1.9.在context.xml的 3
1.10 配置参数说明 3
2. Log4j 配置 8
2.1下载最新的Log4j.jar包,放到相关项目的Lib下,并添加进项目的Libraris. 8
2.2把log4j.properties文件放到项目的SRC根目录下 8
2.3 关于log4j.properties 8
2. 3. 1 log4j.rootLogger = [ level ] , appenderName, appenderName, … 8
2. 3. 2 日志输出方式appender(目的地) 8
2. 3. 3 日志信息的布局 10
2. 3. 4 日志格式控制 10
3 程序中使用 11
3.1  写一个获得数据库连接的工具类 11
3.2 继承JDBCAppender类 13
3.3 在程序中使用 test.jsp 15

1.DBCP配置
1.1  准备 mysql 的 jdbc 驱动程序
1.2  安装 Tomcat 默认全部装在 D:\tomcat6.0
1.3  以 TOMCAT_HOME 代替个版本的安装目录
1.4  将 jdbc 驱动mysql-connector-java-5.0.8-bin.jar,和commons-dbcp.jar,commons-pool-1.4.jar放入 TOMCAT_HOME\ common\lib\ 下面
1.5  如果是其他数据库的话,就是换一下 jdbc 驱动以及各种参数就可以了的
1.6  配置 tomcat 数据源时的各种参数的详细介绍
1.7  其他设置。
1.8 在server.xml<GlobalNamingResources> </GlobalNamingResources>之间添
<!--mysql DBCP-->
     <Resource
  name="jdbc/TestDB"
  auth="Container"
      type="javax.sql.DataSource"
  driverClassName="com.mysql.jdbc.Driver"
      url="jdbc:mysql://localhost:3306"
      maxActive="50"
  maxldle="10"
  maxWait="5000"
  username="root"
  password="000000" /> 
1.9.在context.xml的

<Context></Context>之间添加
     <ResourceLink
       global="jdbc/TestDB"
       name="jdbc/TestDB"
       type="javax.sql.DataSource"/>
1.10 配置参数说明
Username          JDBC驱动建立连接时所需的用户名。

Password           JDBC驱动建立连接时所需的用户密码。

url                 JDBC驱动建立连接时的连接地址。

driverClassName      使用的JDBC驱动完整JAVA类名。

connectionProperties    JDBC驱动建立连接时附带的连接属性
属性的格式必须为这样:[属性名=property;] *
注意:"user" 与 "password" 两个属性会被明确地传递,因此这里不需要包含他们。



defaultAutoCommit     true 指定由连接池所创建的连接的自动提交(auto-commit)状态。

defaultReadOnly        driver default指定由连接池所创建的连接的只读(read-only)状态。如果没有设置该值,则“setReadOnly”方法将不被调用。(某些驱动并不支持只读模式,如:Informix)

defaultTransactionIsolation
driver default
指定由连接池所创建的连接的事务级别(TransactionIsolation)。可用值为下列之一:(详情可见javadoc。)

NONE
READ_COMMITTED
READ_UNCOMMITTED
REPEATABLE_READ
SERIALIZABLE
defaultCatalog
指定由连接池所创建的连接的默认日志。



initialSize           0初始化连接池时创建的连接数。
此版后开始提供:1.2

maxActive          8连接池允许的最大并发连接数,值为非正数时表示不限制。

maxIdle             8连接池中的最大空闲连接数,超过此数值时多余的空闲连接将会被释放,值为负数时表示不限制。

minIdle             0连接池中的最小空闲连接数,低于此数值时将会创建所欠缺的连接,值为0时表示不创建。

maxWait             indefinitely以毫秒表示的当连接池中没有可用连接时等待可用连接返回的时间,超时则抛出异常,值为-1时无限期等待。

validationQuery         在连接返回给调用者前用于校验连接是否有效的SQL语句。如果指定了SQL语句,则必须为一个“SELECT”语句,且至少会返回一行结果。

testOnBorrow         true
指定连接被调用时是否经过校验。如果校验未通过,则该连接被连接池断掉,并由连接池尝试调用另一个连接。
注意:要想值为true时该设置生效,则validationQuery参数必须为一个非空字串。

testOnReturn           false
指定连接返回到池中时是否经过校验。
注意:要想值为true时该设置生效,则validationQuery参数必须为一个非空字串。

testWhileIdle            false
指定连接进入空闲状态时是否经过空闲对象驱逐进程的校验(如果存在空闲对象驱逐进程)。如果校验未通过,则该连接被连接池断掉。
注意:要想值为true时该设置生效,则validationQuery参数必须为一个非空字串。

timeBetweenEvictionRunsMillis    -1
以毫秒表示的空闲对象驱逐进程由运行状态进入休眠状态的数值。值为非正数时表示不运行任何空闲对象驱逐进程。

numTestsPerEvictionRun    3
连接池检查每个空闲对象驱逐进程的对象数量(如果存在空闲对象驱逐进程)。

minEvictableIdleTimeMillis    1000 * 60 * 30
以毫秒表示的连接被空闲对象驱逐进程驱逐前在池中保持空闲状态的最小时间(如果存在空闲对象驱逐进程)。
poolPreparedStatements      false
启用“PreparedStatements”缓存池。

maxOpenPreparedStatements   unlimited
由“PreparedStatements”缓存池中取得“PreparedStatements”的最大并发数值,值为0时表示不限制。此组件也有能力对“PreparedStatements”对象进行缓存。当启用了“PreparedStatements”缓存池时,每个连接通过下列方法建立的“PreparedStatements”对象都会被放入缓存池:

public PreparedStatement prepareStatement(String sql)
public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency)
注意:请保证你的连接有剩余的资源为给其他语句。
accessToUnderlyingConnectionAllowed   false
控制是否允许“PoolGuard”优先使用连接。启用此项后,你可以按照下列方法优先使用连接:

Connection conn = ds.getConnection();
    Connection dconn = ((DelegatingConnection) conn).getInnermostDelegate();
    ...
    conn.close()默认为“false”,这是一个具有潜在威胁的选项,不当的程序可能会做出可怕的事情来(在关闭优先连接或当被守护的连接已经关闭后继续使用优先连接的时候)。小心并且尽量只在当你需要直接驱动指定的扩展时使用。

注意:不要关闭优先连接,它只有一个。
removeAbandoned     false
是否清除已经超过“removeAbandonedTimout”设置的无效连接。
如果值为“true”则超过“removeAbandonedTimout”设置的无效连接将会被清除。设置此属性可以从那些没有合适关闭连接的程序中恢复数据库的连接。

removeAbandonedTimeout      300     以秒表示的清除无效连接的时限。

logAbandoned           false
当清除无效连接时是否在日志中记录清除信息的标志。
记录无效的语句和连接,并附加每个连接开启或新建一个语句的系统开销。

如果你启用了“removeAbandoned”,可能会导致被设为无效的连接被连接池回收。这个机制将会在满足下列两个条件时启动:(getNumIdle() < 2) 和 (getNumActive() > getMaxActive() - 3)

例如:假设maxActive=20,而当前已经拥有18个活动连接,1个空闲连接,“removeAbandoned”机制将会启动。 但是只有在活动连接没有使用的时长超过“removeAbandonedTimeout”(默认为300秒)的连接被清除。在遍历结果集时,所使用的连接不会被标为活动连接。
2. Log4j 配置
2.1下载最新的Log4j.jar包,放到相关项目的Lib下,并添加进项目的Libraris.
2.2把log4j.properties文件放到项目的SRC根目录下
2.3 关于log4j.properties
2. 3. 1 log4j.rootLogger = [ level ] , appenderName, appenderName, …
其中,level 是日志记录的优先级,分为OFF、FATAL、ERROR、WARN、INFO、DEBUG、ALL或者您定义的级别。Log4j建议只使用四个级别,优先级从高到低分别是ERROR、WARN、INFO、DEBUG。通过在这里定义的级别,您可以控制到应用程序中相应级别的日志信息的开关。比如在这里定义了INFO级别,则应用程序中所有DEBUG级别的日志信息将不被打印出来。
appenderName就是指定日志信息输出到哪个地方。您可以同时指定多个输出目的地。
2. 3. 2 日志输出方式appender(目的地)
log4j.appender.appenderName = fully.qualified.name.of.appender.class
log4j.appender.appenderName.option1 = value1

log4j.appender.appenderName.option = valueN
其中,Log4j提供的appender有以下几种:
org.apache.log4j.ConsoleAppender(控制台),
org.apache.log4j.FileAppender(文件),
org.apache.log4j.DailyRollingFileAppender(每天产生一个日志文件),
org.apache.log4j.RollingFileAppender(文件大小到达指定尺寸的时候产生一个新的文件),
org.apache.log4j.WriterAppender(将日志信息以流格式发送到任意指定的地方)
(1).ConsoleAppender选项
Threshold=WARN:指定日志消息的输出最低层次。
ImmediateFlush=true:默认值是true,意谓着所有的消息都会被立即输出。
Target=System.err:默认情况下是:System.out,指定输出控制台
(2).FileAppender 选项
Threshold=WARN:指定日志消息的输出最低层次。
ImmediateFlush=true:默认值是true,意谓着所有的消息都会被立即输出。
File=mylog.txt:指定消息输出到mylog.txt文件。
Append=false:默认值是true,即将消息增加到指定文件中,false指将消息覆盖指定的文件内容。
(3).DailyRollingFileAppender 选项
Threshold=WARN:指定日志消息的输出最低层次。
ImmediateFlush=true:默认值是true,意谓着所有的消息都会被立即输出。
File=mylog.txt:指定消息输出到mylog.txt文件。
Append=false:默认值是true,即将消息增加到指定文件中,false指将消息覆盖指定的文件内容。
DatePattern=’.'yyyy-ww:每周滚动一次文件,即每周产生一个新的文件。当然也可以指定按月、周、天、时和分。即对应的格式如下:
  1)’.'yyyy-MM: 每月
  2)’.'yyyy-ww: 每周
  3)’.'yyyy-MM-dd: 每天
  4)’.'yyyy-MM-dd-a: 每天两次
  5)’.'yyyy-MM-dd-HH: 每小时
  6)’.'yyyy-MM-dd-HH-mm: 每分钟
(4).RollingFileAppender 选项
Threshold=WARN:指定日志消息的输出最低层次。
ImmediateFlush=true:默认值是true,意谓着所有的消息都会被立即输出。
File=mylog.txt:指定消息输出到mylog.txt文件。
Append=false:默认值是true,即将消息增加到指定文件中,false指将消息覆盖指定的文件内容。
MaxFileSize=100KB: 后缀可以是KB, MB 或者是 GB. 在日志文件到达该大小时,将会自动滚动,即将原来的内容移到mylog.log.1文件。
MaxBackupIndex=2:指定可以产生的滚动文件的最大数。
2. 3. 3 日志信息的布局
log4j.appender.appenderName.layout = fully.qualified.name.of.layout.class
log4j.appender.appenderName.layout.option1 = value1

log4j.appender.appenderName.layout.option = valueN
其中,Log4j提供的layout有以下几种:
org.apache.log4j.HTMLLayout(以HTML表格形式布局),
org.apache.log4j.PatternLayout(可以灵活地指定布局模式),
org.apache.log4j.SimpleLayout(包含日志信息的级别和信息字符串),
org.apache.log4j.TTCCLayout(包含日志产生的时间、线程、类别等等信息)

2. 3. 4 日志格式控制
在配置文件中可以通过log4j.appender.A1.layout.ConversionPattern设置日志输出格式。
参数:
%p: 输出日志信息优先级,即DEBUG,INFO,WARN,ERROR,FATAL,
%d: 输出日志时间点的日期或时间,默认格式为ISO8601,也可以在其后指定格式,比如:%d{yyy MMM dd HH:mm:ss,SSS},输出类似:2002年10月18日 22:10:28,921
%r: 输出自应用启动到输出该log信息耗费的毫秒数
%c: 输出日志信息所属的类目,通常就是所在类的全名
%t: 输出产生该日志事件的线程名
%l: 输出日志事件的发生位置,相当于%C.%M(%F:%L)的组合,包括类目名、发生的线程,以及在代码中的行数。举例:Testlog4.main(TestLog4.java:10)
%x: 输出和当前线程相关联的NDC(嵌套诊断环境),尤其用到像java servlets这样的多客户多线程的应用中。
%%: 输出一个”%”字符
%F: 输出日志消息产生时所在的文件名称
%L: 输出代码中的行号
%m: 输出代码中指定的消息,产生的日志具体信息
%n: 输出一个回车换行符,Windows平台为”\r\n”,Unix平台为”\n”输出日志信息换行
可以在%与模式字符之间加上修饰符来控制其最小宽度、最大宽度、和文本的对齐方式。如:
1)%20c:指定输出category的名称,最小的宽度是20,如果category的名称小于20的话,默认的情况下右对齐。
2)%-20c:指定输出category的名称,最小的宽度是20,如果category的名称小于20的话,”-”号指定左对齐。
3)%.30c:指定输出category的名称,最大的宽度是30,如果category的名称大于30的话,就会将左边多出的字符截掉,但小于30的话也不会有空格。
4)%20.30c:如果category的名称小于20就补空格,并且右对齐,如果其名称长于30字符,就从左边交远销出的字符截掉。
3.程序中使用
3.1  写一个获得数据库连接的工具类
import java.sql.Connection;
import java.sql.SQLException;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.sql.DataSource; /**
* @projectName  Log4jTest
* @package      Log4jTest
* @fileName     DBPool.java
* @author       孙欢欢
* @date         2009-9-30
* @version      1.0
* @description  通过从数据库连接池获取连接和关闭连接
*/
public class DBPool {
private static DataSource ds = null;
private static Connection conn = null;

public static Connection getConnection() {
try {
if(conn==null){
ds = (DataSource) (new InitialContext())
.lookup("java:comp/env/jdbc/TestDB");
}
if (ds != null) {
conn = ds.getConnection();
}
} catch (NamingException e) {
e.printStackTrace();
} catch (SQLException e) {
e.printStackTrace();
}
return conn;
}
public static void closeConnection() {
try {
if (conn != null) {
conn.close();
conn=null;
}
} catch (SQLException e) {
e.printStackTrace();
}
}

}
3.2 继承JDBCAppender类
重写closeConnection,getConnection,getLogStatement,close四个方法:

package Log4jTest;

import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;

import org.apache.log4j.jdbc.JDBCAppender;
import org.apache.log4j.spi.ErrorCode;
import org.apache.log4j.spi.LoggingEvent;

/**
* @projectName Log4jTest
* @package Log4jTest
* @fileName JDBCPoolAppender.java
* @author 孙欢欢
* @date 2009-9-30
* @version 1.0
* @description 为了能使用数据库连接池,必须继承JDBCAppender,并重写其closeConnection,getConnection,
*              getLogStatement三个方法
*/

public class JDBCPoolAppender extends JDBCAppender {

@Override
public void closeConnection(Connection con) {
DBPool.closeConnection(con);
}

@Override
public Connection getConnection() throws SQLException {
if (connection == null) {
connection = DBPool.getConnection();
}
return connection;
}

@Override
public String getLogStatement(LoggingEvent event) {
StringBuffer sbuf = new StringBuffer();
sbuf.append(layout.format(event));
if (layout.ignoresThrowable()) {
sbuf.delete(sbuf.length() - 2, sbuf.length());
String[] s = event.getThrowableStrRep();
if (s != null) {
for (int j = 0; j < s.length; j++) {
sbuf.append("\r\n ");
sbuf.append(s[j]);
}
}
sbuf.append("')");
}
return sbuf.toString();
}

@Override
public void execute(String sql) throws SQLException {

Connection con = null;
Statement stmt = null;
String name = "张三";
System.out.println(sql);

int end = sql.lastIndexOf(")");
sql = sql.substring(0, end) + ",'" + name + "')";

System.out.println(sql);

try {
con = getConnection();

stmt = con.createStatement();
stmt.executeUpdate(sql);
} catch (SQLException e) {
if (stmt != null)
stmt.close();
throw e;
}
stmt.close();
    //closeConnection(con);

}

  
3.3 在程序中使用 test.jsp
import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.log4j.Logger;

public class dfsdg extends HttpServlet {
protected void service(HttpServletRequest arg0, HttpServletResponse arg1)
throws ServletException, IOException {
Logger log=Logger.getLogger(getClass());
log.debug("测试log4j");
}
}
结果:
控制台日志:
DEBUG[PRIORITY]
[NDC]
http-80-1[thread] ndfsdg[CATEGORY]
测试log4j[MESSAGE]

数据库记录:







4. 附录:log4j.perporties
# Set log levels #  
log4j.rootLogger = DEBUG, Console, LogFile,DATABASE  

log4j.addivity.org.apache=true 
# ??????  
log4j.appender.Console=org.apache.log4j.ConsoleAppender  
log4j.appender.Threshold=DEBUG  
log4j.appender.Console.Target=System.out  
log4j.appender.Console.layout=org.apache.log4j.PatternLayout  
#log4j.appender.Console.layout.ConversionPattern=[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n  
log4j.appender.Console.layout.ConversionPattern=[start]%d{DATE}[DATE]%n%p[PRIORITY]%n%x[NDC]%n%t[thread] n%c[CATEGORY]%n%m[MESSAGE]%n%n  
#?????  
log4j.appender.LogFile=org.apache.log4j.FileAppender  
log4j.appender.LogFile.File=file.log  
log4j.appender.LogFile.Append=false 
log4j.appender.LogFile.layout=org.apache.log4j.PatternLayout  
log4j.appender.LogFile.layout.ConversionPattern=[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n  
# Use this layout for LogFactor 5 analysis  
# ???????  
log4j.appender.ROLLING_FILE=org.apache.log4j.RollingFileAppender  
log4j.appender.ROLLING_FILE.Threshold=ERROR  
log4j.appender.ROLLING_FILE.File=rolling.log //????,??????${java.home}?rolling.log  
log4j.appender.ROLLING_FILE.Append=true //true\:?? false\:??  
log4j.appender.ROLLING_FILE.MaxFileSize=10KB //??????  
log4j.appender.ROLLING_FILE.MaxBackupIndex=1 //???  
log4j.appender.ROLLING_FILE.layout=org.apache.log4j.PatternLayout  
log4j.appender.ROLLING_FILE.layout.ConversionPattern=[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n  
 
#???socket  
log4j.appender.SOCKET=org.apache.log4j.RollingFileAppender  
log4j.appender.SOCKET.RemoteHost=localhost  
log4j.appender.SOCKET.Port=5001 
log4j.appender.SOCKET.LocationInfo=true 
# Set up for Log Facter 5 
log4j.appender.SOCKET.layout=org.apache.log4j.PatternLayout  
log4j.appender.SOCET.layout.ConversionPattern=[start]%d{DATE}[DATE]%n%p[PRIORITY]%n%x[NDC]%n%t[thread]%n%c[CATEGORY]%n%m[MESSAGE]%n%n  
 
# Log Factor 5 Appender  
log4j.appender.LF5_APPENDER=org.apache.log4j.lf5.LF5Appender  
log4j.appender.LF5_APPENDER.MaxNumberOfRecords=2000 
# ???????  
log4j.appender.MAIL=org.apache.log4j.net.SMTPAppender  
log4j.appender.MAIL.Threshold=FATAL  
log4j.appender.MAIL.BufferSize=10 
log4j.appender.MAIL.From=web@www.wuset.com  
log4j.appender.MAIL.SMTPHost=www.wusetu.com  
log4j.appender.MAIL.Subject=Log4J Message  
log4j.appender.MAIL.To=web@www.wusetu.com  
log4j.appender.MAIL.layout=org.apache.log4j.PatternLayout  
log4j.appender.MAIL.layout.ConversionPattern=[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n  
# ?????  
log4j.appender.DATABASE=Log4jTest.JDBCPoolAppender  
#log4j.appender.DATABASE.URL=jdbc\:mysql\://localhost\:3306/test  
#log4j.appender.DATABASE.driver=com.mysql.jdbc.Driver  
#log4j.appender.DATABASE.user=root  
#log4j.appender.DATABASE.password=000000  
log4j.appender.DATABASE.sql = INSERT INTO dbcplog(occur_date,thread_name,cat,level,info,line,user) values('%d{yyyy-MM-dd HH:mm:ss}','%t','%c','%p','%m','%L',
log4j.appender.DATABASE.layout=org.apache.log4j.PatternLayout  
log4j.appender.DATABASE.layout.ConversionPattern=[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n %L 
 
log4j.appender.A1=org.apache.log4j.DailyRollingFileAppender  
log4j.appender.A1.File=SampleMessages.log4j  
log4j.appender.A1.DatePattern=yyyyMMdd-HH?.log4j?  
log4j.appender.A1.layout=org.apache.log4j.xml.XMLLayout  
#???Appender  
log4j.appender.im = net.cybercorlin.util.logger.appender.IMAppender  
log4j.appender.im.host = mail.cybercorlin.net  
log4j.appender.im.username = username  
log4j.appender.im.password = password  
log4j.appender.im.recipient = corlin@cybercorlin.net  
log4j.appender.im.layout=org.apache.log4j.PatternLayout  
log4j.appender.im.layout.ConversionPattern =[framework] %d - %c -%-4r [%t] %-5p %c %x - %m%n 

0
0
分享到:
评论
2 楼 长安春雪 2009-10-14  
mwmw 写道
大致过了一下你的配置以及写法,我有以下建议,可能由于才疏学浅,还望指教。

1. 你这个Appender不能去处理Business数据,因为他是跟Log4J一起启动的,启动很早,如果在这里面写上Business的东西很是不好,所以你仅仅是把原来写在文件里面的Log放到了数据库里。意义不大(如果权当是练习用的话还好)。
2. 其实你也不用继承那个Appender了吧,因为Log4J自己带的那个JDBCAppender也是能凑活着用的,只需要配置一下就好了吧。 (我自己的理解)
3. 如果你自己写Appender,建议这样写,
   (1).建一个Queue,把Log都写到这个Queue里面
   (2).启动一个Thread,让这个Thread去从Queue里面拿东西往数据库里面写
  这样的话,可能性能会更好一点。

才疏学浅,还望指教。


首先,说明一下这样做的原因:最近做一个项目,要求对log4j的日志进行管理,并且要记录是那个用户使用过程中产生的日志信息。看了一下log4j的API文档,文档里有这样一段话:
   WARNING: This version of JDBCAppender is very likely to be completely replaced in the future. Moreoever, it does not log exceptions. The JDBCAppender provides for sending log events to a database.

Each append call adds to an ArrayList buffer. When the buffer is filled each log event is placed in a sql statement (configurable) and executed. BufferSize, db URL, User, & Password are configurable options in the standard log4j ways.

The setSql(String sql) sets the SQL statement to be used for logging -- this statement is sent to a PatternLayout (either created automaticly by the appender or added by the user). Therefore by default all the conversion patterns in PatternLayout can be used inside of the statement. (see the test cases for examples)

Overriding the getLogStatement(org.apache.log4j.spi.LoggingEvent) method allows more explicit control of the statement used for logging.

For use as a base class:

•Override getConnection() to pass any connection you want. Typically this is used to enable application wide connection pooling.
•Override closeConnection(Connection con) -- if you override getConnection make sure to implement closeConnection to handle the connection you generated. Typically this would return the connection to the pool it came from.
•Override getLogStatement(LoggingEvent event) to produce specialized or dynamic statements. The default uses the sql option value.
   而且我的这个项目要用到Dbcp数据库连接池,故对原来的JDBCAppender继承,并重写了父类中的几个方法。
    中而言之,这样做是项目需求决定的。
1 楼 mwmw 2009-10-13  
大致过了一下你的配置以及写法,我有以下建议,可能由于才疏学浅,还望指教。

1. 你这个Appender不能去处理Business数据,因为他是跟Log4J一起启动的,启动很早,如果在这里面写上Business的东西很是不好,所以你仅仅是把原来写在文件里面的Log放到了数据库里。意义不大(如果权当是练习用的话还好)。
2. 其实你也不用继承那个Appender了吧,因为Log4J自己带的那个JDBCAppender也是能凑活着用的,只需要配置一下就好了吧。 (我自己的理解)
3. 如果你自己写Appender,建议这样写,
   (1).建一个Queue,把Log都写到这个Queue里面
   (2).启动一个Thread,让这个Thread去从Queue里面拿东西往数据库里面写
  这样的话,可能性能会更好一点。

才疏学浅,还望指教。

相关推荐

    数据库系统管理与维护(Oracle)第三次作业.doc

    NORMAL 题目18、一个事务中所有对数据库的操作是一个不可分割的操作序列,这个性质称为事 务的( A )。 选择一项: a. 原子性 b. 隔离性 c. 独立性 d. 孤立性 题目19、当Oracle数据库启动时,如果由于操作系统的...

    数据库操作语句大全(sql)

    13、对数据库进行操作: 分离数据库: sp_detach_db; 附加数据库:sp_attach_db 后接表明,附加需要完整的路径名 14.如何修改数据库的名称: sp_renamedb 'old_name', 'new_name' 二、提升 1、说明:复制表(只...

    orcale常用命令

    但此时不对数据文件和日志文件进行校验检查。 3、startup open dbname 先执行“nomount”,然后执行“mount”,再打开包括Redo log文件在内的所有数据库文件, 这种方式下可访问数据库中的数据。 4、startup,...

    oracle详解

    导入/导出是ORACLE幸存的最古老的两个命令行工具,其实我从来不认为Exp/Imp是一种好的备份方式,正确的说法是Exp/Imp只能是一个好的转储工具,特别是在小型数据库的转储,表空间的迁移,表的抽取,检测逻辑和物理...

    Windows下MySQL主从复制的配置方法

    2、从服务器上面也启动一个 I/O thread,通过配置好的用户名和密码, 连接到主服务器上面请求读取二进制日志,然后把读取到的二进制日志写到本地的一个Realy log(中继日志)里面。 3、从服务器上面同时开启一个 SQL ...

    最全的oracle常用命令大全.txt

    但此时不对数据文件和日志文件进行校验检查。 3、startup open dbname 先执行“nomount”,然后执行“mount”,再打开包括Redo log文件在内的所有数据库文件, 这种方式下可访问数据库中的数据。 4、startup,...

    Oracle9i的init.ora参数中文说明

    请注意所有用户均可读取或写入 UTL_FILE_DIR 参数中指定的所有文件。 值范围: 任何有效的目录路径。 默认值: 无 plsql_v2_compatibility: 说明: 设置 PL/SQL 兼容级。如果设置为 FALSE, 将执行 PL/SQL V3 行为, ...

    citrix 中文管理操作手册

    配置 SQL Server 数据库以便进行配置日志记录 150 配置 Oracle 数据库以便进行配置日志记录 151 设置“配置日志记录”属性 151 设置“配置日志记录”属性 151 委派“配置日志记录”管理 152 使用配置日志 152 查看...

    oracle学习文档 笔记 全面 深刻 详细 通俗易懂 doc word格式 清晰 连接字符串

     数据查询语言 (Data Query Language, DQL) 是SQL语言中,负责进行数据查询而不会对数据本身进行修改的语句,这是最基本的SQL语句。例如:SELECT(查询)  数据控制语言Data Controlling Language(DCL),用来...

    oracle实验报告

    PL/SQL块中的可执行部分是由一系列语句组成的(包括对数据库进行操作的SQL语句,PL/SQL语言的各种流程控制语句等)。在块中对数据库查询,增、删、改等对数据的操作是由SQL命令完成的。在PL/SQL块中,可以使用SQL的...

    MySQL 5.1参考手册

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? 1.5.2. ...

    C#.net_经典编程例子400个

    130 实例095 使用ErrorProvider组件验证文本框输入 130 实例096 利用ErrorProvider组件查看数据集中的错误 132 3.3 EventLog组件 134 实例097 使用EventLog组件读写Windows系统事件日志 134 ...

    [php]mysql数据库操作——DB类

    -- 作 用:数据库执行语句,可执行查询添加修改删除等任何sql语句 -- 参 数:$sql sql语句(必填) -- 返回值:布尔 -- 实 例:无 *******************************************************************/ ...

    IIS6.0 IIS,互联网信息服务

    除了匿名访问用户(Anonymous)外,IIS中的FTP将使用Windows 2000自带的用户库(可在“开始→程序→管理工具→计算机管理”中找到“用户”一项来进行用户库的管理)。 最后,关键一步还有就是将你的电脑变为网络中的...

    MySQL 5.1参考手册 (中文版)

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? 1.5.2. ...

    mysql官方中文参考手册

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? 1.5.2. ...

    MYSQL中文手册

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? ...

    MySQL 5.1参考手册中文版

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? ...

    MySQL 5.1中文手冊

    1.4. MySQL数据库管理系统概述 1.4.1. MySQL的历史 1.4.2. MySQL的的主要特性 1.4.3. MySQL稳定性 1.4.4. MySQL表最大能达到多少 1.4.5. 2000年兼容性 1.5. MaxDB数据库管理系统概述 1.5.1. 什么是MaxDB? 1.5.2. ...

    网管教程 从入门到精通软件篇.txt

     对驱动器进行快速格式化。不扫描驱动器看是否有坏区域,因此只应对以前格式化过的驱动器使用该参数。  /fs:file-system  指定要使用的文件系统:FAT、FAT32 或 NTFS 。如果未指定文件系统,将使用现有的文件...

Global site tag (gtag.js) - Google Analytics