PIXNET Logo登入

Jemmy Walker

跳到主文

部落格全站分類:不設分類

  • 相簿
  • 部落格
  • 留言
  • 名片
  • 8月 02 週一 201011:12
  • Log4J排除<root>的output

  通常在log4j.xml會有如下的配置:

<root>
    <level value="INFO" />
    <appender-ref ref="stdout" />
</root>

  影響所及,任何一個class只要是log到INFO等級以上的,都會被<root>帶到stdout這個appender去寫出,通常是console。Console的IO也是會影響效能。若希望自己的<logger>不為<root>所影響,則可在log4j.xml做如下設定,將additivity設為false:

<logger name="com.mycompany" additivity="false">
    <level value="INFO" />
    <appender-ref ref="dynadailyrolling" />
</logger>

  若是由程式產出logger物件,要避免<root>影響,可增加以下這行:

org.apache.log4j.Logger log
    = org.apache.log4j.Logger.getLogger(name);
log.setAdditivity(false);

(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(217)

  • 個人分類:Log
▲top
  • 5月 27 週四 201016:36
  • TimeAndSizeRollingAppender

  一段時間沒記Blog了,顯示筆者狀態由【研發】轉為【專案】。研發時用Survey最新技術看是否有助提升開發品質,專案時則需選擇最穩定技術,取得進度與風險之間的最佳平衡。三年前接手他人銀行專案前,我為該專案研發最適用的Framework,即使專案成員在程式能力不強,依然需當作客戶看待。之後我接手成為該專案Leader,卻屢屢與其中一位成員衝突,該成員說詞是為何以前可以現在不行,而我回答就是因為可以,前Leader才會被換掉。最後身為Leader,我把他換下來了。角色的轉換,不單關注焦點思維不同,連決策及身負的責任也殊異。   以上與本主題無關,目前要著手的專案,對Log有個By Size與By Time的需求。目前最新的Log4J核心Jar並無此功能,週邊我倒是找到兩個,一個是今年5/18釋出的TimeAndSizeRollingAppender,自http://simonsiteblog.blogspot.com/取得,並無Maven Repository。所以得比照Oracle的JDBC Jar方式放置到Local Repository。以下是用log4j.xml配置:

<appender name="DateAndSize" class="org.apache.log4j.appender.TimeAndSizeRollingAppender">
    <param name="DatePattern" value="'.'yyyy-MM-dd'.log'"/> <!--By Date設定 -->
    <param name="File" value="C:/logs/sample.log" />
    <param name="Threshold" value="DEBUG"/>
    <param name="MaxFileSize" value="20KB"/>
    <param name="MaxRollFileCount" value="10"/>
    <param name="ScavengeInterval" value="30000"/>  <!--間隔30秒輪詢,超出MaxFileSize就壓縮 -->
    <param name="BufferedIO" value="false"/>
    <param name="CompressionAlgorithm" value="GZ"/>
    <layout class="org.apache.log4j.PatternLayout">
           <param name="ConversionPattern" value="%d{yyyy/MM/dd HH:mm:ss} %-5p [%F:%L] : %m%n" />
    </layout>
</appender>

  得到Log檔清單如右:sample.log、sample.log.2010-05-27.log.1.gz、sample.log.2010-05-27.log.2.gz、sample.log.2010-05-27.log.3.gz…。   另一個就不好用,叫CompositeRollingAppender,會產出sample.log、sample.log.1、sample.log.2…,但換到第二天時,只有sample.log會變成sample.log.2010-05-26.log,而有Index的log並不會跟著變更檔名,還會被今天的Log蓋過去。
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(202)

  • 個人分類:Log
▲top
  • 4月 02 週五 201017:25
  • SLF4J的API和impl版本要同步

  踹JPA過程,老是遇到如下的Exception: Caused by: java.lang.AbstractMethodError: org.slf4j.impl.Log4jLoggerAdapter.trace(Ljava/lang/String;Ljava/lang/Object;Ljava/lang/Object;)V   搞了半天,slf4j-api和slf4j-log12沒有同步到同一版本,即1.5.8。實在踹老半天>"<
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(103)

  • 個人分類:Log
▲top
  • 2月 24 週三 201013:10
  • Jar Hell III: Log4J 1.2.15在M2Eclipse的Issue及解法

  Log4J的1.3版還在阿法貝塔階段。1.2版最新到1.2.15,但用於Eclipse上的Maven2卻有個Issue。在執行Maven Clean後再執行Maven Package會Build Failure,有以下的錯誤訊息: [WARNING] Invalid POM for javax.jms:jms:jar:1.1, transitive dependencies (if any) will not be available, enable debug logging for more details
[WARNING] Invalid POM for com.sun.jdmk:jmxtools:jar:1.2.1, transitive dependencies (if any) will not be available, enable debug logging for more details
[WARNING] Invalid POM for com.sun.jmx:jmxri:jar:1.2.1, transitive dependencies (if any) will not be available, enable debug logging for more details   這些loss的Jar在repository都空有其pom.xml檔卻無其jar檔。反而使用Eclipse的Project/Clean後,再執行Maven Package才能Build Success。但回到1.2.14版卻無此問題,經過Dependency Graph才得知Log4J 1.2.15依賴上述三個Jar之故。為何經過Project/Clean後再Package就沒問題?唔!無解,可能是循環依賴所致吧!   2010/3/11補述。後來找到引用1.2.15的解法,dependency設定如下:

<dependency>
    <groupId>log4j</groupId>
    <artifactId>log4j</artifactId>
    <version>1.2.15</version>
        <exclusions>
       <exclusion>
      <groupId>javax.jms</groupId>
      <artifactId>jms</artifactId>
       </exclusion>
       <exclusion>
      <groupId>com.sun.jdmk</groupId>
      <artifactId>jmxtools</artifactId>
       </exclusion>
       <exclusion>
      <groupId>com.sun.jmx</groupId>
      <artifactId>jmxri</artifactId>
       </exclusion>
       <exclusion>
      <groupId>javax.mail</groupId>
      <artifactId>mail</artifactId>
       </exclusion>
    </exclusions>
</dependency>

  利用排除之法就能引用1.2.15來Maven Package。2010/5/12補充:1.2.16版就沒這個情形。
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(58)

  • 個人分類:Log
▲top
  • 10月 25 週日 200923:53
  • Log4J依不同class產出不同log file之二,加Daily Rolling

  上個月寫個Log4J以類別全名作為檔名的Log檔,每個類別都有自己的Log file。若還要再加個需求是Log File可以Daily Rolling,承襲上次的寫法也不困難:
public class DynaDailyRollingAppender extends DailyRollingFileAppender {
    private static String oldFileName = null;
    private static String oldPath = null;
    public void generateLogFile(LocationInfo info) {       
        if (oldPath == null) {
            oldPath = this.fileName.substring(0, this.fileName.lastIndexOf("test"));
        }
        SimpleDateFormat sdf = new SimpleDateFormat(this.getDatePattern());
        String fileName1 = oldPath;
        fileName1 += info.getClassName() + sdf.format(Calendar.getInstance().getTime());
        oldFileName = fileName1;
        this.setFile(fileName1);   
        this.activateOptions();
    }
    @Override
    protected void subAppend(LoggingEvent event) {
        String className =  event.getLocationInformation().getClassName();
        this.logger1.info("Class:" + className);
        if (oldFileName != className) {
            this.generateLogFile(event.getLocationInformation());
        }
        super.subAppend(event);
    }
}
  在log4j.properties若設成DailyRolling的話,會有這樣的屬性設定:
log4j.appender.dynadailyrolling.DatePattern='.'yyyy-MM-dd'.log'
  這樣就會在log file後面補上.2009-10-25.log(以今天為例),是故上述getDatePattern便是取得'.'yyyy-MM-dd'.log',再用java.text.SimpleDateFormat抓今天的日期進行format,就得到我們要的檔名。
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(224)

  • 個人分類:Log
▲top
  • 10月 20 週二 200916:26
  • SLF4J初體驗

  其實SLF4J學起來還蠻快的。會需要兩個Jar,一是slf4j-api.jar,第二個通常是slf4j-log4j12.jar(用於Log4J 1.2.x版),若想換成Apache的,則把第二個換成slf4j-jcl.jar就可以了。可是要是出現兩個…,slf4j-api應該是先找到第一個為主,沒事就別亂冒險。而NOP則是No OPeration之意。logback則是直接implment slf4j,血統最純。
bindings
  SLF4J的Sample如下:
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
  final Logger logger = LoggerFactory.getLogger(My.class);   // 從Factory取得Facade,一次用了兩個Design Pattern
 
  在Apache的JCL也有類似的,但只能轉接到Log4J。就是在commons-logging.properties檔內容設定如下:
org.apache.commons.logging.Log=org.apache.comons.logging.impl.Log4JLogger
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(2,062)

  • 個人分類:Log
▲top
  • 9月 24 週四 200900:05
  • Log4J依不同class產出不同log file

  寫了幾年的Java,最弱的部份是Log,現在看來還是差不多。最近在改寫Framework時才對Log4J的用法稍有體會,不然也是渾渾噩噩看別人怎麼配置,自己也跟著配置。
  2006年曾設計Logger Proxy委託天津同事開發,其目的有二:一是預設按class full name產生log檔,二是避開像JBoss本身的log4j.properties影響。這樣做效益有好有壞,壞就壞在Ap Server會記一份,自己又用Proxy記了一份,而且不只如此,移到不同的AP Server或Web Server,因WAR或EAR的目錄結構不同,連帶的Proxy跟著改寫,無法通用。
  後來在Google找有無可依不同的class name為檔名產出不同的log檔,是有接近的solution,但不完全滿足其需求。也間接了解了log4j.properties真正的配置方式:
log4j.rootLogger = INFO, stdout
log4j.category.com.opensymphony=DEBUG
log4j.category.org.apache.struts2=INFO, rolling
  原來Log4J是由Logger、Appender和Layout決定。後兩者設定方式還算清楚,而Logger其實可以模擬做到依不同class或package產出不同的log file。上例的log4j.rootLogger、log4j.category.package.class就是一種Logger,rootLogger是super Logger可以記錄所有class的Log,而log4j.category.後面是接package甚至是class full name。
  等於(=)後面以逗號分隔,第一個參數是Level,第二個以後的參數均是Appender,以log4j.category.com.opensymphony為例,雖然rootLogger的Level是INFO,但com.opensymphony這package內所有的class和子class均是DEBUG Level,除非還有更detail的package另外設Level,則以最接近的package為優先。第三例則表示還可參照rolling這個appender。
  但為何不能滿足在執行期動態決定產出的log file name,看FileAppender如下:
log4j.appender.rolling=org.apache.log4j.RollingFileAppender
log4j.appender.rolling.File=c:/logs/test
log4j.appender.rolling.MaxFileSize=100KB
log4j.appender.rolling.MaxBackupIndex=1
log4j.appender.rolling.layout=org.apache.log4j.PatternLayout
log4j.appender.rolling.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%F:%L] : %m%n
  上例的粗體字就事先把file給產出,若是目錄就會報錯,爾後在Google找到解法是去繼承RollingFileAppender。
(log4j.properties設定)
log4j.appender.dynarolling=com.xyz.util.DynaRollingAppender
log4j.appender.dynarolling.File=C:/logs/test
log4j.appender.dynarolling.MaxFileSize=100KB
log4j.appender.dynarolling.MaxBackupIndex=1
log4j.appender.dynarolling.layout=org.apache.log4j.PatternLayout
log4j.appender.dynarolling.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%F:%L] : %m%n
(source code部份)
public class DynaRollingAppender extends RollingFileAppender {
   
    private static String oldFileName = null;
    private static String oldPath = null;
    public void generateLogFile(LocationInfo info) {       
        if (oldPath == null) {
            oldPath = this.fileName.substring(0, this.fileName.lastIndexOf("test"));
        }
        String fileName1 = oldPath;
        fileName1 += info.getClassName() + ".log";
        this.logger1.info(fileName1 + "; " + this.fileName);
        oldFileName = fileName1;
        this.setFile(fileName1);   
       this.activateOptions();

    }
    @Override
    protected void subAppend(LoggingEvent event) {
        String className =  event.getLocationInformation().getClassName();
        if (oldFileName != className) {
            this.generateLogFile(event.getLocationInformation());
        }
        super.subAppend(event);
    }
}
  上例中,事先overide subAppend,換掉setFile內容,但是initial時在換掉之前就做了一次setFile,所以File參數必須是檔案,目的是取得其目錄,然後再換成class full name + ".log"格式做setFile,再activateOptions才會生效,而最後一行super.subAppend則將內容寫入新的log file。
  從程式就看到LoggingEvent含有LocationInfo類別,正是log4j使用reflection取得call它的class name, file name和line number等資訊。但這樣做有沒有效能的issue未知,之前第一次去吉隆坡出差,就曾因Logger Proxy不穩掛過。
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(4,258)

  • 個人分類:Log
▲top
  • 5月 11 週一 200916:16
  • Logger變換class name參數的技巧

  2006年委天津開發個LoggerProxy,按class名產出該class的Log檔,也加入可以指定某package以下共用同一個log檔的功能。這在Web Server上運作沒問題,卻在Java Main出現Lock現象。若同A Class hold這個log檔,同package的其他class無法再寫入同一個log檔,是因為使用了不同的Logger Instance。解法是想辦法讓每個class裡的Logger共用同一個Logger的instance,卻衍生一個問題,就是使用%c去顯示package class full name時,該class name是取決於當初Logger.getLogger(clazz)中,所傳的clazz的class name。後來意外發現Logger另一個特性:假設Logger的變數為loggerA,loggerA的%c就是當初傳的clazz(假設名為com.A),若想在%c顯示自己的com.B時,只需按如下方式取得:
  Logger loggerB = loggerA.getLogger("com.B");   // 因為getLogger是static method,透過loggerA.getLogger,loggerB就能得到loggerA屬性
(繼續閱讀...)
文章標籤

Jemmy 發表在 痞客邦 留言(0) 人氣(108)

  • 個人分類:Log
▲top
1

自訂側欄

自訂側欄

個人資訊

Jemmy
暱稱:
Jemmy
分類:
不設分類
好友:
累積中
地區:

熱門文章

  • (18,362)Windows route初體驗
  • (2,912)Java在換行字元的issue
  • (1,417)非我族類的DataTables.js:分頁和排序無作用原因
  • (1,319)Oracle的Array型態定義與存取
  • (776)OGG for Java開發
  • (542)Perl的跨行比對
  • (436)ORA-08002
  • (191)2009的Show Girl
  • (73)Notes的Agent二三事
  • (32)六句聯

文章分類

  • PostgreSQL (1)
  • Ruby (6)
  • 圖書 (18)
  • 旅行 (8)
  • OSGi (13)
  • 健康 (9)
  • Google (6)
  • 歷史 (5)
  • Spring-Security (5)
  • Java Script (11)
  • Log (8)
  • 娛樂 (25)
  • IT趨勢 (12)
  • 心情 (92)
  • 組織 (41)
  • Java基本功 (18)
  • Regex (19)
  • 新聞與政治 (46)
  • 電腦和網際網路 (47)
  • Maven (28)
  • Spring (31)
  • LotusNotes (12)
  • Java (60)
  • Oracle (17)
  • Struts (21)
  • jQuery (10)
  • 未分類文章 (1)

最新文章

  • JDOM解析XML字串(非檔案)
  • Android SDK不能用於JDK 64bit
  • 非我族類的DataTables.js:分頁和排序無作用原因
  • java.lang.IllegalStateException: Committed之解
  • PostgreSQL二三事
  • Form/Field V.S. Document/Item
  • Spring Mail
  • Ant generate manifest.mf的class-path清單
  • dhcp.bat
  • Java update Notes的DateTime欄位

最新留言

  • [21/07/31] D 於文章「複習一下Servlet的機制...」留言:
    請問更換瀏覽器 Servlet的instance vari...
  • [17/05/04] 訪客 於文章「設定Source編碼...」留言:
    謝謝你~~...
  • [15/08/23] 洪秀柱 於文章「UltraEdit轉大小寫...」留言:
    此破解法可用於 UEstudio UltraEdit V2...
  • [10/10/15] Jemmy 於文章「Perl的跨行比對...」留言:
    哈! 學長, 好久不見了。幸虧這案子沒有Nested Tag...
  • [10/10/14] Benson 於文章「Perl的跨行比對...」留言:
    如果有Nested Tag, 這就不太適用; 我有時還是乖乖...
  • [10/05/25] 世文 於文章「JSON-Lib初體驗...」留言:
    用心經營的blog~^^ 加油!<br />---<br ...
  • [10/05/15] Jemmy 於文章「千分位...」留言:
    你的解法太高深了, 有空再練^^...
  • [10/05/14] Benson 於文章「千分位...」留言:
    可能是 gxe, 不管是 perl or java, 你懂我...
  • [10/05/14] Jemmy 於文章「千分位...」留言:
    練功一下而已, 而且我是要用Java,所以無法用Perl...
  • [10/05/14] Benson 於文章「千分位...」留言:
    學弟,你的問題是什麼呢?是把在引號內數字逗號去掉嗎?s/\"...

動態訂閱

文章精選

文章搜尋

誰來我家

參觀人氣

  • 本日人氣:
  • 累積人氣: