Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: use rxjs to send messages within coordinator host #ADEN-9976
feat: use connector instead of host chore: change interface fix: fix native connector chore: fix coordinator spec chore: fix channel spec chore: check connector in channel spec chore: fix receiver spec chore: add connector factory spec chore: add native connector spec chore: add post message connector spec chore: remove coverage check from host.ts chore: update dependencies chore: change operators to functions chore: change lite transmitter constructor chore: fix @types/node version chore: export lite transmitter chore: fix setup chore: fix channel chore: add methods for sending and receiving messages chore: use methods for sending and receiving messages chore: create sender and listener chore: add listener/sender memoization chore: fix channel spec chore: fix receiver spec chore: remove connector chore: add isRxMode spec chore: handle not serializable messages chore: update setup spec chore: update transmitter spec chore: remove lite transmitter chore: remove experimental decorators
- Loading branch information
Showing
38 changed files
with
4,775 additions
and
4,597 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,11 +1,9 @@ | ||
{ | ||
"*.ts": [ | ||
"prettier --write", | ||
"tslint --fix", | ||
"git add" | ||
"tslint --fix" | ||
], | ||
"*.{js,json,css,scss,html}": [ | ||
"prettier --write", | ||
"git add" | ||
"prettier --write" | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Large diffs are not rendered by default.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
import { createHostStub } from '../models/host.stub'; | ||
import { isRxMode } from './is-rx-mode'; | ||
|
||
describe('isRxMode', () => { | ||
const host1 = createHostStub(); | ||
const host2 = createHostStub(); | ||
|
||
it('should return true', () => { | ||
expect(isRxMode({ host: host1, coordinatorHost: host1 })); | ||
}); | ||
|
||
it('should return false', () => { | ||
expect(isRxMode({ host: host1, coordinatorHost: host2 })); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
import { LIB_SUBJECT } from '../models/constants'; | ||
import { PostQuecastOptions } from '../models/options'; | ||
|
||
export function isRxMode(options: Pick<PostQuecastOptions, 'host' | 'coordinatorHost'>): boolean { | ||
return options.host === options.coordinatorHost && !!options.coordinatorHost[LIB_SUBJECT]; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,79 @@ | ||
import { LIB_ID, LIB_SUBJECT } from '../models/constants'; | ||
import { createHostStub, HostStub } from '../models/host.stub'; | ||
import { PostMessageData } from '../models/post-message-data'; | ||
import { PostMessageEvent } from '../models/post-message-event'; | ||
import { Listener, NativeListener, RxListener } from './listener'; | ||
|
||
describe('Listener', () => { | ||
let host1: HostStub; | ||
let host2: HostStub; | ||
|
||
beforeEach(() => { | ||
host1 = createHostStub(); | ||
host2 = createHostStub(); | ||
}); | ||
|
||
it('should create rx listener if the same host', () => { | ||
const spy = jest.spyOn(RxListener, 'make'); | ||
const instance = Listener.make({ coordinatorHost: host1, host: host1 }); | ||
|
||
expect(instance instanceof RxListener).toBe(true); | ||
expect(spy).toHaveBeenCalledTimes(1); | ||
expect(spy).toHaveBeenCalledWith(host1); | ||
}); | ||
|
||
it('should create native listener different hosts', () => { | ||
const spy = jest.spyOn(NativeListener, 'make'); | ||
const instance = Listener.make({ coordinatorHost: host1, host: host2 }); | ||
|
||
expect(instance instanceof NativeListener).toBe(true); | ||
expect(spy).toHaveBeenCalledTimes(1); | ||
expect(spy).toHaveBeenCalledWith(host2); | ||
}); | ||
|
||
describe('RxListener', () => { | ||
it('should receive messages from host subject', () => { | ||
const rxListener = RxListener.make(host1); | ||
const results: PostMessageEvent[] = []; | ||
|
||
rxListener.messages$.subscribe(value => results.push(value)); | ||
host1[LIB_SUBJECT].next(makeMessage('test1')); | ||
host1[LIB_SUBJECT].next(makeMessage('test2')); | ||
host1[LIB_SUBJECT].next('invalid' as any); | ||
|
||
expect(results.length).toBe(2); | ||
expect(results.map(result => result.data.action.type)).toEqual(['test1', 'test2']); | ||
}); | ||
}); | ||
|
||
describe('NativeListener', () => { | ||
it('should receive messages from host subject', () => { | ||
const nativeListener = NativeListener.make(host1); | ||
const results: PostMessageEvent[] = []; | ||
|
||
nativeListener.messages$.subscribe(value => results.push(value)); | ||
host1.postMessage(makeMessageData('test1'), '*'); | ||
host1.postMessage(makeMessageData('test2'), '*'); | ||
host1.postMessage('invalid', '*'); | ||
|
||
expect(results.length).toBe(2); | ||
expect(results.map(result => result.data.action.type)).toEqual(['test1', 'test2']); | ||
}); | ||
}); | ||
|
||
function makeMessage(type: string): PostMessageEvent { | ||
return { | ||
data: makeMessageData(type), | ||
source: host1, | ||
}; | ||
} | ||
|
||
function makeMessageData(type: string): PostMessageData { | ||
return { | ||
action: { type, timestamp: 10 }, | ||
channelId: 'default', | ||
libId: LIB_ID, | ||
private: true, | ||
}; | ||
} | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
import { Subject } from 'rxjs'; | ||
import { PostMessageEvent } from '../models/post-message-event'; | ||
|
||
export type ListenerStub = { | ||
messages$: Subject<PostMessageEvent>; | ||
}; | ||
|
||
export function createListenerStub(): ListenerStub { | ||
return { | ||
messages$: new Subject(), | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
/* tslint:disable:max-classes-per-file */ | ||
import { fromEvent, Observable } from 'rxjs'; | ||
import { LIB_SUBJECT } from '../models/constants'; | ||
import { Host } from '../models/host'; | ||
import { PostQuecastOptions } from '../models/options'; | ||
import { PostMessageEvent } from '../models/post-message-event'; | ||
import { onlyValidMessages } from '../rxjs/only-valid-messages'; | ||
import { isRxMode } from './is-rx-mode'; | ||
|
||
export abstract class Listener { | ||
static make(options: Pick<PostQuecastOptions, 'host' | 'coordinatorHost'>): Listener { | ||
if (isRxMode(options)) { | ||
return RxListener.make(options.coordinatorHost); | ||
} | ||
|
||
return NativeListener.make(options.host); | ||
} | ||
|
||
messages$: Observable<PostMessageEvent>; | ||
} | ||
|
||
export class RxListener implements Listener { | ||
static make(host: Host): RxListener { | ||
return new RxListener(host); | ||
} | ||
|
||
readonly messages$: Observable<PostMessageEvent>; | ||
|
||
private constructor(host: Host) { | ||
this.messages$ = host[LIB_SUBJECT].asObservable().pipe(onlyValidMessages()); | ||
} | ||
} | ||
|
||
export class NativeListener implements Listener { | ||
static make(host: Host): NativeListener { | ||
return new NativeListener(host); | ||
} | ||
|
||
readonly messages$: Observable<PostMessageEvent>; | ||
|
||
private constructor(host: Host) { | ||
this.messages$ = fromEvent(host, 'message').pipe(onlyValidMessages()); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
import { LIB_ID, LIB_SUBJECT } from '../models/constants'; | ||
import { createHostStub, HostStub } from '../models/host.stub'; | ||
import { PostMessageData } from '../models/post-message-data'; | ||
import { PostMessageEvent } from '../models/post-message-event'; | ||
import { NativeSender, RxSender, Sender } from './sender'; | ||
|
||
describe('Sender', () => { | ||
let host1: HostStub; | ||
let host2: HostStub; | ||
|
||
beforeEach(() => { | ||
host1 = createHostStub(); | ||
host2 = createHostStub(); | ||
}); | ||
|
||
it('should create RxSender if the same host', () => { | ||
const spy = jest.spyOn(RxSender, 'make'); | ||
const instance = Sender.make({ coordinatorHost: host1, host: host1 }); | ||
|
||
expect(instance instanceof RxSender).toBe(true); | ||
expect(spy).toHaveBeenCalledTimes(1); | ||
expect(spy).toHaveBeenCalledWith(host1); | ||
}); | ||
|
||
it('should create NativeSender different hosts', () => { | ||
const spy = jest.spyOn(NativeSender, 'make'); | ||
const instance = Sender.make({ coordinatorHost: host1, host: host2 }); | ||
|
||
expect(instance instanceof NativeSender).toBe(true); | ||
expect(spy).toHaveBeenCalledTimes(1); | ||
expect(spy).toHaveBeenCalledWith(host1); | ||
}); | ||
|
||
describe('RxSender', () => { | ||
it('should send messages through host', () => { | ||
const message1 = makeMessageData('test1'); | ||
const message2 = makeMessageData('test2'); | ||
const rxSender = RxSender.make(host1); | ||
const results: PostMessageEvent[] = []; | ||
|
||
host1[LIB_SUBJECT].subscribe(value => results.push(value)); | ||
|
||
rxSender.postMessage(message1); | ||
rxSender.postMessage(message2); | ||
|
||
expect(results.length).toBe(2); | ||
expect(results.map(result => result.data.action.type)).toEqual(['test1', 'test2']); | ||
expect(results[0].source).toBe(results[1].source); | ||
expect(results[0].source).toBe(host1); | ||
}); | ||
}); | ||
|
||
describe('NativeSender', () => { | ||
it('should send messages through host', () => { | ||
const message1 = makeMessageData('test1'); | ||
const message2 = makeMessageData('test2'); | ||
const nativeSender = NativeSender.make(host1); | ||
|
||
nativeSender.postMessage(message1); | ||
expect(host1.postMessage).toHaveBeenCalledTimes(1); | ||
expect(host1.postMessage).toHaveBeenCalledWith(message1, '*'); | ||
|
||
host1.postMessage.mockClear(); | ||
|
||
nativeSender.postMessage(message2); | ||
expect(host1.postMessage).toHaveBeenCalledTimes(1); | ||
expect(host1.postMessage).toHaveBeenCalledWith(message2, '*'); | ||
}); | ||
|
||
it('should fail silently so that not serializable messages pass', () => { | ||
const nativeSender = NativeSender.make(host1); | ||
|
||
host1.postMessage.mockImplementation(() => { | ||
throw new Error(); | ||
}); | ||
nativeSender.postMessage(makeMessageData('test')); | ||
}); | ||
}); | ||
|
||
function makeMessageData(type: string): PostMessageData { | ||
return { | ||
action: { type, timestamp: 10 }, | ||
channelId: 'default', | ||
libId: LIB_ID, | ||
private: true, | ||
}; | ||
} | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
import { Sender } from './sender'; | ||
|
||
export type SenderStub = { | ||
[key in keyof Sender]: jest.SpyInstance & Sender[key]; | ||
}; | ||
|
||
export function createSenderStub(): SenderStub { | ||
return { | ||
postMessage: jest.fn(), | ||
}; | ||
} |
Oops, something went wrong.