sen-ether-client 0.1.6 → 0.1.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/API.md +6 -1
- package/lib/discovery.js +42 -1
- package/package.json +1 -1
package/API.md
CHANGED
|
@@ -67,7 +67,12 @@ variable as its multicast default:
|
|
|
67
67
|
- `SEN_ETHER_DISCOVERY_PORT`
|
|
68
68
|
|
|
69
69
|
Multicast group, bind address and interface selection are explicit `sen-ether-client`
|
|
70
|
-
options, not SEN environment variables.
|
|
70
|
+
options, not SEN environment variables. When no `interfaceAddress` is provided,
|
|
71
|
+
multicast discovery joins every local IPv4 interface visible to Node.js. If a
|
|
72
|
+
SEN producer on the same host sends discovery through a physical interface that
|
|
73
|
+
does not loop multicast packets back locally, discovery can still return no
|
|
74
|
+
processes; in that case run the producer discovery on `lo`, pass the matching
|
|
75
|
+
`interfaceAddress`, or use SEN TCP discovery.
|
|
71
76
|
|
|
72
77
|
Preferred multi-session usage:
|
|
73
78
|
|
package/lib/discovery.js
CHANGED
|
@@ -50,6 +50,26 @@ function resolveInterfaceAddress(value) {
|
|
|
50
50
|
return ipv4.address;
|
|
51
51
|
}
|
|
52
52
|
|
|
53
|
+
function multicastInterfaceCandidates(interfaceAddress) {
|
|
54
|
+
if (interfaceAddress) {
|
|
55
|
+
return [interfaceAddress];
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
try {
|
|
59
|
+
const addresses = [];
|
|
60
|
+
for (const candidates of Object.values(os.networkInterfaces())) {
|
|
61
|
+
for (const item of candidates ?? []) {
|
|
62
|
+
if ((item.family === 'IPv4' || item.family === 4) && item.address) {
|
|
63
|
+
addresses.push(item.address);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return [...new Set(addresses)];
|
|
68
|
+
} catch {
|
|
69
|
+
return [];
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
53
73
|
function normalizeTcpRemote(socket) {
|
|
54
74
|
return {
|
|
55
75
|
address: socket.remoteAddress,
|
|
@@ -149,8 +169,29 @@ export class EtherDiscoveryScanner extends EventEmitter {
|
|
|
149
169
|
const onListening = () => {
|
|
150
170
|
socket.off('error', onError);
|
|
151
171
|
try {
|
|
152
|
-
|
|
172
|
+
const interfaces = multicastInterfaceCandidates(this.interfaceAddress);
|
|
173
|
+
if (interfaces.length) {
|
|
174
|
+
let joined = 0;
|
|
175
|
+
/** @type {Error | undefined} */
|
|
176
|
+
let firstError;
|
|
177
|
+
for (const interfaceAddress of interfaces) {
|
|
178
|
+
try {
|
|
179
|
+
socket.addMembership(this.group, interfaceAddress);
|
|
180
|
+
joined += 1;
|
|
181
|
+
} catch (error) {
|
|
182
|
+
firstError ??= /** @type {Error} */ (error);
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
if (!joined) {
|
|
186
|
+
throw firstError ?? new Error(`could not join multicast group ${this.group}`);
|
|
187
|
+
}
|
|
188
|
+
} else {
|
|
189
|
+
socket.addMembership(this.group);
|
|
190
|
+
}
|
|
153
191
|
socket.setMulticastLoopback(true);
|
|
192
|
+
if (this.interfaceAddress) {
|
|
193
|
+
socket.setMulticastInterface(this.interfaceAddress);
|
|
194
|
+
}
|
|
154
195
|
} catch (error) {
|
|
155
196
|
reject(error);
|
|
156
197
|
return;
|