Titanium JIRA Archive
Titanium SDK/CLI (TIMOB)

[TIMOB-28077] iOS14: Expose new error type in Bonjure Service and update doc to align with Local n/w privacy restrictions

GitHub Issuen/a
TypeImprovement
PriorityHigh
StatusClosed
ResolutionFixed
Resolution Date2020-09-11T18:31:13.000+0000
Affected Version/sn/a
Fix Version/sRelease 9.2.0
ComponentsiOS
Labelsbonjour, iOS
ReporterVijay Singh
AssigneeVijay Singh
Created2020-08-11T19:39:28.000+0000
Updated2020-09-11T18:31:13.000+0000

Description

In iOS 14, Apple has put restriction on accessing local network. It requires user permission. To show the prompt developer need to add key [NSLocalNetworkUsageDescription](https://developer.apple.com/documentation/bundleresources/information_property_list/nslocalnetworkusagedescription?language=objc) in tiapp.xml and if using Bonjure Service, that need to be added in info.plist using key [NSBonjourServices ](https://developer.apple.com/documentation/bundleresources/information_property_list/nsbonjourservices) . More detail can be found in WWDC video https://developer.apple.com/videos/play/wwdc2020/10110/. In iOS 14, new error [constant](https://developer.apple.com/documentation/foundation/nsnetserviceserror/nsnetservicesmissingrequiredconfigurationerror?language=objc) is given. In titanium, it need to added in Ti.Network.BonjureService and expose as error string.

Comments

  1. Vijay Singh 2020-08-11

    Test Case -
       var win = Ti.UI.createWindow({
       	backgroundColor: 'white'
       });
       
       var label = Ti.UI.createLabel({
       	top: 150,
       	text: 'Publish Service'
       });
       
       label.addEventListener('click', function(e) {
       	// Create the Bonjour Service
       	var localService = Ti.Network.createBonjourService({
       	  name: 'example',
       	  type: '_test._tcp',
       	  domain: 'local.'
       	});
       
       	// Create the socket we'll tie to the service
       	var hostname = Ti.Platform.address;
       	var bonjourSocket = Ti.Network.Socket.createTCP({
       	  host: hostname,
       	  port: 40404,
       	  accepted: function (e) {
       	  	alert("Listening socket <" + e.socket + "> accepted incoming connection <" + e.inbound + ">");
       	    Ti.API.info("Listening socket <" + e.socket + "> accepted incoming connection <" + e.inbound + ">");
       	    e.inbound.write(Ti.createBuffer({
       	      value: 'You have been connected to a listening socket.\r\n'
       	    }));
       	    e.inbound.close();
       	  },
       	  error: function (e) {
       	  	alert("Socket <" + e.socket + "> encountered error when listening");
       	    Ti.API.error("Socket <" + e.socket + "> encountered error when listening");
       	    Ti.API.error(" error code <" + e.errorCode + ">");
       	    Ti.API.error(" error description <" + e.error + ">");
       	  }
       	});
       
       	bonjourSocket.listen();
       
       	bonjourSocket.accept({ timeout: 10000 });
       
       	localService.publish(bonjourSocket, function (err, success) {
       		if (!success) {
       			alert('Service publish failed:' +err.message);
       		} else {
       			alert('Service published successfully');
       		}
       	});	
       });
       
       win.add(label);
       
       var searchLabel = Ti.UI.createLabel({
       	top: 300,
       	text: 'Start Searching'
       });
        
       searchLabel.addEventListener('click', function(e) {
        
       	var httpBonjourBrowser = Ti.Network.createBonjourBrowser({
       	  serviceType: '_test._tcp',
       	  domain: 'local.'
       	});
        
       	httpBonjourBrowser.addEventListener('updatedservices', function (e) {
       	  for (var service of e.services) {
       	      service.resolve(120, (err, success) => {
       	        console.log(service.socket);
       	        console.log(service.socket.port);
       	        console.log(service.socket.host);
       	      });
       	  }
       
       	  alert('success')
       	});
        
       	// Start searching
       	httpBonjourBrowser.search();
       });
       
       win.add(searchLabel);
       win.open();
       
    How to Test - 1. Create an app using and add mentioned test case. 2. Run it on device with iOS 14. 3. Click on 'Publish Service'. It should show error in alert. 4. Add key 'NSLocalNetworkUsageDescription' and key 'NSBonjourServices' in tiapp.xml (see the doc). Run again. 5. Click on 'Publish Service'. It should show prompt to ask user permission. On click of 'Ok', it should show success alert. 6. Click on 'Start Searching', it should show success alert. 7. Delete the app from mobile. Remove the added keys from tiapp.xml. 8. Run again. 9. Click on 'Start Searching'. It should throw exception. 10. Add keys again as mentioned in step 4. 11. Run again. It should show prompt to ask user permission. Click 'Ok'. It should not throw exception.
  2. Vijay Singh 2020-08-12

    PR - https://github.com/appcelerator/titanium_mobile/pull/11896
  3. Satyam Sekhri 2020-08-28

    FR Passed. Waiting for Jenkins build
  4. Satyam Sekhri 2020-09-11

    Verified on: Mac OS: 10.15.4 SDK: 9.2.0.v20200911073932, 9.3.0.v20200911052140 Appc CLI: 8.1.0 JDK: 11.0.4 Node: 10.17.0 Studio: 6.0.0.202005141803 Xcode: 12.0 Beta6 iPhone 7Plus(v14.0 Beta6)

JSON Source