Author: ravn
Date: Thu Oct  2 00:26:24 2008
New Revision: 1157

Modified:
   slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java
   
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
   
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java

Log:
now usable as a javaagent, tested with log4j

Modified: slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java
==============================================================================
--- slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java       
(original)
+++ slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java       
Thu Oct  2 00:26:24 2008
@@ -2,11 +2,11 @@
 
 import static org.slf4j.helpers.MessageFormatter.format;
 
+import java.io.ByteArrayInputStream;
+import java.io.IOException;
 import java.lang.instrument.Instrumentation;
-import java.util.Arrays;
 import java.util.Date;
-import java.util.HashSet;
-import java.util.Set;
+import java.util.Properties;
 
 import org.slf4j.instrumentation.LogTransformer;
 
@@ -20,25 +20,40 @@
 
                LogTransformer.Builder builder = new LogTransformer.Builder();
                builder = builder.addEntryExit(true);
-               
+
                if (agentArgument != null) {
-                       String[] args = agentArgument.split(",");
-                       Set<String> argSet = new 
HashSet<String>(Arrays.asList(args));
+                       Properties args = parseArguments(agentArgument);
 
-                       if (argSet.contains("verbose")) {
+                       if (args.containsKey("verbose")) {
                                builder = builder.verbose(true);
                        }
-                       
-                       if (argSet.contains("time")) {
+
+                       if (args.containsKey("time")) {
                                printStartStopTimes();
                        }
-                       
+
+                       if (args.containsKey("ignore")) {
+                               builder = 
builder.ignore(args.getProperty("ignore").split(","));
+                       }
+
                        // ... more agent option handling here
                }
 
                instrumentation.addTransformer(builder.build());
        }
 
+       private static Properties parseArguments(String agentArgument) {
+               Properties p = new Properties();
+               try {
+                       byte[] bytes = agentArgument.replaceAll(";", 
"\n").getBytes();
+                       p.load(new ByteArrayInputStream(bytes));
+               } catch (IOException e) {
+                       throw new RuntimeException(
+                                       "Could not load arguments as 
properties", e);
+               }
+               return p;
+       }
+
        /**
         * Print the start message with the time NOW, and register a shutdown 
hook
         * which will print the stop message with the time then and the number 
of

Modified: 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
==============================================================================
--- 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
  (original)
+++ 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
  Thu Oct  2 00:26:24 2008
@@ -68,7 +68,7 @@
                                sb.append("\"+ $" + (i + 1));
                        }
                }
-               sb.append("+\")\"");
+               sb.append("+\")");
 
                String signature = sb.toString();
                return signature;

Modified: 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
==============================================================================
--- 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
   (original)
+++ 
slf4j/trunk/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
   Thu Oct  2 00:26:24 2008
@@ -16,15 +16,41 @@
 import javassist.CtField;
 import javassist.NotFoundException;
 
+import org.slf4j.helpers.MessageFormatter;
+
+/**
+ * LogTransformer does the work of analyzing each class, and if appropriate add
+ * log statements to each method to allow logging entry/exit.
+ * 
+ */
 public class LogTransformer implements ClassFileTransformer {
 
+       // 
http://rwhansen.blogspot.com/2007/07/theres-builder-pattern-that-joshua.html
        public static class Builder {
+
+               /**
+                * Build and return the LogTransformer corresponding to the 
options set
+                * in this Builder.
+                * 
+                * @return
+                */
                public LogTransformer build() {
+                       if (verbose) {
+                               System.err.println("Creating LogTransformer");
+                       }
                        return new LogTransformer(this);
                }
 
                boolean addEntryExit;
 
+               /**
+                * Should each method log entry (with parameters) and exit (with
+                * parameters and returnvalue)?
+                * 
+                * @param b
+                *            value of flag
+                * @return
+                */
                public Builder addEntryExit(boolean b) {
                        addEntryExit = b;
                        return this;
@@ -32,38 +58,59 @@
 
                boolean addVariableAssignment;
 
-               public Builder addVariableAssignment(boolean b) {
+               private Builder addVariableAssignment(boolean b) {
                        System.err.println("cannot currently log variable 
assignments.");
                        addVariableAssignment = b;
                        return this;
                }
+
                boolean verbose;
 
+               /**
+                * Should LogTransformer be verbose in what it does? This 
currently list
+                * the names of the classes being processed.
+                * 
+                * @param b
+                * @return
+                */
                public Builder verbose(boolean b) {
                        verbose = b;
                        return this;
                }
+               
+               String[] ignore =  { "sun/", "java/", "javax/", "org/slf4j/",
+               "ch/qos/logback/" , "org/apache/log4j/"};
+               public Builder ignore(String[] strings) {
+                       this.ignore = strings;
+                       return this;
+               }
        }
 
-
        private LogTransformer(Builder builder) {
                this.addEntryExit = builder.addEntryExit;
                this.addVariableAssignment = builder.addVariableAssignment;
                this.verbose = builder.verbose;
+               this.ignore = builder.ignore;
        }
 
        private static final String _LOG = "_log";
-       String[] ignore = { "sun/", "java/", "javax/", "org/slf4j/",
-                       "ch/qos/logback/" };
 
        private boolean addEntryExit;
        private boolean addVariableAssignment;
        private boolean verbose;
+       private String[] ignore;
 
        public byte[] transform(ClassLoader loader, String className,
                        Class<?> clazz, ProtectionDomain domain, byte[] bytes) {
+               
 
-               return transform0(className, clazz, bytes);
+               try {
+                       return transform0(className, clazz, bytes);
+               } catch (Exception e) {
+                       // TODO Auto-generated catch block
+                       e.printStackTrace();
+                       return bytes;
+               }
        }
 
        /**
@@ -152,12 +199,14 @@
                if (addEntryExit) {
                        String messagePattern = "if ({}.isDebugEnabled()) 
{}.info(\">> {}\");";
                        Object[] arg1 = new Object[] { _LOG, _LOG, signature };
-                       String before = format(messagePattern, arg1);
+                       String before = 
MessageFormatter.arrayFormat(messagePattern, arg1);
+                       //System.out.println(before);
                        method.insertBefore(before);
 
                        String messagePattern2 = "if ({}.isDebugEnabled()) 
{}.info(\"<< {}{}\");";
                        Object[] arg2 = new Object[] { _LOG, _LOG, signature, 
returnValue };
-                       String after = format(messagePattern2, arg2);
+                       String after = 
MessageFormatter.arrayFormat(messagePattern2, arg2);
+                       //System.out.println(after);
                        method.insertAfter(after);
                }
        }
_______________________________________________
dev mailing list
dev@slf4j.org
http://www.slf4j.org/mailman/listinfo/dev

Reply via email to