2010-03-16 30 views
5

Tôi đã có một thiết lập log4J trong đó logger gốc được cho là để ghi các thông báo mức ERROR và ở trên giao diện điều khiển và một trình ghi nhật ký khác ghi lại mọi thứ vào syslog.log4j rootLogger dường như kế thừa mức nhật ký của trình ghi nhật ký khác. Tại sao?

log4j.properties là:

# Root logger option 
log4j.rootLogger=ERROR,R 

log4j.appender.R=org.apache.log4j.ConsoleAppender 
log4j.appender.R.layout=org.apache.log4j.PatternLayout 
log4j.appender.R.layout.ConversionPattern=%d %p %t %c - %m%n 

log4j.logger.SGSearch=DEBUG,SGSearch 
log4j.appender.SGSearch=org.apache.log4j.net.SyslogAppender 
log4j.appender.SGSearch.SyslogHost=localhost 
log4j.appender.SGSearch.Facility=LOCAL6 
log4j.appender.SGSearch.layout=org.apache.log4j.PatternLayout 
log4j.appender.SGSearch.layout.ConversionPattern=[%-5p] %m%n 

Trong mã tôi làm

private static final Logger logger = Logger.getLogger("SGSearch"); 
. 
. 
. 
logger.info("Commencing snapshot index [" + args[1] + " -> " + args[2] + "]"); 

gì đang xảy ra là tôi có được giao diện điều khiển khai thác gỗ cho tất cả các cấp khai thác gỗ. Điều gì dường như đang xảy ra là mức độ cho SGSearch ghi đè mức thiết lập cho trình ghi gốc bằng cách nào đó. Tôi không thể hiểu được.

Tôi đã xác nhận rằng Log4J đang đọc nộp các tài sản tôi nghĩ rằng đó là, và không có khác (thông qua các tùy chọn -Dlog4j.debug)

+0

Tôi gặp sự cố/sự nhầm lẫn này. Xem http://stackoverflow.com/questions/3023690/why-is-log4j-rootlogger-not-filtering-log-events-according-to-event-level. –

Trả lời

13

Cách thức hoạt động của chuỗi Log4j là một chút phản trực giác (ít nhất là đối với tôi). Xem the log4j manual. Nếu mức yêu cầu bằng hoặc cao hơn ngưỡng của trình ghi nhật ký phù hợp nhất, nó được chấp nhận. Khi yêu cầu được chấp nhận, nó sẽ được xử lý bởi chuỗi hoàn chỉnh của tổ tiên bất kể ngưỡng của chúng!

Để ngăn chặn các hành vi chaining, thêm:

log4j.additivity.SGSearch=false 

Điều này sẽ gây ra các yêu cầu xử lý bởi logger SGSearch không còn được chuyển lên chuỗi.

Một đề xuất khác: không đặt tên cho trình ghi nhật ký và người phụ trang của bạn giống nhau, bởi vì tại một thời điểm nào đó trong tương lai bạn hoặc đồng nghiệp sẽ kết hợp chúng. Tên trình ghi nhật ký phải cho biết loại đăng nhập nào được xử lý, tên của người phụ trách phải chỉ định vị trí đăng nhập. Vì vậy, trong trường hợp này tôi sẽ nghĩ 'SGSearch' có thể là tên logger, và appender nên được gọi là 'LocalSysLog'.

BTW: Theo tôi, bạn đang làm điều đúng bằng cách hạn chế trình ghi nhật ký với ngưỡng cao và hạ thấp trình ghi nhật ký cụ thể.Điều này tránh lộn xộn từ các thư viện lớn (Apache có một vài cái khét tiếng).

+1

Điều làm tôi ngạc nhiên là Log4j không áp dụng ngưỡng sự kiện nhật ký của logger mẹ (nơi logger gốc là cha mẹ trên cùng) độc lập với logger con của họ. –

+0

Cảm ơn bạn! Câu trả lời của bạn rất hữu ích. Tôi tham khảo câu trả lời của bạn trong câu trả lời của tôi tại http://stackoverflow.com/questions/3023690/why-is-log4j-rootlogger-not-filtering-log-events-according-to-event-level/3024279#3024279 với tôi câu hỏi tương tự tại http://stackoverflow.com/questions/3023690/why-is-log4j-rootlogger-not-filtering-log-events-according-to-event-level. –

+1

"Khi yêu cầu được chấp nhận, nó được xử lý bởi chuỗi hoàn chỉnh của tổ tiên bất kể ngưỡng của họ!" Nếu điều này là đúng, thì đây không phải là lỗi trong Log4j? Hành vi đó rất phản trực giác phải là một lỗi. –

5

thông tin nhanh về Levels

Log4J Mức

Người ghi nhật ký có thể được chỉ định các cấp. Bộ số có thể là DEBUG, INFO, WARN, ERROR và FATAL là được định nghĩa trong lớp org.apache.log4j.Level .

Nếu một trình ghi nhật ký cụ thể không được gán mức , thì nó sẽ kế thừa một từ tổ tiên gần nhất với cấp độ được chỉ định .

Trình ghi nhật ký nằm ở đầu số cấu trúc phân cấp trình ghi nhật ký. Nó luôn tồn tại và luôn có cấp được chỉ định.

Tôi đã thay đổi cấu hình log4j mẫu của bạn để làm việc theo cách này:

# Root logger option 
log4j.rootLogger=ALL,R 

log4j.appender.R=org.apache.log4j.ConsoleAppender 
log4j.appender.R.Target=System.out 
log4j.appender.R.layout=org.apache.log4j.PatternLayout 
log4j.appender.R.layout.ConversionPattern=%d %p %t %c - %m%n 
log4j.appender.R.Threshold=ERROR 

log4j.appender.SGSearch=org.apache.log4j.net.SyslogAppender 
log4j.appender.SGSearch.SyslogHost=localhost 
log4j.appender.SGSearch.Facility=LOCAL6 
log4j.appender.SGSearch.layout=org.apache.log4j.PatternLayout 
log4j.appender.SGSearch.layout.ConversionPattern=[%-5p] %m%n 
log4j.appender.SGSearch.Threshold=DEBUG 

Tôi hy vọng điều này sẽ giúp bạn.

+0

Cảm ơn. Điều đó làm việc nhưng tôi thấy tôi đã cần phải thêm dòng "log4j.logger.SGSearch = ALL, SGSearch" cũng như ví dụ bạn đã cung cấp. – AndrewR

+0

@AndrewR: Hoặc bạn có thể đã làm điều này 'log4j.appender.SGSearch.Threshold = ALL' nhưng sau đó điều đó sẽ làm cho 'log4j.rootLogger' vô ích (nếu tôi không nhầm). –

+0

Tôi nghĩ rằng giải pháp này là tối ưu. Xem gợi ý của tôi dưới đây. –

Các vấn đề liên quan