You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
242 lines
7.3 KiB
242 lines
7.3 KiB
/// <reference path="../typings/index.d.ts"/> |
|
|
|
import * as assert from 'assert'; |
|
|
|
import RpcProvider from '../src/RpcProvider'; |
|
|
|
suite('RPC provider', function() { |
|
|
|
let local: RpcProvider, |
|
remote: RpcProvider, |
|
transferLocalToRemote: Array<any>, |
|
transferRemoteToLocal: Array<any>, |
|
errorLocal: Error, |
|
errorRemote: Error; |
|
|
|
setup(function() { |
|
local = new RpcProvider( |
|
(message, transfer) => (transferLocalToRemote = transfer, remote.dispatch(message)), |
|
50 |
|
); |
|
|
|
local.error.addHandler(err => errorLocal = err); |
|
|
|
remote = new RpcProvider( |
|
(message, transfer) => (transferRemoteToLocal = transfer, local.dispatch(message)), |
|
50 |
|
); |
|
|
|
remote.error.addHandler(err => errorRemote = err); |
|
|
|
transferLocalToRemote = transferRemoteToLocal = undefined; |
|
errorRemote = errorLocal = undefined |
|
}); |
|
|
|
suite('signals', function() { |
|
|
|
test('Signals are propagated', function() { |
|
let x = -1; |
|
|
|
remote.registerSignalHandler('action', (value: number) => x = value); |
|
|
|
local.signal('action', 5); |
|
|
|
assert(!errorLocal); |
|
assert(!errorRemote); |
|
assert.strictEqual(x, 5); |
|
}); |
|
|
|
test('Unregistered signals raise an error', function() { |
|
local.signal('action', 10); |
|
|
|
assert(errorLocal); |
|
assert(errorRemote); |
|
}); |
|
|
|
test('Multiple signals do not interfere', function() { |
|
let x = -1, y = -1; |
|
|
|
remote.registerSignalHandler('setx', (value: number) => x = value); |
|
remote.registerSignalHandler('sety', (value: number) => y = value); |
|
|
|
local.signal('setx', 5); |
|
local.signal('sety', 6); |
|
|
|
assert(!errorLocal); |
|
assert(!errorRemote); |
|
assert.strictEqual(x, 5); |
|
assert.strictEqual(y, 6); |
|
}); |
|
|
|
test('Multiple handlers can be bound to one signal', function() { |
|
let x = -1; |
|
|
|
remote.registerSignalHandler('action', (value: number) => x = value); |
|
|
|
local.signal('action', 1); |
|
local.signal('action', 2); |
|
|
|
assert(!errorLocal); |
|
assert(!errorRemote); |
|
assert.strictEqual(x, 2); |
|
}); |
|
|
|
test('Handlers can be deregistered', function() { |
|
let x = -1; |
|
|
|
const handler = (value: number) => x = value; |
|
|
|
remote.registerSignalHandler('action', handler); |
|
remote.deregisterSignalHandler('action', handler); |
|
|
|
local.signal('action', 5); |
|
|
|
assert(!errorLocal); |
|
assert(!errorRemote); |
|
assert.strictEqual(x, -1); |
|
}); |
|
|
|
test('Transfer is honored', function() { |
|
let x = -1; |
|
const transfer = [1, 2, 3]; |
|
|
|
remote.registerSignalHandler('action', (value: number) => x = value); |
|
|
|
local.signal('action', 2, transfer); |
|
|
|
assert(!errorLocal); |
|
assert(!errorRemote); |
|
assert.strictEqual(x, 2); |
|
assert.strictEqual(transferLocalToRemote, transfer); |
|
assert(!transferRemoteToLocal); |
|
}); |
|
|
|
}); |
|
|
|
suite('RPC', function() { |
|
|
|
test('RPC handlers can return values', function() { |
|
remote.registerRpcHandler('action', () => 10); |
|
|
|
return local |
|
.rpc('action') |
|
.then(result => ( |
|
assert.strictEqual(result, 10), |
|
assert(!errorLocal), |
|
assert(!errorRemote) |
|
)); |
|
}); |
|
|
|
test('RPC handlers can return promises', function() { |
|
remote.registerRpcHandler('action', () => new Promise(r => setTimeout(() => r(10), 15))); |
|
|
|
return local |
|
.rpc('action') |
|
.then(result => ( |
|
assert.strictEqual(result, 10), |
|
assert(!errorLocal), |
|
assert(!errorRemote) |
|
)); |
|
}) |
|
|
|
test('Promise rejection is transferred', function() { |
|
remote.registerRpcHandler('action', () => new Promise((resolve, reject) => setTimeout(() => reject(10), 15))); |
|
|
|
return local |
|
.rpc('action') |
|
.then( |
|
() => Promise.reject('should have been rejected'), |
|
result => ( |
|
assert.strictEqual(result, 10), |
|
assert(!errorLocal), |
|
assert(!errorRemote) |
|
) |
|
); |
|
}); |
|
|
|
test('Invalid RPC calls are rejected', function() { |
|
return local |
|
.rpc('action') |
|
.then( |
|
() => Promise.reject('should have been rejected'), |
|
() => undefined |
|
); |
|
}); |
|
|
|
test('Invalid RPC calls throw on both ends', function() { |
|
return local |
|
.rpc('action') |
|
.then( |
|
() => Promise.reject('should have been rejected'), |
|
() => undefined |
|
) |
|
.then(() => ( |
|
assert(errorLocal), |
|
assert(errorRemote) |
|
)); |
|
}); |
|
|
|
test('RPC calls time out', function() { |
|
remote.registerRpcHandler('action', () => new Promise(r => setTimeout(() => r(10), 100))); |
|
|
|
return local |
|
.rpc('action') |
|
.then( |
|
() => Promise.reject('should have been rejected'), |
|
() => (assert(errorLocal), new Promise(r => setTimeout(r, 100))) |
|
) |
|
.then(() => assert(errorRemote)); |
|
}); |
|
|
|
test('Multiple RPC handlers do not interfere', function() { |
|
remote.registerRpcHandler('a1', (value: number) => new Promise(r => setTimeout(() => r(value), 30))); |
|
remote.registerRpcHandler('a2', (value: number) => 2 * value); |
|
|
|
return Promise |
|
.all([ |
|
local.rpc('a1', 10), |
|
local.rpc('a2', 20) |
|
]) |
|
.then(([r1, r2]) => ( |
|
assert.strictEqual(r1, 10), |
|
assert.strictEqual(r2, 40), |
|
assert(!errorLocal), |
|
assert(!errorRemote) |
|
)); |
|
}); |
|
|
|
test('RPC handler can be deregistered', function() { |
|
const handler = () => 10; |
|
|
|
remote.registerRpcHandler('action', handler); |
|
remote.deregisterRpcHandler('action', handler); |
|
|
|
return local |
|
.rpc('action') |
|
.then( |
|
() => Promise.reject('should have been rejected'), |
|
() => ( |
|
assert(errorLocal), |
|
assert(errorRemote) |
|
) |
|
); |
|
}); |
|
|
|
test('Transfer is honored', function() { |
|
const transfer = [1, 2, 3]; |
|
|
|
remote.registerRpcHandler('action', () => 10); |
|
|
|
return local |
|
.rpc('action', undefined, transfer) |
|
.then(x => ( |
|
assert.strictEqual(transferLocalToRemote, transfer), |
|
assert.strictEqual(x, 10), |
|
assert(!errorLocal), |
|
assert(!errorRemote) |
|
)); |
|
}); |
|
|
|
}); |
|
|
|
}); |