我的应用程序有一个WebView,它加载一个简单的
HTML页面,其中包含一个用于从合作伙伴公司加载付款流程的URL的iFrame(而且我无法访问该url源).
当我将targetSdkVersion指向19时,一切正常,我可以通过iFrame付款.然而,当targetSdkVersion指向24时,我没有相同的运气.
在这种情况下,WebView设法加载显示一些EditText的iFrame,用于输入信用卡信息和一个按钮提交它,但是当我点击该按钮时,我总是发生错误500.
由于付款网址已外包,我已到达我们的合作伙伴公司以了解该错误的原因.他们告诉我,这个错误来自一个双重的呼叫,这使得我在WebViewfrom api 24中这样做.
500错误的打印:
HTML文件payment_html如下:
<html> <head> <@R_403_338@ name="viewport" content="width=device-width,initial-scale=1,maximum-scale=1,user-scalable=no"> </head> <body id="bodyContent" onload="addListener()" style="margin:0px;padding:0px;overflow:hidden;height:355px"> <iframe id="ifrPagamento" src="partner_url" frameborder="0" style="overflow:hidden;width:100%;height:100%"></iframe> </body> <script type="text/javascript"> function addListener() { window.addEventListener("message",receiveMessage,false); } function receiveMessage(message) { if (message) { var data = JSON.parse(message.data); if (data.code) { if(data.code === "0") { app.returnStatus(0); } else { app.returnStatus(1); } } } } </script> </html>
partner_url被合作伙伴公司的URL替换,我动态地得到它,如下所示:
private void loadPage() { String url = (String) Session.getObject(Session.Key.PARTNER_URL,""); InputStream inputStream = mActivity.getResources().openRawResource(R.raw.payment_html); ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); try { int i = inputStream.read(); while (i != -1) { byteArrayOutputStream.write(i); i = inputStream.read(); } inputStream.close(); String html = byteArrayOutputStream.toString(); html = html.replace("partner_url",url); mWebView.loadDataWithBaseURL(null,html,"text/html","UTF-8",null); } catch (IOException e) { Funcoes.printError(e.getMessage()); } }
我将WebView设置如下:
private void setupWebView() { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { WebView.setWebContentsDebuggingEnabled(true); } WebSettings webSettings = mWebView.getSettings(); webSettings.setJavaScriptEnabled(true); webSettings.setSupportMultipleWindows(true); webSettings.setJavaScriptCanOpenWindowsAutomatically(true); webSettings.setUseWideViewPort(true); webSettings.setLoadWithOverviewmode(true); webSettings.setLayoutAlgorithm(WebSettings.LayoutAlgorithm.SINGLE_COLUMN); webSettings.setAllowUniversalAccessFromFileURLs(true); webSettings.setCacheMode(WebSettings.LOAD_NO_CACHE); webSettings.setAppCacheEnabled(false); webSettings.setDomStorageEnabled(true); mWebView.setWebChromeClient(new WebChromeClient()); mWebView.setLayerType(View.LAYER_TYPE_SOFTWARE,null); mWebView.addJavascriptInterface(new MyJavaScriptInterface(mActivity),"app"); mWebView.setWebViewClient(new WebViewClient() { @SuppressWarnings("deprecation") @Override public boolean shouldOverrideUrlLoading(WebView view,String url) { view.loadUrl(url); return true; } @Override public boolean shouldOverrideUrlLoading(WebView view,WebResourceRequest request) { view.loadUrl(request.getUrl().toString()); return true; } }); }
最后的layout.xml:
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:paddingTop="10dp" android:paddingBottom="10dp" android:background="@color/white"> <WebView android:id="@+id/webView" android:layout_width="match_parent" android:layout_height="wrap_content" android:scrollbars="none"> </WebView> <ProgressBar android:id="@+id/progress" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:visibility="gone"/> </RelativeLayout>
正如我之前所说,我没有url的来源,因为它是外包.所以我不能分享.
我一直在努力解决这个问题几个星期.有人可以帮我吗
解决方法
几个星期后,我发现这个
https://developer.android.com/about/versions/android-5.0-changes.html#BehaviorWebView说明了api的变化21.看看WebView部分说:
如果您的应用程序使用API级别21或更高版本:
>系统默认锁定混合内容和第三方Cookie.至
允许混合内容和第三方Cookie,使用方法
setMixedContentMode()和setAcceptThirdPartyCookies().
所以,我只是把这些配置添加到WebView中,它工作得很好.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { webSettings.setMixedContentMode(MIXED_CONTENT_ALWAYS_ALLOW); CookieManager.getInstance().setAcceptThirdPartyCookies(mWebView,true); }