, 나는 다음과 같은 코드로 왔어요 :
제안으로
public class FakeEventBinderProvider implements FakeProvider<EventBinder<?>> {
@Override
public EventBinder<?> getFake(Class<?> type) {
return (EventBinder<?>) Proxy.newProxyInstance(FakeEventBinderProvider.class.getClassLoader(), new Class<?>[] { type }, new InvocationHandler() {
@Override
public Object invoke(Object proxy, Method method, final Object[] args) throws Throwable {
String methodName = method.getName();
assert methodName.equals("bindEventHandlers");
final List<HandlerRegistration> registrations = new LinkedList<HandlerRegistration>();
EventBus eventBus = (EventBus) args[1];
List<Method> presenterMethods = getAllMethods(args[0].getClass());
for (final Method presenterMethod : presenterMethods) {
if (presenterMethod.isAnnotationPresent(EventHandler.class)) {
@SuppressWarnings("unchecked") // Should always be ok, since the Generator for EventBinder should do all the safe-checking
Class<? extends GenericEvent> eventType = (Class<? extends GenericEvent>) (presenterMethod.getParameterTypes())[0];
registrations.add(eventBus.addHandler(GenericEventType.getTypeOf(eventType), new GenericEventHandler() {
@Override
public void handleEvent(GenericEvent event) {
try {
presenterMethod.setAccessible(true);
presenterMethod.invoke(args[0], event);
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
throw new RuntimeException(e);
}
}
}));
}
}
return new HandlerRegistration() {
@Override
public void removeHandler() {
for (HandlerRegistration registration : registrations) {
registration.removeHandler();
}
registrations.clear();
}
};
}
});
}
private List<Method> getAllMethods(Class<?> type) {
List<Method> methods = new LinkedList<Method>();
methods.addAll(Arrays.asList(type.getDeclaredMethods()));
if (type.getSuperclass() != null) {
methods.addAll(getAllMethods(type.getSuperclass()));
}
return methods;
}
}
,이를 기반으로 한 FakeUiBinderProvider
의 구현에. 당신은 자바 반사 cruft에 제거하면 그것은 매우 간단합니다 :
- 가
@EventHandler
주석 모든 방법을 찾습니다.
- 지정된 이벤트 유형에 대한 콜백 메소드를 호출하는 새 처리기를 등록하십시오.
removeHandler
을 호출하면 이전 지점에서 추가 된 모든 처리기가 제거됩니다 (이 동작은 gwteventbinder의 실제 구현에서 복사 됨).
당신의 @Before
방법, 예를 들어,이 공급자를 등록하는 것을 잊지 마십시오 :
@Before
public void setUpEventBindery() {
GwtMockito.useProviderForType(EventBinder.class, new FakeEventBinderProvider());
}
을 당신은 이후 GwtMockito.useProviderForType
에 대한 설명서로, 기본 인터페이스, EventBinder
위해이 작업을 수행 할 필요가 말한다 :
(..) 주어진 공급자는 주어진 유형의 인스턴스를 GWT.create하는 데 사용해야하며 하위 클래스을 생성해야합니다.