/*
This file is part of Fantom.
Fantom is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
Fantom is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with Fantom. If not, see <http://www.gnu.org/licenses/>.
*/
package cz.matfyz.aai.fantom.message;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import cz.matfyz.aai.fantom.game.Graph;
import cz.matfyz.aai.fantom.server.Client;
import cz.matfyz.aai.fantom.server.ProtocolException;
/**
* Base class for all messages going between the client and the server.
*/
public abstract class Message {
/**
* Returns the name of the type of the message.
* @return the name of the type of the message.
*/
public abstract String getMessageType();
/**
* Serializes the message to a list of properties.
* @return list of properties that encodes the message.
*/
public abstract Properties[] serialize();
/**
* The name of the property that contains the type of the message.
*/
public static final String PROPERTY_MESSAGE_TYPE = "message";
/**
* The name of the 'ready' message.
*/
public static final String PROPERTY_MESSAGE_TYPE_READY = "ready";
/**
* The name of the 'start' message.
*/
public static final String PROPERTY_MESSAGE_TYPE_START = "start";
/**
* The name of the 'move' message.
*/
public static final String PROPERTY_MESSAGE_TYPE_MOVE = "move";
/**
* The name of the 'update' message.
*/
public static final String PROPERTY_MESSAGE_TYPE_UPDATE = "update";
/**
* The name of the 'quit' message.
*/
public static final String PROPERTY_MESSAGE_TYPE_QUIT = "quit";
/**
* List of message loaders, indexed by the type of the message.
*/
protected static Map<String, MessageLoader> messageLoaders;
/**
* Reads the message from a list of properties.
*
* @param messageData the data of the message.
* @param client the client that send/gets the message.
* @param
*/
public static Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
// Find the (first) line that contains the message type
String messageType = null;
for(int i = 0; i < messageData.length; i++) {
if(messageData[i].containsKey(PROPERTY_MESSAGE_TYPE)) {
messageType = messageData[i].getProperty(PROPERTY_MESSAGE_TYPE);
break;
}
}
if(messageType == null)
throw new ProtocolException("Message type was not specified", client);
MessageLoader loader = messageLoaders.get(messageType);
if(loader == null)
throw new ProtocolException("Unknown message type: '" + messageType + "'", client);
return loader.loadMessage(messageData, client, graph);
}
static {
// Initialize the list of message loaders
messageLoaders = new HashMap<String, MessageLoader>();
messageLoaders.put(PROPERTY_MESSAGE_TYPE_MOVE, new MessageLoader() {
@Override
public Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
return new MessageMove(graph, messageData);
}
});
messageLoaders.put(PROPERTY_MESSAGE_TYPE_QUIT, new MessageLoader() {
@Override
public Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
return new MessageQuit();
}
});
messageLoaders.put(PROPERTY_MESSAGE_TYPE_READY, new MessageLoader() {
@Override
public Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
return new MessageReady(messageData);
}
});
messageLoaders.put(PROPERTY_MESSAGE_TYPE_START, new MessageLoader() {
@Override
public Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
return new MessageStart(messageData);
}
});
messageLoaders.put(PROPERTY_MESSAGE_TYPE_UPDATE, new MessageLoader() {
@Override
public Message loadMessage(Properties[] messageData, Client client, Graph graph) throws ProtocolException {
return new MessageUpdate(graph, messageData);
}
});
}
}