2015-10-14 296 views
2

的iPhone应用程序,我的工作使用WKWebView,但(我的客户要求...)它必须有一个自定义的用户代理。为User-Agent字符串获取AppleWebKit/Mobile/Safari版本号的更好方法?

我们希望用户代理字符串来模仿Safari的,这看起来是这样的:

Mozilla/5.0 (iPhone; CPU iPhone OS 9_0_2 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Version/9.0 Mobile/13A452 Safari/601.1

我知道如何设置用户代理字符串。最简单的就是将UserAgent设置为标准用户默认值。

[[NSUserDefaults standardUserDefaults] registerDefaults:@{@"UserAgent": userAgent}];

我有这个问题实际上是想出在Safari的用户代理使用的版本号苹果。具体来说,AppleWebKit版本(即Mobile(13A452)之后的代码)和Safari版本号。

我想出的唯一解决方案涉及

  1. 实例化一个WKWebView
  2. 从字符串(否则第3步失败)
  3. 在didFinishNavigation委托调用加载的虚拟页面,评估一个javascript返回当前用户代理
  4. 拉UA分开提取那些版本号
  5. 建立一个新的字符串simil AR Safari的,但在末端应用自己的名字/版本,放在括号中的Safari版本的“喜欢”,导致此:

Mozilla/5.0 (iPhone; CPU iPhone OS 9_0_1 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Version/9.0 Mobile/13A452 (like Safari/601.1) TheAppName/1.12

(这两个iPhone版本被发现通过提供系统调用,这不是一个问题。)

有没有更好的办法? (很显然,步骤3-4可以通过JavaScript提取版本号来代替,但这只是改变了一些东西。)

总之,有什么方法可以获得AppleWebKit/Mobile/Safari版本号通过向webview实例请求自己的用户代理字符串?

我可以提供一些示例代码,甚至一个样本项目,如果你不能按照上面的步骤,但我的意图应该是清楚的。

回答

1

我认为最好的办法是坚持沿着你在做什么线的东西:它是派生,外观极像系统默认的用户代理字符串的最安全的方式。尽管创建Web视图,加载字符串以及查询用户代理的开销很大,但在大型计划中这只是微不足道的。

在另一方面,你感兴趣的数据都应该从系统自带的框架迫在眉睫“scrapable”。请记住,虽然iOS进程是沙盒,但这主要是为了防止他们访问其他应用程序的数据。沙盒对iOS和Mac的设计能够留下,因为这些文件支持动态库和资源数据的预期装载到内存中代表应用程序从系统中的文件,这是有道理的宽松阅读应用程序进程。

因此,例如像这样的行添加到您的applicationDidFinishLaunching方法:

NSLog(@"System frameworks: %@", [[NSFileManager defaultManager] directoryContentsAtPath:@"/System/Library/Frameworks/" excludingDirectories:NO]); 

你会看到只是在你期望他们所有可用的系统框架的一个长长的清单。为了得到正确的的WebKit框架的CFBundleVersion,例如:

NSLog(@"%@", [[NSDictionary dictionaryWithContentsOfFile:@"/System/Library/Frameworks/WebKit.framework/Info.plist"] objectForKey:@"CFBundleVersion"]); 

但是,当然,一个NSBundle抽象这个文件中读取出来,而让你在有可能获得已经在内存中的字典直接:

NSLog(@"%@", [[[NSBundle bundleForClass:[[WKWebView class] infoDictionary] objectForKey:@"CFBundleVersion"]); 

你可以使用类似的技巧通过NSBundle的infoDictionaruy访问属性,或者直接从客户手机上的“磁盘”读取数据。

+0

因此,我很好奇为什么你建议坚持我目前的做法(这感觉像一个愚蠢的黑客),如果信息是实际可用的信息字典。很好的答案,不管,谢谢。 – Seth

+0

我想我没有从你的问题中收集足够的信息,你需要仔细模仿“官方”用户代理的真实原因。如果您满意将各种版本号码放在您自己的用户代理字符串中就足够了,那么通过所有方法看起来似乎更清晰。如果你真的需要从WebKit出于某种原因模仿用户代理,我会建议坚持使用WKWebView JavaScript方法。 – danielpunkass

相关问题