如何把log4j中的message信息存储到数据库中 DataBase

来源:互联网 发布:淘宝店如何装修视频 编辑:程序博客网 时间:2024/05/22 20:12
首先需要在log4j.xml文件中对要操作的数据库进行配置: 
<appender name="JDBC" class="test.JDBCAppenderExtended">
                                            
<!--驱动-->
        
<param name="driver" value="oracle.jdbc.driver.OracleDriver" />
                                          
<!--要连接的数据库-->
        
<param name="URL"
            value
="jdbc:oracle:thin:@192.168.1.112:1521:exam" />
        
<param name="user" value="sms2007" />
        
<param name="password" value="sms2007" />
                                           
<!--向数据库表logrecord中插入数据的sql语句-->
        
<param name="sql"
            value
=" insert into logrecord(id,packageid,userid,syscodeid,info,logtime,loglevel) values(?,?,?,?,?,to_date('%d{yyyy-MM-dd HH:mm:ss}','yyyy-MM-dd HH24:mi:ss'),'%p')" />
    
</appender>

 

下面是继承org.apache.log4j.jdbc.JDBCAppenderJDBCAppenderExtended类:
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Iterator;
import java.util.Map;

import org.apache.log4j.PatternLayout;
import org.apache.log4j.spi.ErrorCode;
import org.apache.log4j.spi.LoggingEvent;
import org.apache.log4j.MDC;

public class JDBCAppenderExtended extends org.apache.log4j.jdbc.JDBCAppender {

    
protected Connection connection = null;

    
protected String sqlStatement = "";

    
public JDBCAppenderExtended() {
        
super();
    }


    
public void append(LoggingEvent event) {
        buffer.clear();
// 清空缓冲器
        buffer.add(event);
        flushBuffer();
// 调用execute
    }


    
protected void execute(String sql) throws SQLException {
        ThreadLocal myThread 
= (ThreadLocal) MDC.get("myThread");
        
for (Iterator i = buffer.iterator(); i.hasNext();) {
            LoggingEvent event 
= (LoggingEvent) i.next();
            String message 
= (String) event.getMessage();
            Map map 
= (Map) myThread.get();
            Long packageid 
= Long.valueOf(map.get("packageid").toString());
            Long userid 
= Long.valueOf(map.get("userid").toString());
            Long operateType 
= (Long) map.get("operateType");
            Connection con 
= null;
            PreparedStatement stmt 
= null;
            PreparedStatement stmt1 
= null;
            ResultSet res 
= null;
            Statement myStmt
=null;
            String sql2 
= "select seq_logrecord_id.nextval from dual";
            Long id 
= null;
            
try {
                
if (message.length() > 2000{
                    String msg 
= message.substring(02000);
                    con 
= getConnection();
                    myStmt 
= con.createStatement();
                    res 
= myStmt.executeQuery(sql2);
                    
if (res.next()) {
                        id 
= res.getLong(1);
                    }

                    stmt 
= con.prepareStatement(sql);
                    stmt.setLong(
1, id);
                    stmt.setLong(
2, packageid);
                    stmt.setLong(
3, userid);
                    stmt.setLong(
4, operateType);
                    stmt.setString(
5, msg);
                    stmt.executeUpdate();
                    String sql1 
= "update logrecord set info=? where id=?";
                    stmt1 
= con.prepareStatement(sql1);
                    
if (message.length() > 4000{
                        message 
= message.substring(04000);
                    }

                    stmt1.setString(
1, message);
                    stmt1.setLong(
2, id);
                    stmt1.executeUpdate();
                }
 else {
                    con 
= getConnection();
                    myStmt 
= con.createStatement();
                    res 
= myStmt.executeQuery(sql2);
                    
if (res.next()) {
                        id 
= res.getLong(1);
                    }

                    stmt 
= con.prepareStatement(sql);
                    stmt.setLong(
1, id);
                    stmt.setLong(
2, packageid);
                    stmt.setLong(
3, userid);
                    stmt.setLong(
4, operateType);
                    stmt.setString(
5, message);
                    stmt.executeUpdate();
                }

            }
 catch (SQLException e) {
                
if (stmt != null)
                    stmt.close();
                
if (stmt1 != null)
                    stmt1.close();
                
if (res != null)
                    res.close();
                
if(myStmt!=null)
                    myStmt.close();
                
if(buffer!=null)
                    buffer.clear();
                closeConnection(con);
                
throw e;
            }

            
if (stmt != null)
                stmt.close();
            
if (stmt1 != null)
                stmt1.close();
            
if (res != null)
                res.close();
            
if(myStmt!=null)
                myStmt.close();
            closeConnection(con);
        }

    }


    
/**
     * Override this to return the connection , or to clean up the resource.
     * 
     * The default behavior holds a single connection open until the appender is
     * closed (typically when garbage collected).
     
*/

    
protected void closeConnection(Connection con) {
        
try {
            
if (connection != null && !connection.isClosed())
                connection.close();
        }
 catch (SQLException e) {
            errorHandler.error(
"Error closing connection", e,
                    ErrorCode.GENERIC_FAILURE);
        }

    }


    
/**
     * 
     
*/

    
public void setSql(String s) {
        sqlStatement 
= s;
        
if (getLayout() == null{
            
this.setLayout(new PatternLayout(s));
        }
 else {
            ((PatternLayout) getLayout()).setConversionPattern(s);
        }

    }


    
/**
     * Returns pre-formated statement eg: insert into LogTable (msg) values
     * ("%m")
     
*/

    
public String getSql() {
        
return sqlStatement;
    }


}

在这个实例中我们使用了ThreadLocal来进行参数上的传递,来处理不同用户下的日志记录行为。每一个用户会生成他自己唯一的ThreadLocal,不同用户之间的ThreadLocal是彼此可以区分和唯一的。每个ThreadLocal可以存储到MDC当中去。想要深入了解的朋友可以去看看关于这方面的资料,我这里也只是一个初期版本,还有很多地方需要优化,很期待大家能够一块儿探讨一下!呵呵!希望这点儿东西对一部分人有所帮助!

 

  
原创粉丝点击