Skip to content

Commit 7280c8a

Browse files
committed
Object inheritance in JS: so long and thanks for all the fish
1 parent 5662be4 commit 7280c8a

File tree

3 files changed

+49
-38
lines changed

3 files changed

+49
-38
lines changed

src/reader-writer.js renamed to src/daemon.js

Lines changed: 37 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,52 +1,65 @@
1-
import { Subject } from 'rxjs';
1+
import { Subject, BehaviorSubject } from 'rxjs';
22

3-
export default class ReaderWriter {
3+
export default class Daemon {
44
constructor() {
55
this.socket = null;
66
this.pluginURL = null;
7-
this.messageSubject = new Subject();
8-
this.serialMonitorSubject = new Subject();
9-
this.devicesList = {
7+
this.messageBus = new Subject();
8+
this.serialMonitor = new Subject();
9+
this.devicesList = new BehaviorSubject({
1010
serial: [],
1111
network: []
12-
};
13-
this.messageSubject.subscribe(this.updateDevicesList.bind(this));
12+
});
13+
this.messageBus.subscribe(this.updateDevicesList.bind(this));
1414
this.openingSerial = null;
1515
this.closingSerial = null;
1616
}
1717

18-
initSocket(socket) {
19-
this.socket = socket;
18+
initSocket() {
2019
this.socket.on('message', this.parseMessage.bind(this));
2120
}
2221

2322
initPluginUrl(pluginUrl) {
2423
this.pluginURL = pluginUrl;
2524
}
2625

26+
/**
27+
* Compares 2 devices list checking they contains the same ports in the same order
28+
* @param {Array<device>} a the first list
29+
* @param {Array<device>} b the second list
30+
*/
31+
static devicesListAreEquals(a, b) {
32+
if (!a || !b || a.length !== b.length) {
33+
return false;
34+
}
35+
return a.every((item, index) => b[index].Name === item.Name);
36+
}
37+
2738
updateDevicesList(devicesInfo) {
2839
// Result of a list command
2940
if (devicesInfo.Ports) {
30-
if (devicesInfo.Network) {
31-
this.devicesList.network = devicesInfo.Ports;
41+
const lastDevices = this.devicesList.getValue();
42+
if (devicesInfo.Network && !Daemon.devicesListAreEquals(lastDevices.network, devicesInfo.Ports)) {
43+
this.devicesList.next({
44+
serial: lastDevices.serial,
45+
network: devicesInfo.Ports
46+
});
3247
}
33-
else {
34-
this.devicesList.serial = devicesInfo.Ports;
48+
else if (!devicesInfo.Network && !Daemon.devicesListAreEquals(lastDevices.serial, devicesInfo.Ports)) {
49+
this.devicesList.next({
50+
serial: devicesInfo.Ports,
51+
network: lastDevices.network
52+
});
3553
}
3654
}
3755
}
3856

3957
parseMessage(message) {
40-
let jsonMessage;
4158
try {
42-
jsonMessage = JSON.parse(message);
59+
this.messageBus.next(JSON.parse(message));
4360
}
4461
catch (SyntaxError) {
45-
return;
46-
}
47-
48-
if (jsonMessage) {
49-
this.messageSubject.next(jsonMessage);
62+
this.messageBus.next(message);
5063
}
5164
}
5265

@@ -72,7 +85,7 @@ export default class ReaderWriter {
7285
return reject(new Error('Failed to open serial'));
7386
}
7487
};
75-
this.openSubscription = this.messageSubject.subscribe(checkOpen);
88+
this.openSubscription = this.messageBus.subscribe(checkOpen);
7689
}).finally(() => {
7790
this.openSubscription.unsubscribe();
7891
this.openingSerial = null;
@@ -105,7 +118,7 @@ export default class ReaderWriter {
105118
return reject(new Error('Failed to close serial'));
106119
}
107120
};
108-
this.closeSubscription = this.messageSubject.subscribe(checkClosed);
121+
this.closeSubscription = this.messageBus.subscribe(checkClosed);
109122
}).finally(() => {
110123
this.closeSubscription.unsubscribe();
111124
this.closingSerial = null;
@@ -117,11 +130,11 @@ export default class ReaderWriter {
117130
readSerial() {
118131
const onMessage = message => {
119132
if (message.D) {
120-
this.serialMonitorSubject.next(message.D);
133+
this.serialMonitor.next(message.D);
121134
}
122135
};
123136
if (!this.readSerialSubscription) {
124-
this.readSerialSubscription = this.messageSubject.subscribe(onMessage);
137+
this.readSerialSubscription = this.messageBus.subscribe(onMessage);
125138
}
126139
}
127140
}

src/socket-daemon.js

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ import {
3838
timer
3939
} from 'rxjs';
4040
import { filter, startWith, takeUntil } from 'rxjs/operators';
41-
import ReaderWriter from './reader-writer';
41+
import Daemon from './daemon';
4242

4343
// Required agent version
4444
const MIN_VERSION = '1.1.71';
@@ -62,19 +62,19 @@ if (browser.name !== 'chrome' && browser.name !== 'firefox') {
6262
orderedPluginAddresses = [LOOPBACK_HOSTNAME, LOOPBACK_ADDRESS];
6363
}
6464

65-
export default class SocketDaemon {
65+
export default class SocketDaemon extends Daemon {
6666
constructor() {
67+
super();
6768
this.selectedProtocol = PROTOCOL.HTTP;
6869
this.agentInfo = {};
6970
this.agentFound = new BehaviorSubject(false);
7071
this.wsConnected = new BehaviorSubject(false);
7172
this.error = new Subject();
72-
this.readerWriter = new ReaderWriter();
7373

7474
this.wsConnected
7575
.subscribe(wsConnected => {
7676
if (wsConnected) {
77-
this.readerWriter.initSocket(this.socket);
77+
this.initSocket();
7878
interval(POLLING_INTERVAL)
7979
.pipe(startWith(0))
8080
.pipe(takeUntil(this.wsConnected.pipe(filter(status => !status))))
@@ -135,7 +135,7 @@ export default class SocketDaemon {
135135
// Protocol http, force 127.0.0.1 for old agent versions too
136136
this.agentInfo[this.selectedProtocol] = this.agentInfo[this.selectedProtocol].replace('localhost', '127.0.0.1');
137137
}
138-
this.readerWriter.initPluginUrl(this.agentInfo[this.selectedProtocol]);
138+
this.initPluginUrl(this.agentInfo[this.selectedProtocol]);
139139
return true;
140140
}
141141
return false;

test/app.jsx

Lines changed: 7 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -38,15 +38,13 @@ class App extends React.Component {
3838

3939
this.daemon.error.subscribe(this.showError);
4040

41-
this.daemon.readerWriter.messageSubject.subscribe(() => {
42-
this.setState({
43-
serialDevices: this.daemon.readerWriter.devicesList.serial,
44-
networkDevices: this.daemon.readerWriter.devicesList.network
45-
});
46-
});
41+
this.daemon.devicesList.subscribe(devices => this.setState({
42+
serialDevices: devices.serial,
43+
networkDevices: devices.network
44+
}));
4745

4846
const serialTextarea = document.getElementById('serial-textarea');
49-
this.daemon.readerWriter.serialMonitorSubject.subscribe(message => {
47+
this.daemon.serialMonitor.subscribe(message => {
5048
this.setState({ serialMonitorContent: this.state.serialMonitorContent + message });
5149
scrollToBottom(serialTextarea);
5250
});
@@ -63,12 +61,12 @@ class App extends React.Component {
6361
handleOpen(e, port) {
6462
this.setState({ serialMonitorContent: '' });
6563
e.preventDefault();
66-
this.daemon.readerWriter.openSerialMonitor(port);
64+
this.daemon.openSerialMonitor(port);
6765
}
6866

6967
handleClose(e, port) {
7068
e.preventDefault();
71-
this.daemon.readerWriter.closeSerialMonitor(port);
69+
this.daemon.closeSerialMonitor(port);
7270
}
7371

7472
render() {

0 commit comments

Comments
 (0)