我想编写一个实用程序,对一组调用进行(相对)非侵入式的请求和响应记录,我希望使用java-8 lambda / functional接口来完成它。
假设示例客户端调用代码是:
SomeReturn retVal = someObject.doSomething(arg1, arg2);
我希望编写一个可以调用的Recorder实用程序:
SomeReturn retVal = Recorder.withRecording(() -> someObject.doSomething(arg1, arg2))
记录器看起来像:
public static <R> R withRecording(Supplier<R> call) {
R response = call.get();
// Record the response
return response;
}
但是,我无法确定从Supplier
捕获请求参数(和请求对象)的方法(正确如此 - Supplier
并不关心它)。我认为即使java.util.function.Function
也不会帮助我们,因为他们不会自己处理国家。
不诉诸
之类的事情Object withRecording(Object target, Method method, Object[] arguments)
我们还有其他选择吗?我知道我们可以使用AOP作为解决方案,但想知道我们是否可以不使用它。
提前致谢!
答案 0 :(得分:4)
这仅适用于使用已知的有限功能签名集合进行操作,例如
public static <T,U,R> R withRecording(BiFunction<T,U,R> func, T arg1, U arg2) {
R response = func.apply(arg1, arg2);
// Record arg1, arg2 and the response
return response;
}
可用作
SomeReturn retVal = withRecording(someObject::doSomething, arg1, arg2);
这不仅暗示您必须为每个支持的签名创建一个重载,即不同数量的参数,您还必须为每个具有两个以上参数的函数创建适当的接口,因为没有预定义的接口这些案件。
此外,请注意,函数对象本身不会显示有关实际函数的任何内容,因此您要记录的是某些函数已使用特定参数和结果调用,但不是功能...
更好的解决方案是将doSomething
声明为接口方法,允许将someObject
替换为对另一个实现的引用,该实现委托给someObject
并记录所有调用。可以使用代理以一般方式实现此功能,但是, 与AOP解决方案重叠......