Summary: JS/TS api: - migrate to TS - some refactoring (get rid of bridge, make client abstract) Implementation isn't full yet, things to be implemented: - let plugins connect on init command from Flipper - implement Responder Further plans: - make fully compatible with react-native api without breaking changes Reviewed By: mweststrate Differential Revision: D21839377 fbshipit-source-id: 9e9fe4ad01632f958b59eb255c703c6cbc5fafe2
83 lines
2.3 KiB
TypeScript
83 lines
2.3 KiB
TypeScript
/**
|
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
*
|
|
* This source code is licensed under the MIT license found in the
|
|
* LICENSE file in the root directory of this source tree.
|
|
*
|
|
* @format
|
|
*/
|
|
|
|
import {FlipperClientConnection} from '../../Client';
|
|
import {Flowable, Single} from 'rsocket-flowable';
|
|
import {Payload, ConnectionStatus, ISubscriber} from 'rsocket-types';
|
|
import WebSocket from 'ws';
|
|
|
|
export class WebsocketClientFlipperConnection<M>
|
|
implements FlipperClientConnection<string, M> {
|
|
websocket: WebSocket;
|
|
connStatusSubscribers: Set<ISubscriber<ConnectionStatus>> = new Set();
|
|
connStatus: ConnectionStatus;
|
|
app: string;
|
|
plugins: string[] = [];
|
|
|
|
constructor(ws: WebSocket, app: string, plugins: string[]) {
|
|
this.websocket = ws;
|
|
this.connStatus = {kind: 'CONNECTED'};
|
|
this.app = app;
|
|
this.plugins = plugins;
|
|
}
|
|
|
|
connectionStatus(): Flowable<ConnectionStatus> {
|
|
return new Flowable<ConnectionStatus>((subscriber) => {
|
|
subscriber.onSubscribe({
|
|
cancel: () => {
|
|
this.connStatusSubscribers.delete(subscriber);
|
|
},
|
|
request: (_) => {
|
|
this.connStatusSubscribers.add(subscriber);
|
|
subscriber.onNext(this.connStatus);
|
|
},
|
|
});
|
|
});
|
|
}
|
|
|
|
close(): void {
|
|
this.connStatus = {kind: 'CLOSED'};
|
|
this.connStatusSubscribers.forEach((subscriber) => {
|
|
subscriber.onNext(this.connStatus);
|
|
});
|
|
this.websocket.send(JSON.stringify({type: 'disconnect', app: this.app}));
|
|
}
|
|
|
|
fireAndForget(payload: Payload<string, M>): void {
|
|
this.websocket.send(
|
|
JSON.stringify({
|
|
type: 'send',
|
|
app: this.app,
|
|
payload: payload.data != null ? payload.data : {},
|
|
}),
|
|
);
|
|
}
|
|
|
|
// TODO: fully implement and return actual result
|
|
requestResponse(payload: Payload<string, M>): Single<Payload<string, M>> {
|
|
return new Single((subscriber) => {
|
|
const method =
|
|
payload.data != null ? JSON.parse(payload.data).method : 'not-defined';
|
|
subscriber.onSubscribe(() => {});
|
|
if (method != 'getPlugins') {
|
|
this.fireAndForget(payload);
|
|
}
|
|
subscriber.onComplete(
|
|
method == 'getPlugins'
|
|
? {
|
|
data: JSON.stringify({
|
|
success: {plugins: this.plugins},
|
|
}),
|
|
}
|
|
: {data: JSON.stringify({success: null})},
|
|
);
|
|
});
|
|
}
|
|
}
|