[PATCH] AbstractAccessLogValve: Add pre/post add log element extension points

2021-01-21 Thread Thomas Meyer
a sub class can extend before and after the addElement loop to
establish a context via thread-dependend CharArrayWriter object.
---
 java/org/apache/catalina/valves/AbstractAccessLogValve.java | 5 +
 1 file changed, 5 insertions(+)

diff --git a/java/org/apache/catalina/valves/AbstractAccessLogValve.java 
b/java/org/apache/catalina/valves/AbstractAccessLogValve.java
index e23f49d3a5..5e774c2320 100644
--- a/java/org/apache/catalina/valves/AbstractAccessLogValve.java
+++ b/java/org/apache/catalina/valves/AbstractAccessLogValve.java
@@ -685,9 +685,11 @@ public abstract class AbstractAccessLogValve extends 
ValveBase implements Access
 result = new CharArrayWriter(128);
 }
 
+preLogAddElement(result);
 for (int i = 0; i < logElements.length; i++) {
 logElements[i].addElement(result, date, request, response, time);
 }
+postLogAddElement(result);
 
 log(result);
 
@@ -699,6 +701,9 @@ public abstract class AbstractAccessLogValve extends 
ValveBase implements Access
 
 //  Protected 
Methods
 
+protected void preLogAddElement(CharArrayWriter result) {}
+protected void postLogAddElement(CharArrayWriter result) {}
+
 /**
  * Log the specified message.
  *
-- 
2.20.1


-
To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org
For additional commands, e-mail: dev-h...@tomcat.apache.org



Re: [PATCH] AbstractAccessLogValve: Add pre/post add log element extension points

2021-01-21 Thread Thomas Meyer
On Thu, Jan 21, 2021 at 03:28:12PM +0100, Romain Manni-Bucau wrote:
> Hi

Hi,
 
> Why cant it be added as element earlier at pattern parsing time? Would
> avoid to have two particular cases and keep current pattern/impl.
> A %java or so sounds more natural no?

Mhh, maybe I just share my idea of the concrete implementation, so you see
what I want to do:

Premise: The JUL logging is configured to log all below to an own handler.

public class LoggingAccessLogValve extends AbstractAccessLogValve {

private static final Log log = 
LogFactory.getLog(LoggingAccessLogValve.class);
private Map writers = new 
WeakHashMap<>();

@Override
protected void log(CharArrayWriter message) {
if(log.isInfoEnabled()) {
log.info(message);
}
}

protected void preLogAddElement(CharArrayWriter result) {
JsonGenerator jsonWriter = Json.createGenerator(result);
synchronized (this) {
writers.put(result,jsonWriter);
}
jsonWriter.writeStartObject();
}

protected void postLogAddElement(CharArrayWriter result) {
JsonGenerator jsonWriter = null;
synchronized (this) {
jsonWriter = writers.remove(result);
}
if(jsonWriter != null) {
jsonWriter.writeEnd();
jsonWriter.close();
}
}

private class JsonAccessLogElementWrapper implements AccessLogElement {

private final String jsonAttributeName;
private final AccessLogElement delegate;

public JsonAccessLogElementWrapper(AccessLogElement e, String 
name) {
delegate = e;
jsonAttributeName = name;
}

@Override
public void addElement(CharArrayWriter buf, Date date, Request 
request, Response response, long time) {
JsonGenerator jsonWriter = null;
synchronized (this) {
jsonWriter = writers.get(buf);
}
if(jsonWriter == null) {
// TODO: add warn
return;
}

// TODO: maybe even use stack/cache of CharyArrayWriter 
here, too
CharArrayWriter writer = new CharArrayWriter();
delegate.addElement(writer, date, request, response, 
time);
jsonWriter.write(jsonAttributeName, writer.toString());
}
}

@Override
protected AccessLogElement createAccessLogElement(String name, char 
pattern) {
AccessLogElement e = super.createAccessLogElement(name, 
pattern);
return new JsonAccessLogElementWrapper(e, mapName(e) + '-' + 
name);
}

@Override
protected AccessLogElement createAccessLogElement(char pattern) {
AccessLogElement e = super.createAccessLogElement(pattern);
return new JsonAccessLogElementWrapper(e, mapName(e));
}

private String mapName(AccessLogElement e) {
if(e instanceof RemoteAddrElement) {
return "remoteAddr";
} else if(e instanceof HostElement) {
return "host";
// TODO: finish
}
throw new IllegalArgumentException();
}
}

so what do you think about this approach?

mfg
thomas

> 
> Le jeu. 21 janv. 2021 à 13:59, Thomas Meyer  a écrit :
> 
> > a sub class can extend before and after the addElement loop to
> > establish a context via thread-dependend CharArrayWriter object.
> > ---
> >  java/org/apache/catalina/valves/AbstractAccessLogValve.java | 5 +
> >  1 file changed, 5 insertions(+)
> >
> > diff --git a/java/org/apache/catalina/valves/AbstractAccessLogValve.java
> > b/java/org/apache/catalina/valves/AbstractAccessLogValve.java
> > index e23f49d3a5..5e774c2320 100644
> > --- a/java/org/apache/catalina/valves/AbstractAccessLogValve.java
> > +++ b/java/org/apache/catalina/valves/AbstractAccessLogValve.java
> > @@ -685,9 +685,11 @@ public abstract class AbstractAccessLogValve extends
> > ValveBase implements Access
> >  result = new CharArrayWriter(128);
> >  }
> >
> > +preLogAddElement(result);
> >  for (int i = 0; i < logElements.length; i++) {
> >  logElements[i].addElement(result, date, request, response,
> > time);
> >