001package org.javasimon.spring; 002 003import java.io.Serializable; 004 005import org.aopalliance.intercept.MethodInterceptor; 006import org.aopalliance.intercept.MethodInvocation; 007import org.javasimon.Manager; 008import org.javasimon.SimonManager; 009import org.javasimon.Split; 010import org.javasimon.source.StopwatchSource; 011 012/** 013 * Basic method interceptor that measures the duration of the intercepted call with a Stopwatch. 014 * Class can be overridden in case more sophisticated measuring needs to be provided - this all should 015 * happen in {@link #processInvoke(org.aopalliance.intercept.MethodInvocation, org.javasimon.Split)} method. 016 * 017 * @author Erik van Oosten 018 */ 019public class BasicMonitoringInterceptor implements MethodInterceptor, Serializable { 020 private final StopwatchSource<MethodInvocation> stopwatchSource; 021 022 /** 023 * Constructor with specified {@link org.javasimon.source.MonitorSource}. 024 * 025 * @param stopwatchSource stopwatch provider for method invocation 026 */ 027 public BasicMonitoringInterceptor(StopwatchSource<MethodInvocation> stopwatchSource) { 028 this.stopwatchSource = stopwatchSource; 029 } 030 031 /** Constructor with specified {@link org.javasimon.Manager}. */ 032 public BasicMonitoringInterceptor(Manager manager) { 033 this(new SpringStopwatchSource(manager)); 034 } 035 036 /** Default constructor using {@link org.javasimon.SimonManager#manager}. */ 037 public BasicMonitoringInterceptor() { 038 this(new SpringStopwatchSource(SimonManager.manager())); 039 } 040 041 /** 042 * Performs method invocation and wraps it with Stopwatch. 043 * 044 * @param invocation method invocation 045 * @return return object from the method 046 * @throws Throwable anything thrown by the method 047 */ 048 public final Object invoke(MethodInvocation invocation) throws Throwable { 049 final Split split = stopwatchSource.start(invocation); 050 try { 051 return processInvoke(invocation, split); 052 } finally { 053 split.stop(); 054 } 055 } 056 057 /** 058 * Method with default invoke (just calls proceed). It can be overridden and overriding method can stop 059 * the provided split. If split is not stopped it will be stopped right after this method finishes. 060 * Any caught throwable should be rethrown again. Method should call {@code invocation.proceed()}. 061 * 062 * @param invocation method invocation 063 * @param split running split for this monitored action 064 * @return return object from the method 065 */ 066 protected Object processInvoke(MethodInvocation invocation, @SuppressWarnings("UnusedParameters") Split split) throws Throwable { 067 return invocation.proceed(); 068 } 069}