1 package com.atlassian.performance;
2
3 import org.aopalliance.intercept.MethodInterceptor;
4 import org.aopalliance.intercept.MethodInvocation;
5 import org.slf4j.Logger;
6 import org.slf4j.LoggerFactory;
7 import org.slf4j.MarkerFactory;
8 import org.slf4j.Marker;
9
10 import java.lang.reflect.Method;
11 import java.util.Iterator;
12
13 public class TimeMethodInterceptor implements MethodInterceptor
14 {
15 private static final String PERF_MARKER_TOKEN = "com.atlassian.performance.TestMarker";
16
17 Logger log = LoggerFactory.getLogger("com.atlassian.performance.");
18
19 public Object invoke(MethodInvocation invocation) throws Throwable {
20 TimedMethodInvocation tmi = new TimedMethodInvocation(invocation);
21 EventTime et = EventTime.timeEvent(eventKey(invocation), false, tmi);
22
23 if(et.getTime() > 1) {
24 log.debug(MarkerFactory.getMarker(PERF_MARKER_TOKEN),
25 "{}, {}", new Object[]{argsToString(invocation.getArguments()), et.getTime()});
26 }
27
28 if(tmi.throwable == null) {
29 return tmi.val;
30 } else {
31 throw tmi.throwable;
32 }
33 }
34
35 private static String eventKey(MethodInvocation invocation)
36 {
37 return trimMethod(invocation.getMethod()) + " " + argsToString(invocation.getArguments());
38 }
39
40 private static String trimMethod(Method method) {
41 String rawMethStr = method.toString();
42 int methodStart = rawMethStr.lastIndexOf(" ");
43 if(methodStart > -1)
44 {
45 return rawMethStr.substring(methodStart);
46 } else {
47 return rawMethStr;
48 }
49 }
50
51 private static String argsToString(Object[] args)
52 {
53 StringBuffer buf = new StringBuffer();
54 for(Object arg : args)
55 {
56 buf.append(arg);
57 buf.append("*");
58 }
59 return buf.toString();
60 }
61
62
63 public class TimedMethodInvocation implements EventTime.TimedEvent
64 {
65 Object val;
66 Throwable throwable;
67 MethodInvocation invocation;
68
69 TimedMethodInvocation(MethodInvocation invocation)
70 {
71 this.invocation = invocation;
72 }
73
74 public boolean run()
75 {
76 try
77 {
78 val = invocation.proceed();
79 }
80 catch (Throwable t)
81 {
82 throwable = t;
83 }
84 finally
85 {
86 return true;
87 }
88 }
89
90 }
91
92 }