返回

设备发现协议mDNS详解,局域网设备通信利器

Android

局域网设备发现:mDNS,简化网络通信

在当今互联世界,我们比以往任何时候都更加依赖局域网连接。为了实现局域网设备之间的无缝通信,设备需要一种方法来互相发现。这就是多播域名系统 (mDNS) 协议发挥作用的地方。

什么是 mDNS?

mDNS 是一个用于局域网设备发现的协议。它允许设备在没有中央服务器的情况下自动发现彼此。这意味着,只要设备连接到同一个局域网,它们就可以互相通信,而无需预先配置任何网络设置。

mDNS 的工作原理

mDNS 协议的工作原理很简单:

  1. 设备发送一个包含自己名称和 IP 地址的多播数据包。
  2. 局域网上的其他设备收到这个数据包后,会将设备名称和 IP 地址添加到自己的缓存中。
  3. 当一个设备需要查找其他设备时,它会发送一个包含要查找的设备名称的多播数据包。
  4. 局域网上的其他设备收到这个数据包后,会将设备名称和 IP 地址发送给发送方。

mDNS 的优点

mDNS 协议有很多优点,包括:

  • 简单易用: mDNS 协议不需要任何复杂的配置,设备可以自动发现彼此。
  • 可扩展性强: mDNS 协议可以支持大量设备同时连接到局域网。
  • 可靠性高: mDNS 协议使用多播数据包,即使网络上存在故障,设备也可以互相发现。

使用 mDNS

为了便于大家使用 mDNS 协议,Java 提供了 jmdns 库,而 Android 系统也内置了 NSDManager 服务。

使用 jmdns 库

// 创建一个 JmDNS 实例
JmDNS jmdns = JmDNS.create(InetAddress.getLocalHost());

// 添加一个服务监听器
ServiceListener listener = new ServiceListener() {
    @Override
    public void serviceAdded(ServiceEvent event) {
        System.out.println("Service added: " + event.getInfo().getName());
    }

    @Override
    public void serviceRemoved(ServiceEvent event) {
        System.out.println("Service removed: " + event.getInfo().getName());
    }

    @Override
    public void serviceResolved(ServiceEvent event) {
        ServiceInfo info = event.getInfo();
        System.out.println("Service resolved: " + info.getName() + " " + info.getInetAddresses()[0] + " " + info.getPort());
    }
};
jmdns.addServiceListener("_http._tcp.local.", listener);

// 注册一个服务
ServiceInfo serviceInfo = ServiceInfo.create("_http._tcp.local.", "MyService", 8080, "This is my service");
jmdns.registerService(serviceInfo);

// 查找一个服务
ServiceInfo[] services = jmdns.list("_http._tcp.local.");
for (ServiceInfo service : services) {
    System.out.println("Service found: " + service.getName() + " " + service.getInetAddresses()[0] + " " + service.getPort());
}

// 停止 JmDNS 实例
jmdns.close();

使用 NSDManager 服务

// 创建一个 NsdManager 实例
NsdManager nsdManager = (NsdManager) context.getSystemService(Context.NSD_SERVICE);

// 注册一个服务
NsdServiceInfo serviceInfo = new NsdServiceInfo();
serviceInfo.setServiceName(serviceName);
serviceInfo.setPort(port);
nsdManager.registerService(serviceInfo, NsdManager.PROTOCOL_DNS_SD, new NsdManager.RegistrationListener() {
    @Override
    public void onRegistrationFailed(NsdServiceInfo serviceInfo, int errorCode) {
        System.out.println("Service registration failed: " + errorCode);
    }

    @Override
    public void onServiceRegistered(NsdServiceInfo serviceInfo) {
        System.out.println("Service registered: " + serviceInfo.getServiceName());
    }
});

// 发现一个服务
nsdManager.discoverServices(serviceType, NsdManager.PROTOCOL_DNS_SD, new NsdManager.DiscoveryListener() {
    @Override
    public void onStartDiscoveryFailed(String serviceType, int errorCode) {
        System.out.println("Service discovery failed: " + errorCode);
    }

    @Override
    public void onStopDiscoveryFailed(String serviceType, int errorCode) {
        System.out.println("Service discovery stopped: " + errorCode);
    }

    @Override
    public void onServiceFound(NsdServiceInfo serviceInfo) {
        System.out.println("Service found: " + serviceInfo.getServiceName());
    }

    @Override
    public void onServiceLost(NsdServiceInfo serviceInfo) {
        System.out.println("Service lost: " + serviceInfo.getServiceName());
    }
});

// 停止发现服务
nsdManager.stopServiceDiscovery(new NsdManager.DiscoveryListener() {
    @Override
    public void onStartDiscoveryFailed(String serviceType, int errorCode) {
        System.out.println("Service discovery failed: " + errorCode);
    }

    @Override
    public void onStopDiscoveryFailed(String serviceType, int errorCode) {
        System.out.println("Service discovery stopped: " + errorCode);
    }

    @Override
    public void onServiceFound(NsdServiceInfo serviceInfo) {
        System.out.println("Service found: " + serviceInfo.getServiceName());
    }

    @Override
    public void onServiceLost(NsdServiceInfo serviceInfo) {
        System.out.println("Service lost: " + serviceInfo.getServiceName());
    }
});

常见问题解答

  • 什么是局域网设备发现?
    局域网设备发现是指允许局域网上的设备自动互相发现的方法。

  • mDNS 如何工作?
    mDNS 使用多播数据包在局域网设备之间广播设备名称和 IP 地址。

  • mDNS 有哪些优点?
    mDNS 的优点包括简单易用、可扩展性强和可靠性高。

  • 如何使用 mDNS?
    可以使用 jmdns 库或 Android 系统中的 NSDManager 服务来使用 mDNS。

  • mDNS 可以用来做什么?
    mDNS 可用于发现各种设备,例如打印机、媒体流设备和智能家居设备。