Join MultiPeer Networks Automatically?

Hello,


I'm aware you can present the mcBrowser to the user in order to decide what network to join. However, I am looking for the capability to have a device join a network automatically. Specifically, a device should join a network (identified by PeerID) exactly once, receive a message from the host, and disconnect, never to connect to that PeerID again.


1) Is this behavior possible? If so, through what function(s)?

2) Any recommendations for how I should keep track of what PeerID's a device has seen previously?


Thanks!

Replies

Multipeer Connectivity is a fine API but it’s not the only way to access peer-to-peer networking. As a high-level API, it tends to be very ‘opinionated’, that is, the API wants you to use it in a specific way. Use Multipeer Connectivity when your requirements are well aligned with that design. If you find yourself fighting the framework, it’s better to use a lower-level API.

In your case, it sounds like you’d be better served by a Bonjour API, like

NSNetService
, and a TCP API, like
NWConnection
(or
NSStream
if you need to support older OS releases). These support peer-to-peer networking (make sure to set
includesPeerToPeer
to enable it) and their low-level nature makes them more appropriate for your needs.

For example, these APIs let you dictate the service name, so you can make it a UUID that you create yourself, which means you don’t have to worry about the exact behaviour of

MCPeerID
[1].

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"

[1] If you’re curious what that behaviour is, read this post.

Hi Eskimo,


Thanks for your input. I've done some reading through the NSNetService documentation but still have some holes in my understanding (I'm a total noob at iOS development).


A few follow-up questions:

1) Any particularities about where I should set includesPeerToPeer? The documentation only specifies before calling certain other functions-- is once at the beginning of the instance of the app alright?

2) Should I be using 'initWithDomain:type:name' to initialize my p2p network? If so, what domain should I be using?

3) How do I detect whether or not there exists a receiver and if so, deliver content to them? I see no such functionality in the documentation (the closest thing I see is publish, but I believe this is to advertise a service over the network to receivers? Should I be looking into what a 'service' is?).


Just for some further intuition: I like the way that MultiPeer has the device set up a network (if a bool is set), which other peers can then join. I'd like to mimic this functionality, except I'd like peers to be able to join these networks automatically (if a bool is set) without picking from a menu. Once a peer join a network, they should receive some contents from the host (Data) and then disconnect.

-> Any example code/resources you might be able to recommend towards this high-level goal is much appreciated.


Regards

If you’re looking for general guidance on Bonjour, check out the Bonjour Overview.

The key thing with Bonjour is that you shouldn’t think about networks but instead about services. Your app does not set up a peer-to-peer network, rather it publishes a service and various clients can browse for and connect to that service. In this design, Bonjour does not provide the actual networking — you can use any general-purpose networking API you like for that — but rather it providers the service discovery and advertising.

To answer your specific questions:

1) Any particularities about where I should set

includesPeerToPeer
?

Generally you know in advance whether you want to support peer-to-peer networking, in which case you should set this on your browser or service object immediately after creating it.

2) Should I be using 'initWithDomain:type:name' to initialize my p2p network? If so, what domain should I be using?

This question doesn’t make sense. In Bonjour you don’t “initialise a p2p network”, you register a service. If you set

includesPeerToPeer
, that service is discoverable over peer-to-peer networks.

Similarly, when you browser for or connect to a service, setting

includesPeerToPeer
allows those operations to occur over peer-to-peer networks.

3) How do I detect whether or not there exists a receiver and if so, deliver content to them?

There’s two common approaches for this:

  • The first time you connect you use a browser object (

    NSNetServiceBrowser
    ) to search for services of the right type. You present that list to the user, who can then choose their service.
  • Subsequently you can connect directly to that service (in Bonjour parlance this is the resolve operation, but I generally recommend that you a resolve-then-connect API).

However, Bonjour gives you a lot of flexibility here. For example:

  • If you never want to remember a service, you can present the browser every time.

  • If you’ve discovered the name and domain of a service via other means, you can connect without ever showing a browser.

Any example code/resources you might be able to recommend towards this high-level goal is much appreciated.

A good place to start is the WiTap sample code.

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"