package de.dwerth.gntpserver.gntp;
import java.util.StringTokenizer;
import de.dwerth.gntpserver.gntp.messages.GNTPMessage;
import de.dwerth.gntpserver.gntp.messages.NotifyMessage;
import de.dwerth.gntpserver.gntp.messages.RegisterMessage;
import de.dwerth.gntpserver.gntp.messages.SubscribeMessage;
public class MessageFactory {
public static GNTPMessage parseRawData(byte[] rawData) {
GNTPMessage retVal = null;
String firstLine = "";
int startPos = 0;
for (startPos = 0; startPos < rawData.length - 1; startPos++) {
// Search for CRLF
if (rawData[startPos] == 13 && rawData[startPos + 1] == 10) {
firstLine = new String(rawData, 0, startPos + 1);
break;
}
}
// Check what Messagetype we got here
StringTokenizer st = new StringTokenizer(firstLine, " ");
st.nextToken(); // GNTP/<version>
String messageType = st.nextToken(); // <messagetype>
if (messageType.equals(GNTPMessage.NOTIFY)) {
retVal = new NotifyMessage();
} else if (messageType.equals(GNTPMessage.REGISTER)) {
retVal = new RegisterMessage();
} else if (messageType.equals(GNTPMessage.SUBSCRIBE)) {
retVal = new SubscribeMessage();
} else {
throw new RuntimeException("Unknown Message Type: " + messageType);
}
String encryptionAlgorithmID = null;
String keyHashAlgorithmID = null;
if (st.hasMoreTokens()) {
encryptionAlgorithmID = st.nextToken().trim();
}
if (st.hasMoreTokens()) {
keyHashAlgorithmID = st.nextToken().trim();
}
if (encryptionAlgorithmID != null && !"NONE".equals(encryptionAlgorithmID)) {
throw new RuntimeException("Encryption not supported yet: " + encryptionAlgorithmID);
}
retVal.setEncryptionAlgorithmID(encryptionAlgorithmID);
retVal.setKeyHashAlgorithmID(keyHashAlgorithmID);
String aLine = null;
for (int i = startPos; i < rawData.length - 1; i++) {
// Search for CRLF
if (rawData[i] == 13 && rawData[i + 1] == 10) {
aLine = new String(rawData, startPos, i - startPos);
startPos = i + 2;
try {
if (!aLine.toLowerCase().startsWith("length:")) {
parseLine(aLine, retVal);
} else {
i = parseRaw(rawData, aLine, retVal, startPos);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
return retVal;
}
protected static int parseRaw(byte[] rawData, String aLine, GNTPMessage msg, int i) {
StringTokenizer st = new StringTokenizer(aLine, ":");
@SuppressWarnings("unused")
String key = st.nextToken();
String value = st.nextToken().trim();
int length = Integer.valueOf(value);
byte[] rawBytes = new byte[length];
System.arraycopy(rawData, i + 1, rawBytes, 0, length);
msg.setBinaryData(rawBytes);
return i + 2 + rawData.length;
}
protected static void parseLine(String aLine, GNTPMessage msg) {
if (aLine.length() == 0) {
return;
}
StringTokenizer st = new StringTokenizer(aLine, ":");
String key = st.nextToken();
String value = null;
if (st.hasMoreTokens()) {
value = st.nextToken().trim();
}
if (value != null) {
if (key.equalsIgnoreCase("Origin-Machine-Name")) {
msg.setOriginMachineName(value);
} else if (key.equalsIgnoreCase("Origin-Machine-Name")) {
msg.setOriginMachineName(value);
} else if (key.equalsIgnoreCase("Origin-Software-Name")) {
msg.setOriginSoftwareName(value);
} else if (key.equalsIgnoreCase("Origin-Software-Version")) {
msg.setOriginSoftwareVersion(value);
} else if (key.equalsIgnoreCase("Origin-Platform-Name")) {
msg.setOriginPlatformName(value);
} else if (key.equalsIgnoreCase("Origin-Platform-Version")) {
msg.setOriginPlatformVersion(value);
}
if (msg instanceof RegisterMessage) {
if (key.equalsIgnoreCase("Application-Name")) {
((RegisterMessage) msg).setApplicationName(value);
} else if (key.equalsIgnoreCase("Application-Icon")) {
((RegisterMessage) msg).setApplicationIcon(value);
} else if (key.equalsIgnoreCase("Notifications-Count")) {
((RegisterMessage) msg).setNotificationsCount(Integer.valueOf(value));
} else if (key.equalsIgnoreCase("Notification-Name")) {
((RegisterMessage) msg).setNotificationName(value);
} else if (key.equalsIgnoreCase("Notification-Display-Name")) {
((RegisterMessage) msg).setNotificationDisplayName(value);
} else if (key.equalsIgnoreCase("Notification-Enabled")) {
((RegisterMessage) msg).setNotificationEnabled(value);
} else if (key.equalsIgnoreCase("Notification-Icon")) {
((RegisterMessage) msg).setNotificationIcon(value);
}
} else if (msg instanceof SubscribeMessage) {
if (key.equalsIgnoreCase("Subscriber-ID")) {
((SubscribeMessage) msg).setSubscriberID(value);
} else if (key.equalsIgnoreCase("Subscriber-Name")) {
((SubscribeMessage) msg).setSubscriberName(value);
} else if (key.equalsIgnoreCase("Subscriber-Port")) {
((SubscribeMessage) msg).setSubscriberPort(Integer.valueOf(value));
}
} else if (msg instanceof NotifyMessage) {
if (key.equalsIgnoreCase("Application-Name")) {
((NotifyMessage) msg).setApplicationName(value);
} else if (key.equalsIgnoreCase("Notification-Name")) {
((NotifyMessage) msg).setNotificationName(value);
} else if (key.equalsIgnoreCase("Notification-ID")) {
((NotifyMessage) msg).setNotificationID(value);
} else if (key.equalsIgnoreCase("Notification-Title")) {
((NotifyMessage) msg).setNotificationTitle(value);
} else if (key.equalsIgnoreCase("Notification-Text")) {
((NotifyMessage) msg).setNotificationText(value);
} else if (key.equalsIgnoreCase("Notification-Sticky")) {
((NotifyMessage) msg).setNotificationSticky(Boolean.valueOf(value.toLowerCase()));
} else if (key.equalsIgnoreCase("Notification-Priority")) {
((NotifyMessage) msg).setNotificationPriority(Integer.valueOf(value));
} else if (key.equalsIgnoreCase("Notification-Icon")) {
((NotifyMessage) msg).setNotificationIcon(value);
} else if (key.equalsIgnoreCase("Notification-Coalescing-ID")) {
((NotifyMessage) msg).setNotificationCoalescingID(value);
} else if (key.equalsIgnoreCase("Notification-Callback-Context")) {
((NotifyMessage) msg).setNotificationCallbackContext(value);
} else if (key.equalsIgnoreCase("Notification-Callback-Context-Type")) {
((NotifyMessage) msg).setNotificationCallbackContextType(value);
} else if (key.equalsIgnoreCase("Notification-Callback-Target")) {
((NotifyMessage) msg).setNotificationCallbackTarget(value);
}
}
} else {
System.out.println("ignoring key: " + key);
}
}
}