org.bushe.swing.event.annotation.ProxyTopicSubscriber Maven / Gradle / Ivy
package org.bushe.swing.event.annotation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import org.bushe.swing.event.EventService;
import org.bushe.swing.event.VetoTopicEventListener;
/** A class that subscribes to an EventService on behalf of another object.
* This class is not used directly (though you could), but rather through the use of the
* {@link @org.bushe.swing.event.annotation.EventTopicSubscriber}. Advanced EventBus
* users could use this class in Aspect-Oriented code. Consider using the
* {@link AnnotationProcessor} instead, it may suit your needs and be easier.*/
public class ProxyTopicSubscriber extends AbstractProxySubscriber
implements org.bushe.swing.event.EventTopicSubscriber, VetoTopicEventListener {
private String topic;
/**
* Creates a proxy. This does not subscribe it.
*
* @param proxiedSubscriber the subscriber that the proxy will call when an event is published
* @param subscriptionMethod the method the proxy will call, must have an Object as it's first and only parameter
* @param referenceStrength if the subscription is weak, the reference from the proxy to the real subscriber should
* be too
* @param es the EventService we will be subscribed to, since we may need to unsubscribe when weak refs no longer
* exist
* @param topic the topic to subscribe to, used for unsubscription only
* @param veto if this proxy is for a veto subscriber
*/
public ProxyTopicSubscriber(Object proxiedSubscriber, Method subscriptionMethod, ReferenceStrength referenceStrength,
EventService es, String topic, boolean veto) {
this(proxiedSubscriber, subscriptionMethod, referenceStrength, 0, es, topic, veto);
}
/**
* Creates a proxy. This does not subscribe it.
*
* @param proxiedSubscriber the subscriber that the proxy will call when an event is published
* @param subscriptionMethod the method the proxy will call, must have an Object as it's first and only parameter
* @param referenceStrength if the subscription is weak, the reference from the proxy to the real subscriber should
* be too
* @param es the EventService we will be subscribed to, since we may need to unsubscribe when weak refs no longer
* exist
* @param topic the topic to subscribe to, used for unsubscription only
* @param veto if this proxy is for a veto subscriber
*/
public ProxyTopicSubscriber(Object proxiedSubscriber, Method subscriptionMethod, ReferenceStrength referenceStrength,
int priority, EventService es, String topic, boolean veto) {
super(proxiedSubscriber, subscriptionMethod, referenceStrength, priority, es, veto);
this.topic = topic;
if (topic == null) {
throw new IllegalArgumentException("Proxies for topic subscribers require a non-null topic.");
}
Class[] params = subscriptionMethod.getParameterTypes();
if (params == null || params.length != 2 || !String.class.equals(params[0]) || params[1].isPrimitive()) {
throw new IllegalArgumentException("The subscriptionMethod must have the two parameters, the first one must be a String and the second a non-primitive (Object or derivative).");
}
}
/**
* Handles the event publication by pushing it to the real subscriber's subscription Method.
*
* @param topic the topic on which the object is being published
* @param data The Object that is being published on the topic.
*/
public void onEvent(String topic, Object data) {
Object[] args = new Object[]{topic, data};
Object obj = null;
Method subscriptionMethod = null;
try {
obj = getProxiedSubscriber();
if (obj == null) {
return;
}
subscriptionMethod = getSubscriptionMethod();
subscriptionMethod.invoke(obj, args);
} catch (IllegalAccessException e) {
String message = "IllegalAccessException when invoking annotated method from EventService publication. Topic:" + topic + ", data:" + data + ", subscriber:" + getProxiedSubscriber() + ", subscription Method=" + getSubscriptionMethod();
retryReflectiveCallUsingAccessibleObject(args, subscriptionMethod, obj, e, message);
} catch (InvocationTargetException e) {
throw new RuntimeException("InvocationTargetException when invoking annotated method from EventService publication. Topic:" + topic + ", data:" + data + ", subscriber:" + getProxiedSubscriber() + ", subscription Method=" + getSubscriptionMethod(), e);
}
}
public boolean shouldVeto(String topic, Object data) {
Object[] args = new Object[]{topic, data};
Object obj = null;
Method subscriptionMethod = null;
try {
obj = getProxiedSubscriber();
if (obj == null) {
return false;
}
subscriptionMethod = getSubscriptionMethod();
return Boolean.valueOf(subscriptionMethod.invoke(obj, args)+"");
} catch (IllegalAccessException e) {
String message = "IllegalAccessException when invoking annotated veto method from EventService publication. Topic:" + topic + ", data:" + data + ", subscriber:" + getProxiedSubscriber() + ", subscription Method=" + getSubscriptionMethod();
return retryReflectiveCallUsingAccessibleObject(args, subscriptionMethod, obj, e, message);
} catch (InvocationTargetException e) {
throw new RuntimeException("InvocationTargetException when invoking annotated veto method from EventService publication. Topic:" + topic + ", data:" + data + ", subscriber:" + getProxiedSubscriber() + ", subscription Method=" + getSubscriptionMethod(), e);
}
}
protected void unsubscribe(String topic) {
if (veto) {
getEventService().unsubscribeVetoListener(topic, this);
} else {
getEventService().unsubscribe(topic, this);
}
}
@Override
public boolean equals(Object obj) {
if (obj instanceof ProxyTopicSubscriber) {
if (!super.equals(obj)) {
return false;
}
ProxyTopicSubscriber proxyTopicSubscriber = (ProxyTopicSubscriber) obj;
if (topic.equals(proxyTopicSubscriber.topic)) {
if (topic == null) {
return false;
} else {
if (!topic.equals(proxyTopicSubscriber.topic)) {
return false;
}
}
}
return true;
} else {
return false;
}
}
@Override
public String toString() {
return "ProxyTopicSubscriber{" +
"topic='" + topic + '\'' +
"veto='" + veto + '\'' +
"realSubscriber=" + getProxiedSubscriber() +
", subscriptionMethod=" + getSubscriptionMethod() +
", referenceStrength=" + getReferenceStrength() +
", eventService=" + getEventService() +
'}';
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy