diff --git a/droidstomplib/.gitignore b/droidstomplib/.gitignore new file mode 100644 index 0000000..796b96d --- /dev/null +++ b/droidstomplib/.gitignore @@ -0,0 +1 @@ +/build diff --git a/droidstomplib/build.gradle b/droidstomplib/build.gradle new file mode 100644 index 0000000..4ea1842 --- /dev/null +++ b/droidstomplib/build.gradle @@ -0,0 +1,35 @@ +apply plugin: 'com.android.library' + +android { + compileSdkVersion 28 + + + + defaultConfig { + minSdkVersion 16 + targetSdkVersion 28 + versionCode 1 + versionName "1.0" + + testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" + + } + + buildTypes { + release { + minifyEnabled false + proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' + } + } + +} + +dependencies { + implementation fileTree(dir: 'libs', include: ['*.jar']) + + implementation 'com.android.support:appcompat-v7:28.0.0' + implementation 'com.squareup.okhttp3:okhttp:3.12.0' + testImplementation 'junit:junit:4.12' + androidTestImplementation 'com.android.support.test:runner:1.0.2' + androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2' +} diff --git a/droidstomplib/proguard-rules.pro b/droidstomplib/proguard-rules.pro new file mode 100644 index 0000000..f1b4245 --- /dev/null +++ b/droidstomplib/proguard-rules.pro @@ -0,0 +1,21 @@ +# Add project specific ProGuard rules here. +# You can control the set of applied configuration files using the +# proguardFiles setting in build.gradle. +# +# For more details, see +# http://developer.android.com/guide/developing/tools/proguard.html + +# If your project uses WebView with JS, uncomment the following +# and specify the fully qualified class name to the JavaScript interface +# class: +#-keepclassmembers class fqcn.of.javascript.interface.for.webview { +# public *; +#} + +# Uncomment this to preserve the line number information for +# debugging stack traces. +#-keepattributes SourceFile,LineNumberTable + +# If you keep the line number information, uncomment this to +# hide the original source file name. +#-renamesourcefileattribute SourceFile diff --git a/droidstomplib/src/androidTest/java/com/github/dadekuma/droidstomplib/ExampleInstrumentedTest.java b/droidstomplib/src/androidTest/java/com/github/dadekuma/droidstomplib/ExampleInstrumentedTest.java new file mode 100644 index 0000000..aeafdc8 --- /dev/null +++ b/droidstomplib/src/androidTest/java/com/github/dadekuma/droidstomplib/ExampleInstrumentedTest.java @@ -0,0 +1,26 @@ +package com.github.dadekuma.droidstomplib; + +import android.content.Context; +import android.support.test.InstrumentationRegistry; +import android.support.test.runner.AndroidJUnit4; + +import org.junit.Test; +import org.junit.runner.RunWith; + +import static org.junit.Assert.*; + +/** + * Instrumented test, which will execute on an Android device. + * + * @see Testing documentation + */ +@RunWith(AndroidJUnit4.class) +public class ExampleInstrumentedTest { + @Test + public void useAppContext() { + // Context of the app under test. + Context appContext = InstrumentationRegistry.getTargetContext(); + + assertEquals("com.github.dadekuma.droidstomplib.test", appContext.getPackageName()); + } +} diff --git a/droidstomplib/src/main/AndroidManifest.xml b/droidstomplib/src/main/AndroidManifest.xml new file mode 100644 index 0000000..f3ea17c --- /dev/null +++ b/droidstomplib/src/main/AndroidManifest.xml @@ -0,0 +1,2 @@ + diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IConnectionProvider.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IConnectionProvider.java new file mode 100644 index 0000000..fe63f7c --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IConnectionProvider.java @@ -0,0 +1,13 @@ +package com.github.dadekuma.droidstomplib.connection; + +import com.github.dadekuma.droidstomplib.payload.HttpHeader; + +import java.util.Collection; + +public interface IConnectionProvider { + void connect(String stompEndpoint, Collection headers); + void send(String payload); + void setStompCallback(IStompCallback stompCallback); + boolean isConnected(); + boolean isConnecting(); +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompCallback.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompCallback.java new file mode 100644 index 0000000..1082634 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompCallback.java @@ -0,0 +1,10 @@ +package com.github.dadekuma.droidstomplib.connection; + +public interface IStompCallback { + void onConnectionOpened(); + void onConnectionClosed(int code, String reason); + void onResponseReceived(String response); + void onMessageReceived(String topic, Long subscriptionId, String message); + boolean isConnected(); + boolean isConnecting(); +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompClient.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompClient.java new file mode 100644 index 0000000..5a6dc66 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/IStompClient.java @@ -0,0 +1,18 @@ +package com.github.dadekuma.droidstomplib.connection; + +import com.github.dadekuma.droidstomplib.payload.HttpHeader; + +import java.util.Collection; + +public interface IStompClient { + void setStompCallback(IStompCallback stompCallback); + void connect(String stompEndpoint); + void connect(String stompEndpoint, Collection headers); + void send(String stompDestination, String message); + void sendJson(String stompDestination, String jsonMessage); + void subscribe(String topic); + void unsubscribe(String topic); + void disconnect(); + boolean isConnected(); + boolean isConnecting(); +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/OkHttpConnectionProvider.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/OkHttpConnectionProvider.java new file mode 100644 index 0000000..132d548 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/OkHttpConnectionProvider.java @@ -0,0 +1,82 @@ +package com.github.dadekuma.droidstomplib.connection; + +import com.github.dadekuma.droidstomplib.payload.HttpHeader; + +import java.util.Collection; + +import okhttp3.OkHttpClient; +import okhttp3.Request; +import okhttp3.Response; +import okhttp3.WebSocket; +import okhttp3.WebSocketListener; +import okio.ByteString; + + +public class OkHttpConnectionProvider implements IConnectionProvider { + private OkHttpClient okHttpClient; + private WebSocket webSocket; + private IStompCallback stompCallback; + + public OkHttpConnectionProvider() { + this(new OkHttpClient()); + } + + public OkHttpConnectionProvider(OkHttpClient okHttpClient) { + this.okHttpClient = okHttpClient; + } + + + @Override + public void connect(String stompEndpoint, Collection headers) { + Request.Builder requestBuilder = new Request.Builder().url(stompEndpoint); + //add all http headers that you need to the request. + for (HttpHeader h : headers) { + requestBuilder.addHeader(h.getName(), h.getValue()); + } + Request request = requestBuilder.build(); + + webSocket = okHttpClient.newWebSocket(request, new WebSocketListener() { + @Override + public void onOpen(WebSocket webSocket, Response response) { + if(stompCallback == null) return; + stompCallback.onConnectionOpened(); + } + + @Override + public void onMessage(WebSocket webSocket, ByteString bytes) { + } + + @Override + public void onClosed(WebSocket webSocket, int code, String reason) { + if(stompCallback == null) return; + stompCallback.onConnectionClosed(code, reason); + } + + @Override + public void onMessage(WebSocket webSocket, String text) { + if(stompCallback == null) return; + stompCallback.onResponseReceived(text); + } + }); + } + + @Override + public void send(String payload) { + webSocket.send(payload); + } + + @Override + public void setStompCallback(IStompCallback stompCallback) { + this.stompCallback = stompCallback; + } + + @Override + public boolean isConnected() { + return stompCallback.isConnected(); + } + + @Override + public boolean isConnecting() { + return stompCallback.isConnecting(); + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompCallback.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompCallback.java new file mode 100644 index 0000000..bf13755 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompCallback.java @@ -0,0 +1,55 @@ +package com.github.dadekuma.droidstomplib.connection; + +import com.github.dadekuma.droidstomplib.enums.StompHeaderName; +import com.github.dadekuma.droidstomplib.payload.StompFrame; +import com.github.dadekuma.droidstomplib.payload.StompParser; + +import java.util.Map; + +public abstract class StompCallback implements IStompCallback{ + private boolean isConnected, isConnecting; + + @Override + public void onConnectionOpened() { + isConnecting = true; + } + + @Override + public void onConnectionClosed(int code, String reason) { + isConnected = isConnecting = false; + } + + @Override + public void onResponseReceived(String response) { + StompFrame stompFrame = StompParser.parse(response); + switch (stompFrame.getStompCommand()){ + case CONNECTED: + isConnected = true; + break; + case MESSAGE: + handleSubscriptionMessage(stompFrame); + break; + } + } + + private void handleSubscriptionMessage(StompFrame stompFrame){ + Map headers = stompFrame.getStompHeaders(); + String topic = headers.get(StompHeaderName.DESTINATION); + long subscriptionId = Long.parseLong(headers.get(StompHeaderName.SUBSCRIPTION)); + String body = stompFrame.getStompBody(); + onMessageReceived(topic, subscriptionId, body); + } + + @Override + public abstract void onMessageReceived(String topic, Long subscriptionId, String message); + + @Override + public boolean isConnected() { + return isConnected; + } + + @Override + public boolean isConnecting() { + return isConnecting; + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompClient.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompClient.java new file mode 100644 index 0000000..a3c23a7 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/connection/StompClient.java @@ -0,0 +1,118 @@ +package com.github.dadekuma.droidstomplib.connection; + +import android.util.Log; + +import com.github.dadekuma.droidstomplib.enums.StompCommandName; +import com.github.dadekuma.droidstomplib.enums.StompHeaderName; +import com.github.dadekuma.droidstomplib.payload.HttpHeader; +import com.github.dadekuma.droidstomplib.payload.StompFrame; + +import java.util.Collection; +import java.util.HashMap; +import java.util.LinkedList; +import java.util.Map; + +public class StompClient implements IStompClient { + private Map subscriptions; + private long subscriptionId; + private IConnectionProvider connectionProvider; + + public StompClient() { + this(new OkHttpConnectionProvider()); + } + + public StompClient(IConnectionProvider connectionProvider) { + this.connectionProvider = connectionProvider; + subscriptions = new HashMap<>(); + } + + @Override + public void connect(String stompEndpoint) { + connect(stompEndpoint, new LinkedList()); + } + + @Override + public void connect(String stompEndpoint, Collection headers) { + connectionProvider.connect(stompEndpoint, headers); + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.CONNECT) + .addStompHeader(StompHeaderName.ACCEPT_VERSION, "1.0,1.1,2.0") + .addStompHeader(StompHeaderName.HOST, "stomp.github.org"); + connectionProvider.send(stompFrame.build()); + } + + @Override + public void send(String stompDestination, String message) { + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.SEND) + .addStompHeader(StompHeaderName.DESTINATION, stompDestination) + .addStompHeader(StompHeaderName.CONTENT_TYPE, "text/plain") + .addBody(message); + connectionProvider.send(stompFrame.build()); + } + + @Override + public void sendJson(String stompDestination, String jsonMessage) { + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.SEND) + .addStompHeader(StompHeaderName.DESTINATION, stompDestination) + .addStompHeader(StompHeaderName.CONTENT_TYPE, "application/json;charset=utf-8") + .addBody(jsonMessage); + connectionProvider.send(stompFrame.build()); + } + + @Override + public void subscribe(String topic) { + subscriptionId += 1; + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.SUBSCRIBE) + .addStompHeader(StompHeaderName.ID, String.valueOf(subscriptionId)) + .addStompHeader(StompHeaderName.DESTINATION, topic) + .addStompHeader(StompHeaderName.ACK, "auto"); + connectionProvider.send(stompFrame.build()); + subscriptions.put(topic, subscriptionId); + } + + @Override + public void unsubscribe(String topic) { + if (!subscriptions.containsKey(topic)) { + Log.e("SUB_NOT_FOUND", "Subscription doesn't exist"); + return; + } + Long unsubscribeId = subscriptions.get(topic); + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.UNSUBSCRIBE) + .addStompHeader(StompHeaderName.ID, String.valueOf(unsubscribeId)); + connectionProvider.send(stompFrame.build()); + } + + @Override + public void disconnect() { + unsubscribeAll(); + StompFrame stompFrame = new StompFrame(); + stompFrame.addStompCommand(StompCommandName.DISCONNECT) + .addStompHeader(StompHeaderName.RECEIPT, String.valueOf(subscriptionId)); + connectionProvider.send(stompFrame.build()); + } + + public void unsubscribeAll() { + for (String topic : subscriptions.keySet()) { + unsubscribe(topic); + } + } + + @Override + public void setStompCallback(IStompCallback stompCallback){ + connectionProvider.setStompCallback(stompCallback); + } + + @Override + public boolean isConnected() { + return connectionProvider.isConnected(); + } + + @Override + public boolean isConnecting() { + return connectionProvider.isConnecting(); + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompCommandName.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompCommandName.java new file mode 100644 index 0000000..8d4807e --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompCommandName.java @@ -0,0 +1,36 @@ +package com.github.dadekuma.droidstomplib.enums; + +public enum StompCommandName { + CONNECT("CONNECT"), + CONNECTED("CONNECTED"), + SEND("SEND"), + SUBSCRIBE("SUBSCRIBE"), + UNSUBSCRIBE("UNSUBSCRIBE"), + BEGIN("BEGIN"), + COMMIT("COMMIT"), + ABORT("ABORT"), + ACK("ACK"), + NACK("NACK"), + DISCONNECT("DISCONNECT"), + MESSAGE("MESSAGE"), + RECEIPT("RECEIPT"), + ERROR("ERROR") + ; + + String command; + StompCommandName(String command) { + this.command = command; + } + + @Override + public String toString() { + return command; + } + + public static StompCommandName getEnum(String stompCommandName) { + for (StompCommandName h : StompCommandName.values()) { + if (h.toString().equals(stompCommandName)) return h; + } + throw new IllegalArgumentException("StompCommandName not found."); + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompHeaderName.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompHeaderName.java new file mode 100644 index 0000000..9e0e94b --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompHeaderName.java @@ -0,0 +1,38 @@ +package com.github.dadekuma.droidstomplib.enums; + +public enum StompHeaderName { + ACCEPT_VERSION("accept-version"), + CONTENT_LENGTH("content-length"), + CONTENT_TYPE("content-type"), + ID("id"), + ACK("ack"), + HOST("host"), + RECEIPT("receipt"), + DESTINATION("destination"), + SERVER("server"), + SESSION("session"), + SUBSCRIPTION("subscription"), + MESSAGE_ID("message-id"), + RECEIPT_ID("receipt-id"), + HEART_BEAT("heart-beat"), + MESSAGE("message"), + VERSION("version"), + ; + + private String header; + StompHeaderName(String header) { + this.header = header; + } + + @Override + public String toString() { + return header; + } + + public static StompHeaderName getEnum(String stompHeaderName) { + for (StompHeaderName h : StompHeaderName.values()) { + if (h.toString().equals(stompHeaderName)) return h; + } + throw new IllegalArgumentException("StompHeaderName not found."); + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompSymbolName.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompSymbolName.java new file mode 100644 index 0000000..4ee04e7 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/enums/StompSymbolName.java @@ -0,0 +1,17 @@ +package com.github.dadekuma.droidstomplib.enums; + +public enum StompSymbolName { + SEPARATOR(":"), + NEWLINE("\n"), + TERMINATOR("\u0000"); + + private String symbol; + StompSymbolName(String symbol) { + this.symbol = symbol; + } + + @Override + public String toString() { + return symbol; + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/HttpHeader.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/HttpHeader.java new file mode 100644 index 0000000..07e2720 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/HttpHeader.java @@ -0,0 +1,19 @@ +package com.github.dadekuma.droidstomplib.payload; + +public class HttpHeader { + private String name; + private String value; + + public HttpHeader(String name, String value) { + this.name = name; + this.value = value; + } + + public String getName() { + return name; + } + + public String getValue() { + return value; + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompFrame.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompFrame.java new file mode 100644 index 0000000..ea6f5e7 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompFrame.java @@ -0,0 +1,69 @@ +package com.github.dadekuma.droidstomplib.payload; + +import android.support.annotation.NonNull; + +import com.github.dadekuma.droidstomplib.enums.StompCommandName; +import com.github.dadekuma.droidstomplib.enums.StompHeaderName; +import com.github.dadekuma.droidstomplib.enums.StompSymbolName; + +import java.io.Serializable; +import java.util.LinkedHashMap; +import java.util.Map; + +public class StompFrame { + private Map stompHeaders; + private StompCommandName stompCommand; + private String stompBody; + + public StompFrame() { + stompHeaders = new LinkedHashMap<>(); + } + + public StompFrame addStompCommand(@NonNull StompCommandName command){ + this.stompCommand = command; + return this; + } + + public StompFrame addStompHeader(@NonNull StompHeaderName header, @NonNull String value){ + stompHeaders.put(header, value); + return this; + } + + public StompFrame addBody(Serializable body){ + stompBody = body.toString(); + return this; + } + + public String build(){ + String newline = StompSymbolName.NEWLINE.toString(); + String separator = StompSymbolName.SEPARATOR.toString(); + String terminator = StompSymbolName.TERMINATOR.toString(); + + StringBuilder stringBuilder = new StringBuilder(); + stringBuilder.append(stompCommand).append(newline); + + for(StompHeaderName headerName : stompHeaders.keySet()){ + String name = headerName.toString(); + String value = stompHeaders.get(headerName); + stringBuilder.append(name).append(separator).append(value).append(newline); + } + stringBuilder.append(newline); + if(stompBody != null){ + stringBuilder.append(stompBody).append(newline); + } + stringBuilder.append(terminator); + return stringBuilder.toString(); + } + + public Map getStompHeaders() { + return stompHeaders; + } + + public StompCommandName getStompCommand() { + return stompCommand; + } + + public String getStompBody() { + return stompBody; + } +} diff --git a/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompParser.java b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompParser.java new file mode 100644 index 0000000..99a5cf7 --- /dev/null +++ b/droidstomplib/src/main/java/com/github/dadekuma/droidstomplib/payload/StompParser.java @@ -0,0 +1,60 @@ +package com.github.dadekuma.droidstomplib.payload; + +import android.util.Log; + +import com.github.dadekuma.droidstomplib.enums.StompCommandName; +import com.github.dadekuma.droidstomplib.enums.StompHeaderName; +import com.github.dadekuma.droidstomplib.enums.StompSymbolName; + +public class StompParser { + public static StompFrame parse(String message) { + StompFrame stompFrame = new StompFrame(); + String[] messageRows = message.split(StompSymbolName.NEWLINE.toString()); + try { + StompCommandName stompCommandName = StompCommandName.getEnum(messageRows[0]); + stompFrame.addStompCommand(stompCommandName); + } + catch (IllegalArgumentException e){ + Log.e("STOMP_ILLEGAL_COMMAND", e.getMessage()); + } + catch (RuntimeException e){ + e.fillInStackTrace(); + Log.e("STOMP_PARSER_EX", e.getMessage()); + } + + int bodyPosition = 1; + for (int i = 1; i < messageRows.length; ++i) { + if (messageRows[i].equals("")) { + bodyPosition = i; + break; + } + try { + String[] header = messageRows[i].split(StompSymbolName.SEPARATOR.toString()); + StompHeaderName headerName = StompHeaderName.getEnum(header[0]); + String headerValue = header[1]; + stompFrame.addStompHeader(headerName, headerValue); + } + catch (IllegalArgumentException e){ + Log.e("STOMP_ILLEGAL_HEADER", e.getMessage()); + } + catch (RuntimeException e){ + e.fillInStackTrace(); + Log.e("STOMP_PARSER_EX", e.getMessage()); + } + } + String stompBody = parseBody(bodyPosition, messageRows); + stompFrame.addBody(stompBody); + return stompFrame; + } + + private static String parseBody(int startPosition, String[] messageRows){ + StringBuilder stompBody = new StringBuilder(); + for (int i = startPosition; i < messageRows.length; i++) { + if(messageRows[i].equals(StompSymbolName.TERMINATOR.toString())){ + break; + } + stompBody.append(messageRows[i]); + } + return stompBody.toString(); + } +} \ No newline at end of file diff --git a/droidstomplib/src/main/res/values/strings.xml b/droidstomplib/src/main/res/values/strings.xml new file mode 100644 index 0000000..6d6df04 --- /dev/null +++ b/droidstomplib/src/main/res/values/strings.xml @@ -0,0 +1,3 @@ + + DroidSTOMP + diff --git a/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/ExampleUnitTest.java b/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/ExampleUnitTest.java new file mode 100644 index 0000000..376b64f --- /dev/null +++ b/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/ExampleUnitTest.java @@ -0,0 +1,17 @@ +package com.github.dadekuma.droidstomplib; + +import org.junit.Test; + +import static org.junit.Assert.*; + +/** + * Example local unit test, which will execute on the development machine (host). + * + * @see Testing documentation + */ +public class ExampleUnitTest { + @Test + public void addition_isCorrect() { + assertEquals(4, 2 + 2); + } +} \ No newline at end of file diff --git a/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/StompFrameTest.java b/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/StompFrameTest.java new file mode 100644 index 0000000..368a9f9 --- /dev/null +++ b/droidstomplib/src/test/java/com/github/dadekuma/droidstomplib/StompFrameTest.java @@ -0,0 +1,66 @@ +package com.github.dadekuma.droidstomplib; + +import com.github.dadekuma.droidstomplib.enums.StompCommandName; +import com.github.dadekuma.droidstomplib.enums.StompHeaderName; +import com.github.dadekuma.droidstomplib.payload.StompFrame; + +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; + +public class StompFrameTest { + private StompFrame stompFrame; + + @Before + public void initStompFrame(){ + stompFrame = new StompFrame(); + } + + @Test + public void buildTest(){ + stompFrame.addStompCommand(StompCommandName.CONNECT); + stompFrame.addStompHeader(StompHeaderName.ID, "1"); + String result = stompFrame.build(); + String expected = "CONNECT\n" + + "id:1\n" + + "\n" + + "\u0000"; + Assert.assertEquals(expected, result); + } + + @Test + public void buildMultipleHeadersTest(){ + stompFrame.addStompCommand(StompCommandName.SEND); + stompFrame.addStompHeader(StompHeaderName.ID, "10") + .addStompHeader(StompHeaderName.DESTINATION, "/topic/example") + .addStompHeader(StompHeaderName.CONTENT_TYPE, "text-plain"); + String result = stompFrame.build(); + String expected = "SEND\n" + + "id:10\n" + + "destination:/topic/example\n" + + "content-type:text-plain\n" + + "\n" + + "\u0000"; + Assert.assertEquals(expected, result); + } + + @Test + public void buildWithBody(){ + stompFrame.addStompCommand(StompCommandName.MESSAGE); + stompFrame.addStompHeader(StompHeaderName.SUBSCRIPTION, "10") + .addStompHeader(StompHeaderName.MESSAGE_ID,"004") + .addStompHeader(StompHeaderName.DESTINATION, "/topic/example") + .addStompHeader(StompHeaderName.CONTENT_TYPE, "text-plain") + .addBody("Hello darkness my old friend"); + String result = stompFrame.build(); + String expected = "MESSAGE\n" + + "subscription:10\n" + + "message-id:004\n" + + "destination:/topic/example\n" + + "content-type:text-plain\n" + + "\n" + + "Hello darkness my old friend\n" + + "\u0000"; + Assert.assertEquals(expected, result); + } +} \ No newline at end of file