Node.js 通过网络的 UDP 多播

Node.js UDP Multicast over Network

我遇到了关于 UDP 多播概念验证的重复 EADDRNOTAVAIL 问题。我有一个 Linux 服务器向 Windows 客户端发送多播消息(已尝试将其逆转无济于事..)。当 运行 客户端和服务器在同一台机器上,但不是在 same 网络上时,服务器工作正常。

下面是我尝试使用的代码、我正在使用的 IP 以及我收到的错误。

我不确定我做错了什么!


环境

Windows本地IP:192.168.1.10
Linux本地IP:192.168.1.11

服务器:server.js

const SRC_PORT = 6025;
const PORT = 6024;
const MULTICAST_ADDR = '239.255.255.250';
const LOCAL_IP = '192.168.1.11';
const dgram = require('dgram');
const server = dgram.createSocket("udp4");

server.bind(SRC_PORT, LOCAL_IP, function () {
  setInterval(function () {
    let message = new Buffer(new Date().toLocaleTimeString());
    server.send(message, 0, message.length, PORT, MULTICAST_ADDR, function () {
      console.log("Sent '" + message + "'");
    });
  }, 4000);
});


客户:client.js

const PORT = 6024;
const MULTICAST_ADDR = '239.255.255.250';
const LOCAL_IP = '192.168.1.10';
const HOST_IP = '192.168.1.11';
const dgram = require('dgram');
const client = dgram.createSocket('udp4');

client.on('listening', function () {
  let address = client.address();
  console.log('UDP Client listening on ' + address.address + ":" + address.port);
});

client.on('message', function (message, rinfo) {
  console.log('Message from: ' + rinfo.address + ':' + rinfo.port + ' - ' + message);
});

//*** Also tried with client.bind(PORT, LOCAL_IP, ... and failed
client.bind(PORT, function () {
  client.addMembership(MULTICAST_ADDR, HOST_IP);
});

错误

dgram.js:508
    throw errnoException(err, 'addMembership');
    ^

Error: addMembership EADDRNOTAVAIL
    at exports._errnoException (util.js:1026:11)
    at Socket.addMembership (dgram.js:508:11)
    at Socket.<anonymous> (~/dev/node-multicast/client.js:16:10)
    at Socket.g (events.js:286:16)
    at emitNone (events.js:91:20)
    at Socket.emit (events.js:185:7)
    at startListening (dgram.js:121:10)
    at dgram.js:228:7
    at _combinedTickCallback (internal/process/next_tick.js:77:11)

我确定您从这个错误中加入了错误的多播接口:

addMembership EADDRNOTAVAIL

应该是你的本地接口地址: client.addMembership(MULTICAST_ADDR, LOCAL_IP);

正如 doc 所说:

socket.addMembership(multicastAddress[, multicastInterface])
Tells the kernel to join a multicast group at the given multicastAddress and multicastInterface using the IP_ADD_MEMBERSHIP socket option. If the multicastInterface argument is not specified, the operating system will choose one interface and will add membership to it. To add membership to every available interface, call addMembership multiple times, once per interface.