// // NetworkServiceHandler.m // OneCable // // Created by Jason Lee on 2/15/16. // Copyright © 2016 ntels. All rights reserved. // #import "JDObject.h" #import "NetworkServiceHandler.h" #import "Reachability.h" #import "NSString-Addtions.h" #import "NSNetService+Util.h" @interface NetworkServiceHandler () { NSNetServiceBrowser *_netServiceBrowser; BOOL _isNotFirstLoading; Reachability *_reachability; NSMutableArray* _services; } @property (strong, nonatomic) NSNetService *netService; @end @implementation NetworkServiceHandler - (BOOL)startSearchBonjourServices { NSLog(@"currentReachabilityStatus= %zd", _reachability.currentReachabilityStatus); // _isNotFirstLoading = NO; if (_reachability.currentReachabilityStatus != ReachableViaWiFi) { return NO; } //1.check if wifi // if (_netServiceBrowser) { // [_netServiceBrowser stop]; // _netServiceBrowser = nil; // } NSString *browseType; if (!_netService) { _netServiceBrowser = [[NSNetServiceBrowser alloc] init]; _netServiceBrowser.delegate = self; _services = [[NSMutableArray alloc] init]; // browseType = @"_services._dns-sd._udp."; browseType = @"_ntelshub._tcp."; // browseType = @"_ntelshub._tcp.local."; NSLog(@"Serch BrowseType : %@", browseType); [_netServiceBrowser searchForServicesOfType:browseType inDomain:@""]; } else { [self publishNetService]; } return YES; } - (void)stopSearchBonjourServices{ if (_netServiceBrowser) { [_netServiceBrowser stop]; _netServiceBrowser = nil; } if(_netService) { [_netService stop]; _netService = nil; } } - (void)publishNetService { NSLog(@"%@", [JDFacade facade].deviceHostName); if (!_netService) { _netService = [[NSNetService alloc] initWithDomain:@"" type:@"_ntelshub._tcp" name:[JDFacade facade].deviceHostName port:7979]; _netService.delegate = self; } if (_netService) { [_netService publish]; } else { NSLog(@"An error occurred initializing the NSNetService object."); } } #pragma mark - NSNetServiceDelegate methods - (void)netServiceBrowser:(NSNetServiceBrowser *)browser didFindService:(NSNetService *)service moreComing:(BOOL)moreComing { /* 현재 안드로이드에서 MDNS통해서 수집하는 정보는 manufacturer, modelNumber, serialNumber, profileVersion, hostAddress 입니다. */ [service setDelegate:self]; [service resolveWithTimeout:0.0]; [_services addObject:service]; // NSMutableDictionary *info = [NSMutableDictionary dictionary]; // NSDictionary* dict = [NSNetService dictionaryFromTXTRecordData:[service TXTRecordData]]; // info[@"name"] = service.name; // info[@"domain"] = service.domain; // info[@"type"] = service.type; // info[@"hostName"] = service.hostName; // info[@"Data"] = service.type; // info[@"Address"] = service.addresses; //// info[@"port"] = service.port; // NSLog(@"Finish : %@", info ); // NSLog(@"Info : %@", dict ); // // if (!moreComing) // { // [self chkServiceData]; // } // if (!_isNotFirstLoading) { [self publishNetService]; _isNotFirstLoading = YES; } } -(void)chkServiceData { for (NSNetService *service in _services) { NSMutableDictionary *info = [NSMutableDictionary dictionary]; info[@"name"] = service.name; info[@"domain"] = service.domain; info[@"type"] = service.type; info[@"hostName"] = service.hostName; info[@"Data"] = service.type; info[@"Address"] = service.addresses; NSLog(@"Service : %@", info ); NSDictionary* dict = [NSNetService dictionaryFromTXTRecordData:[service TXTRecordData]]; NSLog(@"Service TXT : %@", dict ); } } - (void)netServiceDidPublish:(NSNetService *)sender { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, sender); // if (self.delegate && [self.delegate respondsToSelector:@selector(didSucceedPublishService)]) { // [self.delegate didSucceedPublishService]; // } if (self.delegate && [self.delegate respondsToSelector:@selector(didSucceedPublishService:)]) { [self.delegate didSucceedPublishService:_services]; } } - (void)netServiceWillPublish:(NSNetService *)sender { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, sender); } - (void)netServiceDidStop:(NSNetService *)sender { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, sender); } - (void)netService:(NSNetService *)sender didAcceptConnectionWithInputStream:(NSInputStream *)inputStream outputStream:(NSOutputStream *)outputStream { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, sender); } - (void)netService:(NSNetService *)sender didNotPublish:(NSDictionary *)errorDict { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, errorDict); if (self.delegate && [self.delegate respondsToSelector:@selector(didFailPublishService:)]) { [self.delegate didFailPublishService:errorDict]; } } - (void)netService:(NSNetService *)sender didNotResolve:(NSDictionary *)errorDict { NSLog(@"%s\n %@", __PRETTY_FUNCTION__, sender); NSNumber *errorCode = [errorDict valueForKey:NSNetServicesErrorCode]; switch ([errorCode intValue]) { case NSNetServicesActivityInProgress: NSLog(@"%s\n %@", __PRETTY_FUNCTION__, @"Service Resolution Currently in Progress. Please Wait."); break; case NSNetServicesTimeoutError: NSLog(@"%s\n %@", __PRETTY_FUNCTION__, @"Service Resolution Currently in Progress. Please Wait."); //service stop [sender stop]; if (self.delegate && [self.delegate respondsToSelector:@selector(didFailPublishService:)]) { [self.delegate didFailPublishService:errorDict]; } break; } } - (void)netServiceDidResolveAddress:(NSNetService *)service { NSDictionary* dict = [NSNetService dictionaryFromTXTRecordData:[service TXTRecordData]]; /* manufacturer = <4e54656c 73>; "model_number" = <53544248 55427633>; "profile_version" = <7633>; "serial_number" = <30383632 36363064 30633935>; */ NSMutableDictionary *info = [NSMutableDictionary dictionary]; info[@"name"] = service.name; info[@"domain"] = service.domain; info[@"type"] = service.type; info[@"hostName"] = service.hostName; info[@"Data"] = service.type; // info[@"Address"] = service.addressesAndPorts; for (AddressAndPort *addrInfo in service.addressesAndPorts) { NSLog(@"ADDR : %@", addrInfo.address); } for (NSString *key in dict.allKeys) NSLog(@"[%@] : %@", key,[NSString stringWithUTF8Data:[dict objectForKey:key]]); } #pragma mark - Reachability Notification - (void)netReachabilityChanged:(id)notification { if (_reachability.currentReachabilityStatus == ReachableViaWiFi) { NSLog(@"%s\n currentReachabilityStatus = %zd", __PRETTY_FUNCTION__, _reachability.currentReachabilityStatus); [self performSelectorInBackground:@selector(startSearchBonjourServices) withObject:nil]; } } - (void)dealloc { NSLog(@"%s", __PRETTY_FUNCTION__); [[NSNotificationCenter defaultCenter] removeObserver:self forKeyPath:kReachabilityChangedNotification]; [_reachability stopNotifier]; [_netServiceBrowser stop]; } #pragma mark - Singleton + (NetworkServiceHandler *)handler { static NetworkServiceHandler *sharedNetworkServiceHandler = nil; static dispatch_once_t onceToken; dispatch_once(&onceToken, ^{ sharedNetworkServiceHandler = [[self alloc] init]; }); return sharedNetworkServiceHandler; } - (id)init { if (self = [super init]) { [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(netReachabilityChanged:) name:kReachabilityChangedNotification object:nil]; _reachability = [Reachability reachabilityForLocalWiFi]; [_reachability startNotifier]; } return self; } @end