/*
* Copyright (c) 2012-2015 The original author or authors
* ------------------------------------------------------
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* and Apache License v2.0 which accompanies this distribution.
*
* The Eclipse Public License is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* The Apache License v2.0 is available at
* http://www.opensource.org/licenses/apache2.0.php
*
* You may elect to redistribute this code under either of these licenses.
*/
package org.eclipse.moquette.spi.impl;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
import org.eclipse.moquette.proto.messages.AbstractMessage;
/**
* Annotation @MQTTMessage helper class.
*
* It has the responsibility to identify the @MQTTMessage method of a given instance or class and define an easy access to invoke them.
*
* @author andrea
*/
class AnnotationSupport {
private final Map<Class, Method> messageClassToMethod = new HashMap<Class, Method>();
private Object targetInstance;
void processAnnotations(Object instance) {
targetInstance = instance;
Class instanceCls = instance.getClass();
Method[] allMethods = instanceCls.getDeclaredMethods();
for (Method m : allMethods) {
MQTTMessage annotation = m.getAnnotation(MQTTMessage.class);
if (annotation == null) {
continue;
}
Class mqttMessageClass = annotation.message();
messageClassToMethod.put(mqttMessageClass, m);
}
}
/**
* Dispatch a call to the wrapped target invoking the method that match the msg class.
*
* @throws RuntimeException
* if the message can't be routed to any annotated method, or if there are any errors during invocation.
*/
void dispatch(org.red5.server.mqtt.ServerChannel session, AbstractMessage msg) {
Method targetMethod = this.messageClassToMethod.get(msg.getClass());
if (targetMethod == null) {
throw new RuntimeException("Can't dispatch to any @MQTTMessage marked the message: " + msg);
}
try {
targetMethod.invoke(targetInstance, session, msg);
} catch (Exception ex) {
throw new RuntimeException(ex);
}
}
}