7 Replies
      Latest reply on Mar 22, 2020 6:06 PM by kemalenver
      zontar Level 1 Level 1 (0 points)

        Hello,

         

        I'm writing an application that uses WKWebView on iOS 11.4.

        We initiate the webview by loading a remote URL. Then the user navigates normally, but when we are about to load a certain url (as detected by the delegate method "

        func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {

         

        we must make a submit to a given url (basically we must authenticate the user with a pair of credentials he has stored in the App beforehand).

         

        we tried this

             var urlRequest = URLRequest(url: URL(string: "https://xxxxxx/login")!)
              urlRequest.httpMethod = "POST"
             let params = [
                                    "username":   SessionManager.shared.username!,
                                    "password":  SessionManager.shared.password!,
                                    "vhost": "standard"
              ]
              let postString = self.getPostString(params: params)
                urlRequest.httpBody = postString.data(using: .utf8)
               webView.load(urlRequest)
        
        
        ...
        //helper method to build url form request
        func getPostString(params:[String:String]) -> String
            {
                var data = [String]()
                for(key, value) in params
                {
                    data.append(key + "=\(value)")
                    
                }
                return data.map { String($0) }.joined(separator: "&")
            }
        
        

         

        But then we check the same request in the delegate method

         

        func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
        
                    print("BODY", navigationAction.request.httpBody)
        
        

        and the body is null.

        In fact the request fails and we get an error in the WKWebView page.

         

        Is this still the bug as in

        https://forums.developer.apple.com/thread/18952

         

        or is it something I'm doing wrong?

        Thanks

        W

        • Re: WKWebView using URLRequest with POST results in nil body
          Mr. Jefferson Level 1 Level 1 (0 points)

          I just discovered that, at least in iOS 13 beta 4, WKWebView doesn't automatically set the Content-Type header to application/x-www-formurlencoded for POST requests the way UIWebView does. Could that be the issue?

          • Re: WKWebView using URLRequest with POST results in nil body
            hflow7 Level 1 Level 1 (0 points)

            I have the same probleme in our client's application for 3DS2 response handling.

             

            We used to have a UIWebView and inspect the httpbody response from 3DS2 form in order to create a "3DSResponse" object in our app, and then determine the credit card informations and if the validation passed or not.

             

            We received a warning that in the future, our builds will be rejected because of the use of UIWebView. So we have to migrate to a WKWebView.

             

            Problem: in the

            func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void)

            the

            navigationAction.request.httpBody

            is equal to nil, so impossible to retreive the result of the form post and what to do with it.

             

            I saw on a lot of forums that it was a known bug of WKWebView, that it was going to be patched in future releases. But for now we are in a urge that on one hand our apps will be rejected if we use UIWebView, and on the other and we can't miss the implementation of 3DS and 3DS2 in our e-commerce application as we are forced to by european legislation.

             

            Is it something finally planned?

            • Re: WKWebView using URLRequest with POST results in nil body
              kemalenver Level 1 Level 1 (0 points)

              We found a solution that will not require drastic changes or javascript.  Basically you need to make use of WKURLSchemeHandler protocol:

               

              1. Setup webview

               

              let config = WKWebViewConfiguration()
              config.setURLSchemeHandler(self, forURLScheme: "my-custom-scheme")
              let wkWebView = WKWebView(frame: .zero, configuration: config)

               

              2. Implement WKURLSchemeHandler protocol

               

              func webView(_ webView: WKWebView, start urlSchemeTask: WKURLSchemeTask) {
                if let url = urlSchemeTask.request.url, url.scheme == "my-custom-scheme" {
                self.handleTermURLCallback(urlSchemeTask.request)
                }
              }

               

              By using this you'll find that your request httpBody in the callback is not null and you can continue the same way you used to with UIWebView.

               

              Just set the URL to be my-custom-scheme

               

              You'll also no longer need to cancel requests in the WKNavigationDelegate that match your url.  This actually ends up being a nice improvement over UIWebView!

               

              It took a lot of effort to find this but it is working for us and we didn't need to change very much.  Hope it helps you guys.