during request processing there bunch of debug logs logged. @ point there might error logged if problem occurs. idea: when no error hapens during whole request processing ignore debugs, if error happens, see in logs preceeding , succeding debugs.
is there out-of-the-box solution (in log4j, logback or other), or must implement kind of wrapper logger, "cache" debugs per thread until needed?
it not built in solution here mys draft implementation quite minimal , easy integrate. isusing log4j2 , there no need change client code if using log4j2 or slf4j.
so corresponding test case
@test public void no_error_so_no_log() throws exception { logeventcollector.clean(); try { log.debug("hello world"); log.debug("some debug again"); } { logeventcollector.clean(); } } @test public void error_so_log_from_the_beginning() throws exception { logeventcollector.clean(); try { log.debug("hello world"); log.error("some error", new runtimeexception("whatever")); log.debug("some debug again"); } { logeventcollector.clean(); } } logeventcollector take care of initialize , cleanup on web app request thread. put servlet filter.
i have created custom appender. core of appender following:
@override public void append(logevent event) { if (level.error.islessspecificthan(event.getlevel())) logeventcollector.markerror(); if (!logeventcollector.haderror()) { logeventcollector.collect(event); return; } (logevent collected : logeventcollector.events()) push_log_out(collected); //and current 1 push_log_out(event); } method push_log_event real logging. custom implementation or delegate other 1 (like asyncappender).
the logeventcollector itself:
public class logeventcollector { static threadlocal<context> log_collector = new threadlocal<context>() { @override protected context initialvalue() { return new context(); } }; public static void clean() { log_collector.get().clean(); } static class context { boolean had_error = false; list<logevent> events = new arraylist<logevent>(); public void clean() { had_error = false; events = new arraylist<logevent>(); } } public static void markerror() { log_collector.get().had_error = true; } public static boolean haderror() { return log_collector.get().had_error; } public static void collect(logevent event) { log_collector.get().events.add(event); } public static list<logevent> events() { list<logevent> ret = log_collector.get().events; log_collector.get().events = new arraylist<logevent>(); return ret; } } i think must enough customize own needs.
Comments
Post a Comment