| /* |
| * Copyright 2016 The WebRTC Project Authors. All rights reserved. |
| * |
| * Use of this source code is governed by a BSD-style license |
| * that can be found in the LICENSE file in the root of the source |
| * tree. An additional intellectual property rights grant can be found |
| * in the file PATENTS. All contributing project authors may |
| * be found in the AUTHORS file in the root of the source tree. |
| */ |
| |
| package org.appspot.apprtc; |
| |
| import static org.junit.Assert.assertFalse; |
| import static org.junit.Assert.assertTrue; |
| import static org.junit.Assert.fail; |
| import static org.mockito.ArgumentMatchers.any; |
| import static org.mockito.ArgumentMatchers.isNotNull; |
| import static org.mockito.Mockito.mock; |
| import static org.mockito.Mockito.timeout; |
| import static org.mockito.Mockito.verify; |
| import static org.mockito.Mockito.verifyNoMoreInteractions; |
| |
| import org.chromium.testing.local.LocalRobolectricTestRunner; |
| import org.junit.Before; |
| import org.junit.Test; |
| import org.junit.runner.RunWith; |
| import org.robolectric.annotation.Config; |
| import org.robolectric.shadows.ShadowLog; |
| import org.webrtc.IceCandidate; |
| import org.webrtc.SessionDescription; |
| |
| /** |
| * Test for DirectRTCClient. Test is very simple and only tests the overall sanity of the class |
| * behaviour. |
| */ |
| @RunWith(LocalRobolectricTestRunner.class) |
| @Config(manifest = Config.NONE) |
| public class DirectRTCClientTest { |
| private static final String ROOM_URL = ""; |
| private static final boolean LOOPBACK = false; |
| |
| private static final String DUMMY_SDP_MID = "sdpMid"; |
| private static final String DUMMY_SDP = "sdp"; |
| |
| public static final int SERVER_WAIT = 100; |
| public static final int NETWORK_TIMEOUT = 1000; |
| |
| private DirectRTCClient client; |
| private DirectRTCClient server; |
| |
| AppRTCClient.SignalingEvents clientEvents; |
| AppRTCClient.SignalingEvents serverEvents; |
| |
| @Before |
| public void setUp() { |
| ShadowLog.stream = System.out; |
| |
| clientEvents = mock(AppRTCClient.SignalingEvents.class); |
| serverEvents = mock(AppRTCClient.SignalingEvents.class); |
| |
| client = new DirectRTCClient(clientEvents); |
| server = new DirectRTCClient(serverEvents); |
| } |
| |
| @Test |
| public void testValidIpPattern() { |
| // Strings that should match the pattern. |
| // clang-format off |
| final String[] ipAddresses = new String[] { |
| "0.0.0.0", |
| "127.0.0.1", |
| "192.168.0.1", |
| "0.0.0.0:8888", |
| "127.0.0.1:8888", |
| "192.168.0.1:8888", |
| "::", |
| "::1", |
| "2001:0db8:85a3:0000:0000:8a2e:0370:7946", |
| "[::]", |
| "[::1]", |
| "[2001:0db8:85a3:0000:0000:8a2e:0370:7946]", |
| "[::]:8888", |
| "[::1]:8888", |
| "[2001:0db8:85a3:0000:0000:8a2e:0370:7946]:8888" |
| }; |
| // clang-format on |
| |
| for (String ip : ipAddresses) { |
| assertTrue(ip + " didn't match IP_PATTERN even though it should.", |
| DirectRTCClient.IP_PATTERN.matcher(ip).matches()); |
| } |
| } |
| |
| @Test |
| public void testInvalidIpPattern() { |
| // Strings that shouldn't match the pattern. |
| // clang-format off |
| final String[] invalidIpAddresses = new String[] { |
| "Hello, World!", |
| "aaaa", |
| "1111", |
| "[hello world]", |
| "hello:world" |
| }; |
| // clang-format on |
| |
| for (String invalidIp : invalidIpAddresses) { |
| assertFalse(invalidIp + " matched IP_PATTERN even though it shouldn't.", |
| DirectRTCClient.IP_PATTERN.matcher(invalidIp).matches()); |
| } |
| } |
| |
| // TODO(sakal): Replace isNotNull(class) with isNotNull() once Java 8 is used. |
| @SuppressWarnings("deprecation") |
| @Test |
| public void testDirectRTCClient() { |
| server.connectToRoom(new AppRTCClient.RoomConnectionParameters(ROOM_URL, "0.0.0.0", LOOPBACK)); |
| try { |
| Thread.sleep(SERVER_WAIT); |
| } catch (InterruptedException e) { |
| fail(e.getMessage()); |
| } |
| client.connectToRoom( |
| new AppRTCClient.RoomConnectionParameters(ROOM_URL, "127.0.0.1", LOOPBACK)); |
| verify(serverEvents, timeout(NETWORK_TIMEOUT)) |
| .onConnectedToRoom(any(AppRTCClient.SignalingParameters.class)); |
| |
| SessionDescription offerSdp = new SessionDescription(SessionDescription.Type.OFFER, DUMMY_SDP); |
| server.sendOfferSdp(offerSdp); |
| verify(clientEvents, timeout(NETWORK_TIMEOUT)) |
| .onConnectedToRoom(any(AppRTCClient.SignalingParameters.class)); |
| |
| SessionDescription answerSdp = |
| new SessionDescription(SessionDescription.Type.ANSWER, DUMMY_SDP); |
| client.sendAnswerSdp(answerSdp); |
| verify(serverEvents, timeout(NETWORK_TIMEOUT)) |
| .onRemoteDescription(isNotNull(SessionDescription.class)); |
| |
| IceCandidate candidate = new IceCandidate(DUMMY_SDP_MID, 0, DUMMY_SDP); |
| server.sendLocalIceCandidate(candidate); |
| verify(clientEvents, timeout(NETWORK_TIMEOUT)) |
| .onRemoteIceCandidate(isNotNull(IceCandidate.class)); |
| |
| client.sendLocalIceCandidate(candidate); |
| verify(serverEvents, timeout(NETWORK_TIMEOUT)) |
| .onRemoteIceCandidate(isNotNull(IceCandidate.class)); |
| |
| client.disconnectFromRoom(); |
| verify(clientEvents, timeout(NETWORK_TIMEOUT)).onChannelClose(); |
| verify(serverEvents, timeout(NETWORK_TIMEOUT)).onChannelClose(); |
| |
| verifyNoMoreInteractions(clientEvents); |
| verifyNoMoreInteractions(serverEvents); |
| } |
| } |