Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
org.test4j.mock.faking.fluent.MockMethod Maven / Gradle / Ivy
package org.test4j.mock.faking.fluent;
import org.test4j.mock.Invocation;
import org.test4j.mock.faking.meta.MethodId;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
/**
* 自定义mock行为
*
* @author darui.wu
*/
@SuppressWarnings({"rawtypes", "unused", "unchecked"})
public class MockMethod {
protected final FluentMockUp mockUp;
private final String realClass;
private final String name;
private final String desc;
private final AtomicInteger index = new AtomicInteger(0);
public MockMethod(FluentMockUp mockUp, String realClass, String name, String desc) {
this.mockUp = mockUp;
this.realClass = realClass;
this.name = name;
this.desc = desc;
}
/**
* 对方法参数校验
*
* .assertResult(inv -> {})
*
*
* @param asserts Invocation Consumer
* @return MockMethod
*/
public MockMethod assertParameters(Consumer asserts) {
String methodDesc = MethodId.buildMethodDesc(this.name, this.desc);
this.mockUp.addAssertMethodParas(methodDesc, asserts);
this.placeHolder();
return this;
}
/**
* 对真实调用结果进行断言
*
* .assertResult((inv,rst) -> {})
*
*
* @param asserts Invocation Consumer
* @return ignore
*/
public MockMethod assertResult(BiConsumer asserts) {
String methodDesc = MethodId.buildMethodDesc(this.name, this.desc);
this.mockUp.addAssertMethodResult(methodDesc, asserts);
this.placeHolder();
return this;
}
/**
* mock调用依次返回的结果值
*
* @param values return value list
* @return ignore
*/
public MockMethod thenReturn(R... values) {
if (values == null) {
values = (R[]) new Object[]{null};
}
for (Object value : values) {
int times = index.incrementAndGet();
this.mockUp.mockReturn(this.realClass, this.name, this.desc, times, value);
}
this.mockUp.apply();
return this;
}
/**
* 指定时序结果
*
* @param times 方法调用时序列表, 从1开始计数
* @param values return value list
* @return ignore
*/
public MockMethod thenReturn(int[] times, R... values) {
if (times == null) {
return this.thenReturn((R[]) nullPlusArray(values));
}
int max = 0;
if (values == null) {
values = (R[]) new Object[]{null};
}
for (int index = 0; index < times.length; index++) {
R value = this.getValue(values, index);
this.mockUp.mockReturn(this.realClass, this.name, this.desc, times[index], value);
max = Math.max(max, times[index]);
}
this.setIncreaseTimes(max);
this.mockUp.apply();
return this;
}
private Object[] nullPlusArray(Object[] array) {
Object[] objects = new Object[array == null ? 2 : array.length + 1];
objects[0] = null;
if (array == null) {
objects[1] = null;
} else {
System.arraycopy(array, 0, objects, 1, array.length);
}
return objects;
}
/**
* 除已指定的行为外, 剩下的调用都返回value
*
* @param value return value
*/
public void restReturn(R value) {
this.mockUp.mockReturn(this.realClass, this.name, this.desc, INDEX_REST_BEHAVIOR, value);
this.mockUp.apply();
}
/**
* mock调用依次抛出异常
*
* @param es throw exception
* @return ignore
*/
public MockMethod thenThrows(Throwable... es) {
if (es == null) {
es = new Throwable[]{null};
}
for (Throwable e : es) {
this.mockUp.mockThrows(this.realClass, this.name, this.desc, index.incrementAndGet(), e);
}
this.mockUp.apply();
return this;
}
public MockMethod thenThrows(int[] times, Throwable... es) {
if (times == null) {
return this.thenThrows((Throwable[]) nullPlusArray(es));
}
int max = 0;
if (es == null) {
es = new Throwable[]{null};
}
for (int index = 0; index < times.length; index++) {
Throwable e = this.getValue(es, index);
this.mockUp.mockThrows(this.realClass, this.name, this.desc, times[index], e);
max = Math.max(max, times[index]);
}
this.setIncreaseTimes(max);
this.mockUp.apply();
return this;
}
/**
* 除已指定的行为外, 剩下的调用都抛出异常
*
* @param e throw exception
*/
public void restThrows(Throwable e) {
this.mockUp.mockThrows(this.realClass, this.name, this.desc, INDEX_REST_BEHAVIOR, e);
this.mockUp.apply();
}
/**
* 按序执行模拟逻辑
*
* @param fake fake function
* @return ignore
*/
public MockMethod thenAnswer(FakeFunction fake) {
if (fake == null) {
throw new RuntimeException("The parameter[fake] of restAnswer method can't be null.");
}
this.mockUp.mockMethod(this.realClass, this.name, this.desc, index.incrementAndGet(), fake);
this.mockUp.apply();
return this;
}
/**
* mock调用依次执行的逻辑
*
* @param timeSeq 从1开始计数
* @param fake fake function
* @return ignore
*/
public MockMethod thenAnswer(int timeSeq, FakeFunction fake) {
if (fake == null) {
throw new RuntimeException("The parameter[fake] of restAnswer method can't be null.");
}
return this.thenAnswer(new int[]{timeSeq}, fake);
}
/**
* mock调用依次执行的逻辑
*
* @param times 指定时序, 从1开始计数
* @param fake fake function
* @return ignore
*/
public MockMethod thenAnswer(int[] times, FakeFunction fake) {
if (fake == null) {
throw new RuntimeException("The parameter[fake] of restAnswer method can't be null.");
}
int max = 0;
for (int time : times) {
this.mockUp.mockMethod(this.realClass, this.name, this.desc, time, fake);
max = Math.max(max, time);
}
this.setIncreaseTimes(max);
this.mockUp.apply();
return this;
}
/**
* 除已指定的行为外, 剩下的调用执行的逻辑
*
* @param fake fake function
*/
public void restAnswer(FakeFunction fake) {
if (fake == null) {
throw new RuntimeException("The parameter[fake] of restAnswer method can't be null.");
}
this.mockUp.mockMethod(this.realClass, this.name, this.desc, INDEX_REST_BEHAVIOR, fake);
this.mockUp.apply();
}
/**
* 默认行为序号
*/
public final static int INDEX_REST_BEHAVIOR = 0;
private A getValue(A[] values, int index) {
if (values == null) {
return null;
}
int size = values.length;
if (size == 0) {
return null;
} else {
return index < size ? values[index] : values[size - 1];
}
}
/**
* 按指定时序设置过, 把自增序列设置到最大值
*/
private void setIncreaseTimes(int max) {
if (this.index.get() < max) {
this.index.set(max);
}
}
/**
* 占位处理, 保证在没有设置模拟行为, 只设置了{@link #assertParameters(Consumer)} 和 {@link #assertResult(BiConsumer)}
* 时, {@link org.test4j.mock.faking.meta.FakeStates#getLastMethod(MethodId)}可以找到断言
*/
private void placeHolder() {
this.mockUp.mockReturn(this.realClass, this.name, this.desc, -1, null);
this.mockUp.apply();
}
/**
* 清空行为时, 定义序号归零
*/
public void resetIndex() {
this.index.set(0);
}
}