【问题标题】:The best way to intercept a WebView request in Android在Android中拦截WebView请求的最佳方法
【发布时间】:2015-12-06 19:43:44
【问题描述】:

我在我的应用程序中使用WebView,我必须在其中拦截请求。我目前正在使用以下代码来执行此操作。

public WebResourceResponse shouldInterceptRequest (WebView view, String url) {
    HttpURLConnection conn = (HttpURLConnection) new URL(url).openConnection();
    conn.setRequestProperty("User-Agent", userAgent);

    String mime;
    if (url.lastIndexOf('.') > url.lastIndexOf('/')) {
        String ext = url.substring(url.lastIndexOf('.') + 1);
        mime = MimeTypeMap.getSingleton().getMimeTypeFromExtension(ext);
    } else {
       mime = "text/html";
    }
    return new WebResourceResponse(mime, "UTF-8", conn.getInputStream());
}

以上代码在大多数情况下都能正常工作,但并非全部。例如,当我尝试登录 Outlook 时,它只是显示我的电子邮件或密码不正确,我还看到了其他请求被破坏的情况,但如果我删除 shouldInterceptRequest,一切正常。

有没有比我目前用来拦截请求更好的方法?

【问题讨论】:

  • 您没有显示拦截请求的代码。谁的要求?
  • 当然是WebView 的请求。上面的代码拦截请求。我只是没有写public WebResourceResponse shouldInte...,所以问题会更干净。
  • 对我来说这段代码看起来不错,除非 if (url.lastIndexOf('.') > url.lastIndexOf('/')) 这可以设置错误的 mime 类型来响应。例如,如果我们假设 PNG 图像的 URL 是 example.com/image1,那么您的 mime 类型将是错误的。我建议您用类似 stackoverflow.com/a/30101299/669159 的代码替换该代码,以得出应为响应 mime 的结论。
  • 为什么需要拦截请求?至少从您的代码来看,您只是在设置 UserAgent。您是否尝试过使用 setUserAgentString? developer.android.com/reference/android/webkit/…
  • @Raanan 我实际上做了更多的事情,比如为某些域添加 cookie,而为其他一些域添加 cookie,我没有包含在问题中,因为我确信代码中的问题是获取请求的 URL 的内容类型。

标签: java android webview


【解决方案1】:

你的代码有两个问题

  1. 不正确的扩展检测

例如,当代码尝试获取此 URL 的资源扩展时:

https://login.live.com/login.srf?wa=wsignin1.0&rpsnv=12&ct=1442476202&rver=6.4.6456.0&wp=MBI_SSL_SHARED&wreply=https:%2F%2Fmail.live.com%2Fdefault.aspx%3Frru%3Dinbox&lc=1033&id=64855&mkt=en-us&cbcxt=mai

它会返回错误的aspx%3Frru%3Dinbox&lc=1033&id=64855&mkt=en-us&cbcxt=mai。从 URL 获取扩展有特殊的方法:getFileExtensionFromUrl()

  1. 根据文档方法MimeTypeMap.getSingleton().getMimeTypeFromExtension(ext) 可能会返回null。在这种情况下,您的代码为页面设置了错误的 MIME 类型。

这里是考虑到这两个问题的方法代码

@Override
public WebResourceResponse shouldInterceptRequest(WebView view,
    String url) {
    String ext = MimeTypeMap.getFileExtensionFromUrl(url);
    String mime = MimeTypeMap.getSingleton().getMimeTypeFromExtension(ext);
    if (mime == null) {
        return super.shouldInterceptRequest(view, url);
    } else {
        HttpURLConnection conn = (HttpURLConnection) new URL(
                                                 url).openConnection();
        conn.setRequestProperty("User-Agent", userAgent);
        return new WebResourceResponse(mime, "UTF-8",
                                                 conn.getInputStream());
    }
}

【讨论】:

  • 此代码有效,但它是一种解决方案,其中一些请求被拦截而另一些则不被拦截。仍在等待更好的答案...
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-03
  • 2016-06-12
  • 1970-01-01
  • 2012-02-18
  • 1970-01-01
  • 2019-02-18
相关资源
最近更新 更多