Пользовательская регистрация для сбора сообщений во время выполнения - PullRequest
8 голосов
/ 16 июня 2009

Есть ли способ создать Log4j Logger во время выполнения, который будет собирать сообщения регистрации в буфер?

В настоящее время у меня есть класс, который регистрирует ряд событий. Для удаленного приложения, которому необходимо отслеживать зарегистрированные события, я бы хотел просто поменять регистратор, который регистрирует в буфере, а затем извлечь буфер, а не рефакторизовать класс. Например. учитывая что-то вроде:

Class Foo{
   Logger log = ....;

   public void doSomething(){ 
      log.debug(...
      .. actual code
      log.debug(...
   }
}

// что я хотел бы сделать из внешнего кода:

String showFooLog(){
   Foo f = new Foo();
   f.log=new Logger(... 
   f.doSomething();
   return f.log.contents();
}

Возможно ли это?

Редактировать: Нашел более короткое решение, на которое указывает публикация Джареда (хотя это все еще не безопасно для потоков). Спасибо за помощь.

 Logger l = Logger.getLogger( ...  );
 StringWriter writer = new StringWriter();
 WriterAppender appender = new WriterAppender( new HTMLLayout(), writer );
 l.addAppender( appender );
    ... run code here
  writer.flush();
 l.removeAppender( appender );
 return writer.toString()

Ответы [ 2 ]

4 голосов
/ 16 июня 2009

Это абсолютно возможно - хотя вам, вероятно, понадобится создать свой собственный Appender. Это действительно легко сделать, хотя. Вот примерный пример (нужно подумать о безопасности потоков ... это не потокобезопасно ... и я не уверен, что мне нравится статика ... но этого должно быть достаточно, чтобы вас подтолкнуть в правильном направлении):

public class BufferAppender extends org.apache.log4j.AppenderSkeleton {
    private static Map<String, StringBuffer> buffers = new HashMap<String, StringBuffer>();

    @Override
    protected void append(LoggingEvent evt) {
        String toAppend = this.layout.format(evt);
        StringBuffer sb = getBuffer(evt.getLoggerName());
        buffer.append(toAppend);
    }

    public static String getBufferContents(String loggerName) {
            StringBuffer sb = buffers.get(sb);
            if(sb == null) {
               return null;
            } else {
               return sb.toString();
            }
    }

    public static void clearBuffer(String loggerName) {
            createBuffer(loggerName);
    }

    private static StringBuffer getBuffer(String loggerName) {
       StringBuffer sb = buffers.get(loggerName);
       if(sb == null) {
            sb = createBuffer(loggerName);
       }
       return sb;
    }

    private static StringBuffer createBuffer(String loggerName) {
       StringBuffer sb = new StringBuffer();
       buffers.put(loggerName, sb);
       return sb;
    }
}
2 голосов
/ 16 июня 2009

Вы можете создать подкласс org.apache.log4j.WriterAppender и предоставить ему ByteArrayOutputStream для хранения любых сообщений. См. Другие подклассы WriterAppender для увлечения. Затем вы можете предоставить экземпляр этого объекта вашему регистратору для добавления через addAppender.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...