Package com.pusher.client.connection.websocket

Source Code of com.pusher.client.connection.websocket.WebSocketConnectionTest

package com.pusher.client.connection.websocket;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyString;
import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

import java.net.URI;
import java.net.URISyntaxException;

import javax.net.ssl.SSLException;

import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.runners.MockitoJUnitRunner;

import com.pusher.client.channel.impl.ChannelManager;
import com.pusher.client.connection.ConnectionEventListener;
import com.pusher.client.connection.ConnectionState;
import com.pusher.client.connection.ConnectionStateChange;
import com.pusher.client.util.DoNothingExecutor;
import com.pusher.client.util.Factory;
import com.pusher.client.util.InstantExecutor;

@RunWith(MockitoJUnitRunner.class)
public class WebSocketConnectionTest {

    private static final long ACTIVITY_TIMEOUT = 120000;
    private static final long PONG_TIMEOUT = 30000;
    private static final String URL = "ws://ws.example.com/";
    private static final String EVENT_NAME = "my-event";
    private static final String CONN_ESTABLISHED_EVENT =
            "{\"event\":\"pusher:connection_established\",\"data\":\"{\\\"socket_id\\\":\\\"21112.816204\\\"}\"}";
    private static final String INCOMING_MESSAGE =
            "{\"event\":\"" + EVENT_NAME + "\",\"channel\":\"my-channel\",\"data\":{\"fish\":\"chips\"}}";

    @Mock
    private ChannelManager mockChannelManager;
    @Mock
    private WebSocketClientWrapper mockUnderlyingConnection;
    @Mock
    private ConnectionEventListener mockEventListener;
    @Mock
    private Factory factory;

    private WebSocketConnection connection;

    @Before
    public void setUp() throws URISyntaxException, SSLException {
        when(factory.getChannelManager()).thenReturn(mockChannelManager);
        when(factory.newWebSocketClientWrapper(any(URI.class), any(WebSocketConnection.class)))
                .thenReturn(mockUnderlyingConnection);
        when(factory.getEventQueue()).thenReturn(new InstantExecutor());
        when(factory.getTimers()).thenReturn(new DoNothingExecutor());

        this.connection = new WebSocketConnection(URL, ACTIVITY_TIMEOUT, PONG_TIMEOUT, factory);
        this.connection.bind(ConnectionState.ALL, mockEventListener);
    }

    @Test
    public void testUnbindingWhenNotAlreadyBoundReturnsFalse() throws URISyntaxException {
        ConnectionEventListener listener = mock(ConnectionEventListener.class);
        WebSocketConnection connection = new WebSocketConnection(URL, ACTIVITY_TIMEOUT, PONG_TIMEOUT, factory);
        boolean unbound = connection.unbind(ConnectionState.ALL, listener);
        assertEquals(false, unbound);
    }

    @Test
    public void testUnbindingWhenBoundReturnsTrue() throws URISyntaxException {
        ConnectionEventListener listener = mock(ConnectionEventListener.class);
        WebSocketConnection connection = new WebSocketConnection(URL, ACTIVITY_TIMEOUT, PONG_TIMEOUT, factory);

        connection.bind(ConnectionState.ALL, listener);

        boolean unbound = connection.unbind(ConnectionState.ALL, listener);
        assertEquals(true, unbound);
    }

    @Test
    public void testStartsInDisconnectedState() {
        assertSame(ConnectionState.DISCONNECTED, connection.getState());
    }

    @Test
    public void testConnectCallIsDelegatedToUnderlyingConnection() {
        connection.connect();
        verify(mockUnderlyingConnection).connect();
    }

    @Test
    public void testConnectUpdatesStateAndNotifiesListener() {
        connection.connect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.DISCONNECTED, ConnectionState.CONNECTING));
        assertEquals(ConnectionState.CONNECTING, connection.getState());
    }

    @Test
    public void testConnectDoesNotCallConnectOnUnderlyingConnectionIfAlreadyInConnectingState() {
        connection.connect();
        connection.connect();

        verify(mockUnderlyingConnection, times(1)).connect();
        verify(mockEventListener, times(1)).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    @Test
    public void testListenerDoesNotReceiveConnectingEventIfItIsOnlyBoundToTheConnectedEvent() throws URISyntaxException {
        connection = new WebSocketConnection(URL, ACTIVITY_TIMEOUT, PONG_TIMEOUT, factory);
        connection.bind(ConnectionState.CONNECTED, mockEventListener);
        connection.connect();

        verify(mockEventListener, never()).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    @Test
    public void testReceivePusherConnectionEstablishedMessageIsTranslatedToAConnectedCallback() {
        connection.connect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.DISCONNECTED, ConnectionState.CONNECTING));

        connection.onMessage(CONN_ESTABLISHED_EVENT);
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.CONNECTING, ConnectionState.CONNECTED));

        assertEquals(ConnectionState.CONNECTED, connection.getState());
    }

    @Test
    public void testReceivePusherConnectionEstablishedMessageSetsSocketId() {
        assertNull(connection.getSocketId());

        connection.connect();
        connection.onMessage(CONN_ESTABLISHED_EVENT);

        assertEquals("21112.816204", connection.getSocketId());
    }

    @Test
    public void testReceivePusherErrorMessageRaisesErrorEvent() {
        connection.connect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.DISCONNECTED, ConnectionState.CONNECTING));

        connection.onMessage(
                "{\"event\":\"pusher:error\",\"data\":{\"code\":4001,\"message\":\"Could not find app by key 12345\"}}");
        verify(mockEventListener).onError("Could not find app by key 12345", "4001", null);
    }

    @Test
    public void testSendMessageSendsMessageToPusher() {
        connect();

        connection.sendMessage("message");

        verify(mockUnderlyingConnection).send("message");
    }

    @Test
    public void testSendMessageWhenNotConnectedRaisesErrorEvent() {
        connection.sendMessage("message");

        verify(mockUnderlyingConnection, never()).send("message");
        verify(mockEventListener).onError(
                "Cannot send a message while in " + ConnectionState.DISCONNECTED.toString() + " state", null, null);
    }

    @Test
    public void testSendMessageWhenWebSocketLibraryThrowsExceptionRaisesErrorEvent() {
        connect();

        RuntimeException e = new RuntimeException();
        doThrow(e).when(mockUnderlyingConnection).send(anyString());

        connection.sendMessage("message");

        verify(mockEventListener).onError("An exception occurred while sending message [message]", null, e);
    }

    @Test
    public void testReceiveUserMessagePassesMessageToChannelManager() {
        connect();

        connection.onMessage(INCOMING_MESSAGE);

        verify(mockChannelManager).onMessage(EVENT_NAME, INCOMING_MESSAGE);
    }

    @Test
    public void testOnCloseCallbackUpdatesStateToDisconnected() {
        connection.connect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.DISCONNECTED, ConnectionState.CONNECTING));

        connection.onClose(1, "reason", true);
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.CONNECTING, ConnectionState.DISCONNECTED));
    }

    @Test
    public void testOnCloseCallbackDoesNotCallListenerIfItIsNotBoundToDisconnectedEvent() throws URISyntaxException {
        connection = new WebSocketConnection(URL, ACTIVITY_TIMEOUT, PONG_TIMEOUT, factory);
        connection.bind(ConnectionState.CONNECTED, mockEventListener);

        connection.connect();
        connection.onClose(1, "reason", true);
        verify(mockEventListener, never()).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    @Test
    public void testOnErrorCallbackRaisesErrorEvent() {
        connection.connect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.DISCONNECTED, ConnectionState.CONNECTING));

        Exception e = new Exception();
        connection.onError(e);
        verify(mockEventListener).onError("An exception was thrown by the websocket", null, e);
    }

    @Test
    public void testDisonnectCallIsDelegatedToUnderlyingConnection() {
        connection.connect();
        connection.onMessage(CONN_ESTABLISHED_EVENT);

        connection.disconnect();
        verify(mockUnderlyingConnection).close();
    }

    @Test
    public void testDisconnectInConnectedStateUpdatesStateToDisconnectingAndNotifiesListener() {
        connection.connect();
        connection.onMessage(CONN_ESTABLISHED_EVENT);

        connection.disconnect();
        verify(mockEventListener).onConnectionStateChange(
                new ConnectionStateChange(ConnectionState.CONNECTED, ConnectionState.DISCONNECTING));
        assertEquals(ConnectionState.DISCONNECTING, connection.getState());
    }

    @Test
    public void testDisconnectInDisconnectedStateIsIgnored() {
        connection.disconnect();

        verify(mockUnderlyingConnection, times(0)).close();
        verify(mockEventListener, times(0)).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    @Test
    public void testDisconnectInConnectingStateIsIgnored() {
        connection.connect();

        connection.disconnect();

        verify(mockUnderlyingConnection, times(0)).close();
        verify(mockEventListener, times(1)).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    @Test
    public void testDisconnectInDisconnectingStateIsIgnored() {
        connection.connect();
        connection.onMessage(CONN_ESTABLISHED_EVENT);

        connection.disconnect();

        verify(mockUnderlyingConnection, times(1)).close();
        verify(mockEventListener, times(3)).onConnectionStateChange(any(ConnectionStateChange.class));
    }

    /* end of tests */

    private void connect() {
        connection.connect();
        connection.onMessage(CONN_ESTABLISHED_EVENT);
    }
}
TOP

Related Classes of com.pusher.client.connection.websocket.WebSocketConnectionTest

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.