/*
*
* * Copyright 2010, Unitils.org
* *
* * Licensed under the Apache License, Version 2.0 (the "License");
* * you may not use this file except in compliance with the License.
* * You may obtain a copy of the License at
* *
* * http://www.apache.org/licenses/LICENSE-2.0
* *
* * Unless required by applicable law or agreed to in writing, software
* * distributed under the License is distributed on an "AS IS" BASIS,
* * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* * See the License for the specific language governing permissions and
* * limitations under the License.
*
*/
package org.unitils.mock.core.proxy;
import java.lang.reflect.Method;
import java.util.List;
import static org.unitils.mock.core.proxy.CloneUtil.createDeepClone;
/**
* An invocation of a proxy method.
*
* @author Filip Neven
* @author Tim Ducheyne
* @author Kenny Claes
*/
public class ProxyInvocation {
/* The name of the mock, e.g. the field name */
private String mockName;
/* The proxy on which the method was called */
private Object proxy;
/* The method that was called */
private Method method;
/* The arguments that were used */
private List<Object> arguments;
/* The arguments at the time that they were used */
private List<Object> argumentsAtInvocationTime;
/* The trace of the invocation */
private StackTraceElement[] invokedAtTrace;
/**
* Creates an invocation.
*
* @param mockName The name of the mock, e.g. the field name, not null
* @param proxy The proxy on which the method was called, not null
* @param method The method that was called, not null
* @param arguments The arguments that were used, not null
* @param invokedAtTrace The trace of the invocation, not null
*/
public ProxyInvocation(String mockName, Object proxy, Method method, List<Object> arguments, StackTraceElement[] invokedAtTrace) {
this.mockName = mockName;
this.proxy = proxy;
this.method = method;
this.arguments = arguments;
this.argumentsAtInvocationTime = arguments;
this.invokedAtTrace = invokedAtTrace;
}
/**
* Creates a copy of the given proxy invocation.
*
* The argumentsAtInvocationTime will be set as copies (deep clones) of the arguments at the time of
* the invocation. This way the original values can still be used later-on even when changes
* occur to the original values (pass-by-value vs pass-by-reference). If not explicitly set, this will return the
* same values as the arguments.
*
* @param proxyInvocation The proxy invocation to copy, not null
*/
public ProxyInvocation(ProxyInvocation proxyInvocation) {
this.mockName = proxyInvocation.getMockName();
this.proxy = proxyInvocation.getProxy();
this.method = proxyInvocation.getMethod();
this.arguments = proxyInvocation.getArguments();
this.argumentsAtInvocationTime = createDeepClone(arguments);
this.invokedAtTrace = proxyInvocation.getInvokedAtTrace();
}
/**
* Calls the actual method that was proxied using the same arguments.
*
* @return The result value
*/
public Object invokeOriginalBehavior() throws Throwable {
throw new UnsupportedOperationException("Invoking of original behavior not implemented.");
}
/**
* @return The nr of arguments at invocation time that were not null
*/
public int getNrOfNotNullArguments() {
if (argumentsAtInvocationTime == null) {
return 0;
}
int count = 0;
for (Object argument : argumentsAtInvocationTime) {
if (argument != null) {
count++;
}
}
return count;
}
/**
* @return The name of the mock, e.g. the field name, not null
*/
public String getMockName() {
return mockName;
}
/**
* @return The proxy on which the method was called, not null
*/
public Object getProxy() {
return proxy;
}
/**
* @return The method that was called, not null
*/
public Method getMethod() {
return method;
}
/**
* @return The arguments that were used, not null
*/
public List<Object> getArguments() {
return arguments;
}
/**
* The arguments at the time that they were used.
*
* The argumentsAtInvocationTime can be set as copies (deep clones) of the arguments at the time of
* the invocation. This way the original values can still be used later-on even when changes
* occur to the original values (pass-by-value vs pass-by-reference). If not explicitly set, this will return the
* same values as the arguments.
*
* @return The arguments, not null
*/
public List<Object> getArgumentsAtInvocationTime() {
return argumentsAtInvocationTime;
}
/**
* @return The trace of the invocation, not null
*/
public StackTraceElement[] getInvokedAtTrace() {
return invokedAtTrace;
}
/**
* @return The location of the invocation, not null
*/
public StackTraceElement getInvokedAt() {
return invokedAtTrace[0];
}
/**
* @return The line nr of the invocation
*/
public int getLineNumber() {
return getInvokedAt().getLineNumber();
}
}