UNPKG

networked-aframe

Version:

A web framework for building multi-user virtual reality experiences.

440 lines (318 loc) 12.2 kB
/* global assert, setup, suite, test, sinon, teardown */ var NetworkConnection = require('../../src/NetworkConnection'); var AdapterFactory = require('../../src/adapters/AdapterFactory'); var naf = require('../../src/NafIndex'); suite('NetworkConnection', function() { var connection; var entities; var adapter; function NetworkEntitiesStub() { this.completeSync = sinon.stub(); this.removeEntitiesOfClient = sinon.stub(); this.updateEntity = sinon.stub(); this.updateEntityMulti = sinon.stub(); this.removeRemoteEntity = sinon.stub(); this.removeEntity = sinon.stub(); } function MockNetworkAdapter() { this.setServerUrl = sinon.stub(); this.setApp = sinon.stub(); this.setRoom = sinon.stub(); this.setWebRtcOptions = sinon.stub(); this.setServerConnectListeners = sinon.stub(); this.setRoomOccupantListener = sinon.stub(); this.setDataChannelListeners = sinon.stub(); this.connect = sinon.stub(); this.shouldStartConnectionTo = sinon.stub(); this.startStreamConnection = sinon.stub(); this.closeStreamConnection = sinon.stub(); this.getConnectStatus = sinon.stub(); this.sendData = sinon.stub(); this.sendDataGuaranteed = sinon.stub(); this.broadcastData = sinon.stub(); this.broadcastDataGuaranteed = sinon.stub(); } setup(function() { entities = new NetworkEntitiesStub(); connection = new NetworkConnection(entities); adapter = new MockNetworkAdapter(); connection.setNetworkAdapter(adapter); }); teardown(function() { naf.clientId = ''; }); suite('setupDefaultDataSubscriptions', function() { test('subscribes to NetworkEntities DC callbacks', function() { var actualSync = connection.dataChannelSubs['u']; var actualRemove = connection.dataChannelSubs['r']; assert.isOk(actualSync); assert.isOk(actualRemove); }); }); suite('onConnect', function () { test('callback is called immediately if already connected', function() { var stub = sinon.stub(); connection.connectSuccess('test-id'); connection.onConnect(stub); assert.isTrue(stub.called); }); test('callback is not called immediately if not connected', function() { var stub = sinon.stub(); connection.onConnect(stub); assert.isFalse(stub.called); }); test('callback is fired when connected', function() { var stub = sinon.stub(); connection.onConnect(stub); assert.isFalse(stub.called); connection.connectSuccess('test-id'); assert.isTrue(stub.called); }); test('multiple callbacks are fired when logged in', function() { var stub = sinon.stub(); var stub2 = sinon.stub(); connection.onConnect(stub); connection.onConnect(stub2); assert.isFalse(stub.called); assert.isFalse(stub2.called); connection.connectSuccess('test-id'); assert.isTrue(stub.called); assert.isTrue(stub2.called); }); test('callback is not fired when connecting in unsuccessful', function() { var stub = sinon.stub(); connection.onConnect(stub); assert.isFalse(stub.called); connection.connectFailure('test-id'); assert.isFalse(stub.called); }); }); suite('connectSuccess', function() { test('setting client id', function() { var id = 'testId1'; connection.connectSuccess(id); assert.isTrue(connection.isMineAndConnected(id)); }); }); suite('connectFailure', function() { test('runs', function() { connection.connectFailure(0, 'msg'); }); }); suite('occupantsReceived', function() { test('updates connect list', function() { var occupants = { 'user1': true }; connection.occupantsReceived(occupants); assert.equal(connection.connectedClients, occupants); }); test('newer client joins and starts call', function() { connection.myRoomJoinTime = 1; var newClient = { roomJoinTime: 10 }; var occupants = { 'user1': newClient }; adapter.getConnectStatus = sinon.stub().returns(AdapterFactory.NOT_CONNECTED); adapter.shouldStartConnectionTo = sinon.stub().returns(true); connection.occupantsReceived(occupants); assert.isTrue(adapter.startStreamConnection.called); }); test('older client joins and does not start call', function() { connection.myRoomJoinTime = 10; var olderClient = { roomJoinTime: 1 }; var occupants = { 'user1': olderClient }; adapter.getConnectStatus = sinon.stub().returns(AdapterFactory.NOT_CONNECTED); connection.occupantsReceived(occupants); assert.isFalse(adapter.startStreamConnection.called); }); }); suite('isMineAndConnected', function() { test('is my client id', function() { var testId = 'test1'; connection.connectSuccess(testId); var result = connection.isMineAndConnected(testId); assert.isTrue(result); }); test('is not my client id', function() { var testId = 'test1'; connection.connectSuccess(testId); var result = connection.isMineAndConnected('wrong'); assert.isFalse(result); }); }); suite('isNewClient', function() { test('not connected', function() { var testId = 'test1'; adapter.getConnectStatus = sinon.stub().returns(AdapterFactory.NOT_CONNECTED); var result = connection.isNewClient(testId); assert.isTrue(result); }); test('is connected', function() { var testId = 'test1'; adapter.getConnectStatus = sinon.stub().returns(AdapterFactory.IS_CONNECTED); var result = connection.isNewClient(testId); assert.isFalse(result); }); }); suite('isConnectedTo', function() { test('is connected', function() { var otherClientId = 'other'; var connected = AdapterFactory.IS_CONNECTED; adapter.getConnectStatus = sinon.stub().returns(connected); var result = connection.isConnectedTo(otherClientId); assert.isTrue(result); }); test('is not connected', function() { var otherClientId = 'other'; var notConnected = AdapterFactory.NOT_CONNECTED; adapter.getConnectStatus = sinon.stub().returns(notConnected); var result = connection.isConnectedTo(otherClientId); assert.isFalse(result); }); }); suite('dataChannelOpen', function() { test('connects and syncs', function() { var clientId = 'other'; connection.dataChannelOpen(clientId); var hasMessageChannel = connection.hasActiveDataChannel(clientId); assert.isTrue(hasMessageChannel); assert.isTrue(entities.completeSync.called); }); test('is not connected to', function() { var clientId = 'correct'; var wrongClientId = 'wrong'; connection.dataChannelOpen(clientId); var hasMessageChannel = connection.hasActiveDataChannel(wrongClientId); assert.isFalse(hasMessageChannel); assert.isTrue(entities.completeSync.called); }); }); suite('dataChannelClosed', function() { test('connects and syncs', function() { var clientId = 'client'; connection.dataChannelClosed(clientId); var hasMessageChannel = connection.hasActiveDataChannel(clientId); assert.isFalse(hasMessageChannel); assert.isTrue(entities.removeEntitiesOfClient.called); }); test('is still connected to other', function() { var clientId = 'removeMe'; var otherClientId = 'other'; connection.dataChannelOpen(otherClientId); connection.dataChannelClosed(clientId); var hasMessageChannel = connection.hasActiveDataChannel(otherClientId); assert.isTrue(hasMessageChannel); assert.isTrue(entities.removeEntitiesOfClient.called); }); }); suite('broadcastData', function() { test('broadcast data to adapter', function() { var data = {things:true}; connection.broadcastData('s', data); assert.isTrue(adapter.broadcastData.calledWith('s', data)); }); }); suite('broadcastDataGuaranteed', function() { test('sends guaranteed data to each client', function() { var data = {things:true}; connection.broadcastDataGuaranteed('s', data); assert.isTrue(adapter.broadcastDataGuaranteed.calledWith('s', data)); }); }); suite('sendData', function() { test('is connected, not guaranteed', function() { var clientId = 'client1'; var dataType = 's'; var data = {}; sinon.stub(connection, 'hasActiveDataChannel').returns(true); connection.sendData(clientId, dataType, data, false); assert.isFalse(adapter.sendDataGuaranteed.called); assert.isTrue(adapter.sendData.calledWith(clientId, dataType, data)); }); test('is connected, guaranteed', function() { var clientId = 'client1'; var dataType = 's'; var data = {}; sinon.stub(connection, 'hasActiveDataChannel').returns(true); connection.sendData(clientId, dataType, data, true); assert.isFalse(adapter.sendData.called); assert.isTrue(adapter.sendDataGuaranteed.calledWith(clientId, dataType, data)); }); test('not connected', function() { var clientId = 'client1'; var dataType = 's'; var data = {}; sinon.stub(connection, 'hasActiveDataChannel').returns(false); connection.sendData(clientId, dataType, data); assert.isFalse(adapter.sendData.called); assert.isFalse(adapter.sendDataGuaranteed.called); }); }); suite('sendDataGuaranteed', function() { test('sends data guaranteed', function() { var clientId = 'client1'; var dataType = 's'; var data = {}; sinon.stub(connection, 'hasActiveDataChannel').returns(true); sinon.spy(connection, 'sendData'); connection.sendDataGuaranteed(clientId, dataType, data); assert.isTrue(connection.sendData.calledWith(clientId, dataType, data, true)); }); }); suite('subscribeToDataChannel', function() { test('is added to datachannel subscribers', function() { var dataType = 'method1'; var callback = function() { return 'callback' }; connection.subscribeToDataChannel(dataType, callback); var actual = connection.dataChannelSubs[dataType]; assert.deepEqual(actual, callback); }); }); suite('unsubscribeToDataChannel', function() { test('is removed from datachannel subscribers', function() { var dataType = 'method1'; var callback = function() { return 'callback' }; connection.dataChannelSubs[dataType] = callback; connection.unsubscribeToDataChannel(dataType); assert.isTrue(!connection.dataChannelSubs[dataType]); }); }); suite('receivedData', function() { test('sync entity', function() { connection.receivedData('client', 'u', {testData:true}); assert.isTrue(entities.updateEntity.called); assert.isFalse(entities.removeEntity.called); }); test('remove entity', function() { connection.receivedData('client', 'r', {testData:true}); assert.isFalse(entities.updateEntity.called); assert.isTrue(entities.removeRemoteEntity.called); }); test('unknown msg type', function() { connection.receivedData('client', 'unknown', {testData:true}); assert.isFalse(entities.updateEntity.called); assert.isFalse(entities.removeEntity.called); }); test('subscribe then call', function() { var dataType = 'method1'; var stub = sinon.stub(); var data = { test: true }; connection.subscribeToDataChannel(dataType, stub); connection.receivedData('client1', dataType, data); assert.isTrue(stub.calledWith('client1', dataType, data)); }); }); suite('isConnected', function() { test('true when connected', function() { connection.connectSuccess('testid2'); var result = connection.isConnected(); assert.isTrue(result); }); test('false when not connected', function() { var result = connection.isConnected(); assert.isFalse(result); }); }); });