【问题标题】:Change User Agent in UIWebView在 UIWebView 中更改用户代理
【发布时间】:2010-10-03 11:09:42
【问题描述】:

我的业务需要能够为嵌入式 UIWebView 自定义 UserAgent。 (例如,如果用户使用的是应用程序的一个版本而不是另一个版本,我希望服务器做出不同的响应。)

是否可以在现有的 UIWebView 控件中自定义 UserAgent,例如 Windows 应用程序中的嵌入式 IE 浏览器?

【问题讨论】:

    标签: ios iphone cocoa-touch uiwebview


    【解决方案1】:

    它应该与 Kuso 所写的 NSMutableURLRequest 一起使用。

    NSMutableURLRequest *urlRequest = [[NSMutableURLRequest alloc] initWithURL: [NSURL URLWithString: @"http://www.google.com/"]];
    [urlRequest setValue: @"iPhone" forHTTPHeaderField: @"User-Agent"]; // Or any other User-Agent value.
    

    您必须使用 NSURLConnection 来获取 responseData。将 responseData 设置为您的 UIWebView 并且 webView 应该呈现:

    [webView loadData:(NSData *)data MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)encodingName baseURL:(NSURL *)baseURL];
    

    【讨论】:

    • mac 上 safari 的用户代理字符串是什么样的?
    【解决方案2】:

    现代斯威夫特

    以下是 StackOverflow 用户 PassKit 和 Kheldar 对 Swift 3+ 项目的建议:

    UserDefaults.standard.register(defaults: ["UserAgent" : "Custom Agent"])
    

    来源:https://stackoverflow.com/a/27330998/128579

    早期的 Objective-C 答案

    随着 iOS 5 的变化,我推荐以下方法,最初来自这个 StackOverflow 问题:UIWebView iOS5 changing user-agent,正如下面的答案中所指出的那样。在该页面上的 cmets 中,它似乎也适用于 4.3 及更早版本。

    通过运行此代码一次来更改“UserAgent”默认值 您的应用启动:

    NSDictionary *dictionary = @{@"UserAgent": @"Your user agent"};
    [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary];
    [[NSUserDefaults standardUserDefaults] synchronize];
    

    如果您需要在 4.3/5.0 之前的 iOS 版本中工作的方法,请参阅这篇文章的先前编辑。请注意,由于进行了广泛的编辑,此页面上的以下 cmets / 其他答案可能没有意义。毕竟,这是一个四年前的问题。 ;-)

    【讨论】:

    • 这种方法的一个缺点:如果您的 webView 包含自定义 url (someapplication://),它们将失败,因为您总是返回 YES。
    • @stigi 尝试将密钥从 @"User_Agent" 更改为 @"User-Agent"。这对我有用。
    • 有人知道如何通过 AJAX 调用来持久化它吗?
    • @nmr 这又回到了 3.x 天。请参阅帖子顶部的“2012 年更新”。不,对不起,我不能说为什么当时有必要。 TCP 堆栈中的另一层可能会将带有下划线的标头转换为带有连字符的标头。我只能说我认为他们已经修复了这种行为,所以我不会担心。
    • 这可以最初在控制器的网络视图中完成吗?就像首先检查 url 并以此为基础调用 [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary]; ?基本上我已经尝试过了,但没有成功。只是想知道是否有可能,因为您建议最初在启动时执行此操作。
    【解决方案3】:

    把这一切都解决了:

    - (void)viewDidLoad {
        NSURL *url = [NSURL URLWithString: @"http://www.amazon.com"];
        NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
        [request setValue:@"Foobar/1.0" forHTTPHeaderField:@"User-Agent"];
        [webView loadRequest:request];
    }
    

    谢谢大家。

    【讨论】:

      【解决方案4】:

      使用@"User_Agent" 只会导致自定义标头出现在 GET 请求中。

      用户代理:Foobar/1.0\r\n
      用户代理:Mozilla/5.0(iPhone;U;CPU iPhone OS 3_1_2 类似 Mac OS X; zh-CN)AppleWebKit/528.18(KHTML,如 壁虎) 移动/7D11\r\n

      以上是剖析的 HTTP 数据包中出现的内容,基本上证实了 Sfjava 从该论坛引用的内容。有趣的是,“User-Agent”变成了“User_agent”。

      【讨论】:

        【解决方案5】:

        这个解决方案似乎被视为一种非常聪明的方法

        changing-the-headers-for-uiwebkit-http-requests

        它使用 Method Swizzling,您可以在 CocoaDev page 上了解更多信息

        看看吧!

        【讨论】:

        • 从 iOS 5 开始,iOS 不再使用公共 API 来创建它的 NSURLRequest 对象,所以 swizzling 方法在 iOS 5 下将不再起作用。
        【解决方案6】:

        实际上将任何标头字段添加到 shouldStartLoadWithRequest 中的 NSURLRequest 参数 似乎 工作,因为请求响应 setValue:ForHTTPHeaderField - 但它实际工作 -请求在没有标头的情况下发出。

        所以我在 shouldStartLoadWithRequest 中使用了这个解决方法,它只是将给定的请求复制到一个新的可变请求中,然后重新加载它。这实际上会修改发送出去的标头。

        if ( [request valueForHTTPHeaderField:@"MyUserAgent"] == nil )
        {
            NSMutableURLRequest *modRequest = [request mutableCopyWithZone:NULL];
            [modRequest setValue:@"myagent" forHTTPHeaderField:@"MyUserAgent"];
            [webViewArgument loadRequest:modRequest];
            return NO;
        }
        

        不幸的是,这仍然不允许覆盖用户代理 http 标头,该标头显然已被 Apple 覆盖。我想要覆盖它,您必须自己管理 NSURLConnection。

        【讨论】:

          【解决方案7】:

          我也遇到过这个问题,各种方法都试过了。我发现只有这种方法有效(iOS 5.x): UIWebView iOS5 changing user-agent

          原理是在用户设置中永久设置用户代理。这行得通; Webview 发送给定的标头。就两行代码:

          NSDictionary *dictionary = [NSDictionary dictionaryWithObjectsAndKeys:@"Mozilla/Whatever version 913.6.beta", @"UserAgent", nil];
          [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary];
          

          在可变请求中设置 User-Agent 或 User_Agent,或者通过 swizzling 覆盖 NSHttpRequest 中的 setValue,-我尝试了所有这些并使用 wireshark 控制了结果,但这些似乎都不起作用,因为 Webview 仍然使用来自用户默认值的用户代理值,无论您尝试在 NSHttpRequest 中设置什么。

          【讨论】:

          • 只有这对我有用!您现在可以使用更短的版本:[[NSUserDefaults standardUserDefaults] registerDefaults:@{ @"UserAgent": @"custom agent" }];
          【解决方案8】:

          在 AppDelegate.m 中试试这个

          + (void)initialize 
          
          {
          
              // Set user agent (the only problem is that we can’t modify the User-Agent later in the program)
          
              // iOS 5.1
          
              NSDictionary *dictionnary = [[NSDictionary alloc] initWithObjectsAndKeys:@”Mozilla/5.0 (iPad; CPU OS 5_1 like Mac OS X) AppleWebKit/534.46 (KHTML, like Gecko) Version/5.1 Mobile/9B176 Safari/7534.48.3”, @”UserAgent”, nil];
          
          
              [[NSUserDefaults standardUserDefaults] registerDefaults:dictionnary];
          
          }
          

          【讨论】:

            【解决方案9】:

            我发现的唯一问题是仅更改用户代理

            - (BOOL)application:(UIApplication *)application
                    didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
                NSDictionary *dictionary = [NSDictionary 
                    dictionaryWithObjectsAndKeys:
                    @"Mozilla/5.0 (iPod; U; CPU iPhone OS 4_3_3 like Mac OS X; ja-jp) AppleWebKit/533.17.9 (KHTML, like Gecko) Version/5.0.2 Mobile/8J2 Safari/6533.18.5", 
                    @"UserAgent", nil];
                [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary];
            }
            

            【讨论】:

              【解决方案10】:

              通过汇集the answer by Louis St-AmourNSUserDefaults+UnRegisterDefaults 类别from this question/answer,您可以在应用运行时随时使用以下方法启动和停止用户代理欺骗:

              #define kUserAgentKey @"UserAgent"
              
              - (void)startSpoofingUserAgent:(NSString *)userAgent {
                  [[NSUserDefaults standardUserDefaults] registerDefaults:@{ kUserAgentKey : userAgent }];
              }
              
              - (void)stopSpoofingUserAgent {
                  [[NSUserDefaults standardUserDefaults] unregisterDefaultForKey:kUserAgentKey];
              }
              

              【讨论】:

              • 在 iPhone 5 设备上的 iOS7 中进行了测试,它可以工作,但不能在模拟器上工作,但这没关系。谢谢你的信息。
              • startSpoofingUserAgent 对我有用,但 unregisterDefaultForKey 不是有效命令。我让它工作的唯一方法是使用原始值执行 registerDefaults 来重置它。 -rrh
              • unregisterDefaultForKey: 在此处实现:stackoverflow.com/a/18109860/1580288(如答案中所述)。
              【解决方案11】:

              我遇到了同样的问题。我想向用户代理添加一些信息,还需要保留 webview 的原始用户代理。我使用下面的代码解决了它:

                  //get the original user-agent of webview
              UIWebView *webView = [[UIWebView alloc] initWithFrame:CGRectZero];
              NSString *oldAgent = [webView stringByEvaluatingJavaScriptFromString:@"navigator.userAgent"];
              NSLog(@"old agent :%@", oldAgent);
              
              //add my info to the new agent
              NSString *newAgent = [oldAgent stringByAppendingString:@" Jiecao/2.4.7 ch_appstore"];
              NSLog(@"new agent :%@", newAgent);
              
              //regist the new agent
              NSDictionary *dictionnary = [[NSDictionary alloc] initWithObjectsAndKeys:newAgent, @"UserAgent", nil];
              [[NSUserDefaults standardUserDefaults] registerDefaults:dictionnary];
              

              在实例化 webview 之前使用它。

              【讨论】:

                【解决方案12】:

                在 Swift 中非常简单。只需将以下内容放入您的 App Delegate。

                UserDefaults.standard.register(defaults: ["UserAgent" : "Custom Agent"])
                

                如果要附加到现有代理字符串,则:

                let userAgent = UIWebView().stringByEvaluatingJavaScript(from: "navigator.userAgent")! + " Custom Agent"
                UserDefaults.standard.register(defaults: ["UserAgent" : userAgent])
                

                注意:您可能需要卸载并重新安装应用程序以避免附加到现有的代理字符串。

                【讨论】:

                • 谢谢。节省了很多时间!
                • 感谢@Kheldar 更新 Swift 3。对于早期的 Swift 版本,请查看编辑历史记录。
                【解决方案13】:

                要仅将自定义内容添加到当前 UserAgent 值,请执行以下操作:

                1 - 从新的 WEBVIEW 获取用户代理值

                2 - 将自定义内容附加到它

                3 - 使用键 UserAgent 将新值保存在字典中

                4 - 将字典保存在标准用户默认值中。

                请看下面的例子:

                NSString *userAgentP1 = [[[UIWebView alloc] init] stringByEvaluatingJavaScriptFromString:@"navigator.userAgent"];
                NSString *userAgentP2 = @"My_custom_value";
                NSString *userAgent = [NSString stringWithFormat:@"%@ %@", userAgentP1, userAgentP2];
                NSDictionary *dictionary = [NSDictionary dictionaryWithObjectsAndKeys:userAgent, @"UserAgent", nil];
                [[NSUserDefaults standardUserDefaults] registerDefaults:dictionary];
                

                【讨论】:

                  【解决方案14】:

                  Apple 将很快停止接受带有 UIWebView 的应用程序。在下面查找如何更改 WKWebView 中的用户代理。

                  let config = WKWebViewConfiguration()
                  
                  config.applicationNameForUserAgent = "My iOS app"
                  
                  webView = WKWebView(frame: <the frame you need>, configuration: config)
                  

                  【讨论】:

                    猜你喜欢
                    • 2012-12-14
                    • 2012-01-19
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    相关资源
                    最近更新 更多