我需要以编程方式检测 iphone 是否连接到 VPN。我正在开发一个尝试加载 URL 的应用程序,此页面仅在设备连接到 VPN 时打开。在加载此 URL 之前,我需要检查 VPN 连接。我尝试了以下。但这并没有按预期工作。
- (BOOL)checkForVPNConnectivity {
NSDictionary *dict = (__bridge NSDictionary *)(CFNetworkCopySystemProxySettings());
//NSLog(@"cfnetwork proxy setting : %@", dict);
return [dict count] > 0;
}
最佳答案
我认为不应通过检查 CFNetworkCopySystemProxySettings()
中的非零元素数来确定 VPN 连接。 (例如,我在 WiFi 网络上看到条目,但在 VPN 上看不到。)
因此,有两个观察结果:
我会考虑使用
SystemConfiguration.framework
并将以下代码与您 VPN 上的主机名一起使用:- (BOOL)checkForConnectivity:(NSString *)hostName { BOOL success = false; SCNetworkReachabilityRef reachability = SCNetworkReachabilityCreateWithName(NULL, [hostName UTF8String]); SCNetworkReachabilityFlags flags; success = SCNetworkReachabilityGetFlags(reachability, &flags); CFRelease(reachability); NSLog(@"success=%x", flags); // this is the standard non-VPN logic, you might have to alter it for VPN connectivity BOOL isAvailable = success && (flags & kSCNetworkFlagsReachable) && !(flags & kSCNetworkFlagsConnectionRequired); if (isAvailable) { NSLog(@"Host is reachable: %d", flags); return YES; }else{ NSLog(@"Host is unreachable"); return NO; } }
假设
success
不为零,您可能需要对flags
中的位设置进行一些实证研究。参见 SCNetworkReachability Reference有关这些标志的技术定义。我听说他们得到了kSCNetworkReachabilityFlagsReachable | kSCNetworkReachabilityFlagsTransientConnection
当 VPN 已连接时,但我没有 VPN,因此我无法测试该声明。我建议在开启和不开启 VPN 的情况下进行尝试,看看是否会返回不同的标志
。与手头的问题无关,您的代码示例会泄漏。如果使用 ARC,请不要忘记使用
CFBridgingRelease
或__bridge_transfer
。或者不管是否在 ARC 中,在返回之前显式调用CFRelease
。如果您运行静态分析器(按 shift+command+B 或从“产品”菜单中选择“分析”) Xcode 的最新版本,它应该警告您有关 Core Foundation 调用的内存管理。
无论如何,这就是我倾向于在 ARC 中处理它的方式:
- (BOOL)checkForVPNConnectivity { NSDictionary *dict = CFBridgingRelease(CFNetworkCopySystemProxySettings()); return [dict count] > 0; }
关于iphone - 如何检测 iphone 的 VPN 连接?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16285093/