2013-12-23 83 views
5

私はページを読み込むために相互認証が必要なWebページを持っています。 私はERROR_FAILED_SSL_HANDSHAKEでonReceivedError()を取得します。ログには、「セキュアな接続を確立できませんでした」というメッセージがWebkitによって出力されます。 私は広範囲に検索しましたが、回答が見つかりませんでした。いくつかの記事がありますが、決定的なものはありません。 私はすべての3つのソリューションを投稿しましたhere。 仕事への可能性が高い解決策だった: - 解決策1: 使用ClientCertRequestHandlerとにかく(これは、隠されたとしてマークされたが、どうやらまだ使用可能です):Android Webviewクライアント証明書、相互認証、SSL over Webview

だから私は)onReceivedClientCertRequestを(上書きする内部APIが含まれるようにandroid.jarを修正 しかし、私は実行時にコールバックを取得していません。サードパーティのブラウザでも同様です。私は標準的なブラウザで同じWebページをロードしようとしました。クライアント証明書を選択するようにUIにコールバックがあります。

WebkitからonReceivedClientCertRequest()のコールバックを取得できるのは、システムブラウザのアプリケーションだけです。

iOSプラットフォームの場合、Webviewはサイトも直接ロードできません。しかし、NSURLを使用してHTTPS接続を行うと、 はしばらくの間、クライアント証明書をメモリに保持し、Webviewはこのページを正常にロードできます。

Androidでは、クライアントとサーバーの証明書をロードするSSLSocketFactoryを登録することで、HTTPS通信を正常にセットアップしました。 私はそれを使ってREST API呼び出しを行うことができます.iOSとは異なり、Android webviewが相互認証のためにクライアント証明書を使用する方法を見つけることができません。

Webviewでの相互認証は、セキュリティの基本要件の1つとしてプラットフォームでサポートされるべきだと思います。この問題に関する最新情報はありますか?

EDIT 1

私はそれが下記の私の答えどおり4.3へのAndroid 4.0に取り組んでいました。 Android 4.4のHovererは、WebViewClientClassicExtクラス自体が削除されているようです。 この場合、何ができますか? AndroidでwebviewでClientCertificatesを設定できないのはなぜですか?

答えて

3

は、だから私は、クラスのonReceivedClientCertRequest()オーバーライドすることにより、4.2、4.3でWebViewClient

  • 拡張クラスのonReceivedClientCertRequest()オーバーライドすることで、Androidの4.0と4.1で4.3

    1. まで働いてこの事を得ることができますWebViewClientClassicExtを拡張します。

    秘密鍵と証明書ClientCertRequestHandler proceed()メソッドを設定しました。

    は4.3 uptil ソリューションが

    WebviewClientCustom.java

    public class WebViewClientCustom extends WebViewClient { 
        private X509Certificate[] certificatesChain; 
        private PrivateKey clientCertPrivateKey; 
        private IWebViewCallbacks webviewCallbacks; 
    
        public WebViewClientCustom(IWebViewCallbacks webviewCallbacks) { 
         this.webviewCallbacks = webviewCallbacks; 
        } 
    
        public void onReceivedClientCertRequest(WebView paramWebView, 
          ClientCertRequestHandler paramClientCertRequestHandler, 
          String paramString) { 
         PrivateKey localPrivateKey = this.clientCertPrivateKey; 
         X509Certificate[] arrayOfX509Certificate = this.certificatesChain; 
         paramClientCertRequestHandler.proceed(localPrivateKey, 
           arrayOfX509Certificate); 
        } 
    
        public void onReceivedError(WebView view, int errorCode, 
          String description, String failingUrl) { 
         webviewCallbacks.onReceivedError(view, errorCode, 
           description, failingUrl); 
    
         super.onReceivedError(view, errorCode, 
           description, failingUrl); 
        } 
    
    
        public void setClientCertificate(PrivateKey paramPrivateKey, 
          X509Certificate[] paramArrayOfX509Certificate) { 
         this.clientCertPrivateKey = paramPrivateKey; 
         this.certificatesChain = paramArrayOfX509Certificate; 
        } 
    
        public boolean shouldOverrideUrlLoading(WebView paramWebView, 
          String paramString) { 
         return webviewCallbacks.shouldOverrideUrlLoading(paramWebView, 
           paramString); 
    
    
        } 
    
        @Override 
        public void onPageStarted(WebView view, String url, Bitmap favicon) { 
         // TODO Auto-generated method stub 
    
         webviewCallbacks.onPageStarted(view, url, favicon); 
         super.onPageStarted(view, url, favicon); 
        } 
    
        @Override 
        public void onPageFinished(WebView view, String url) { 
         // TODO Auto-generated method stub 
    
         webviewCallbacks.onPageFinished(view, url); 
         super.onPageFinished(view, url); 
        } 
    
    } 
    

    WebViewClientCustomExtの下に与えられているEDITED 4.4と

    上記のためのAndroidから修正パッチが必要です。Javaの

    public class WebViewClientCustomExt extends WebViewClientClassicExt { 
        private X509Certificate[] certificatesChain; 
        private PrivateKey clientCertPrivateKey; 
        private IWebViewCallbacks webviewCallbacks; 
    
        public WebViewClientCustomExt(IWebViewCallbacks webviewCallbacks) { 
         this.webviewCallbacks = webviewCallbacks; 
        } 
    
        public void onReceivedClientCertRequest(WebView paramWebView, 
          ClientCertRequestHandler paramClientCertRequestHandler, 
          String paramString) { 
         PrivateKey localPrivateKey = this.clientCertPrivateKey; 
         X509Certificate[] arrayOfX509Certificate = this.certificatesChain; 
         paramClientCertRequestHandler.proceed(localPrivateKey, 
           arrayOfX509Certificate); 
        } 
    
        public void onReceivedError(WebView view, int errorCode, 
          String description, String failingUrl) { 
         webviewCallbacks.onReceivedError(view, errorCode, 
           description, failingUrl); 
    
         super.onReceivedError(view, errorCode, 
           description, failingUrl); 
        } 
    
    
    
        public void setClientCertificate(PrivateKey paramPrivateKey, 
          X509Certificate[] paramArrayOfX509Certificate) { 
         this.clientCertPrivateKey = paramPrivateKey; 
         this.certificatesChain = paramArrayOfX509Certificate; 
        } 
    
        public boolean shouldOverrideUrlLoading(WebView paramWebView, 
          String paramString) { 
         return webviewCallbacks.shouldOverrideUrlLoading(paramWebView, paramString); 
        } 
    
        @Override 
        public void onPageStarted(WebView view, String url, Bitmap favicon) { 
         // TODO Auto-generated method stub 
    
    
         webviewCallbacks.onPageStarted(view, url, favicon); 
         super.onPageStarted(view, url, favicon); 
        } 
    
        @Override 
        public void onPageFinished(WebView view, String url) { 
         // TODO Auto-generated method stub 
    
         webviewCallbacks.onPageFinished(view, url); 
         super.onPageFinished(view, url); 
        } 
    } 
    

    使用

    */ 
        private void setCertificateData() { 
         // TODO Auto-generated method stub 
         try { 
          KeyStore clientCertKeystore = KeyStore.getInstance("pkcs12"); 
          String clientCertPkcsPassword = getPkcsPassword(); 
          byte[] pkcs12; 
    
          pkcs12 = getAuthP12Data(); 
          ByteArrayInputStream pkcs12BAIS = new ByteArrayInputStream(pkcs12); 
    
          clientCertKeystore.load(pkcs12BAIS, 
            clientCertPkcsPassword.toCharArray()); 
          String alias = (clientCertKeystore.aliases().nextElement()); 
          Certificate[] arrayOfCertificate = clientCertKeystore 
            .getCertificateChain(alias); 
          X509Certificate[] arrayOfX509Certificate = new X509Certificate[arrayOfCertificate.length]; 
          for (int i = 0; i < arrayOfCertificate.length; i++) { 
           arrayOfX509Certificate[i] = (X509Certificate) arrayOfCertificate[i]; 
          } 
          PrivateKey localPrivateKey = (PrivateKey) clientCertKeystore 
            .getKey(alias, clientCertPkcsPassword.toCharArray()); 
          if (android.os.Build.VERSION.SDK_INT <= 16) { 
           WebViewClientCustom webvviewClient = new WebViewClientCustom(
             myWebViewClient); 
           webvviewClient.setClientCertificate(localPrivateKey, 
             arrayOfX509Certificate); 
           webView.setWebViewClient(webvviewClient); 
    
          } else { 
           WebViewClientCustomExt webvviewClient = new WebViewClientCustomExt(
             myWebViewClient); 
           webvviewClient.setClientCertificate(localPrivateKey, 
             arrayOfX509Certificate); 
           webView.setWebViewClient(webvviewClient); 
          } 
          // webView.getSettings().setJavaScriptEnabled(true); 
    
         } catch (Exception e) { 
          // TODO Auto-generated catch block 
          e.printStackTrace(); 
         } 
    
        } 
    
  • +0

    私はこの答えのための2つのクエリを持っています。 1。メソッドWebViewClient.onReceivedClientCertRequest()がAPIレベル21(Lolipop)で追加されましたが、Android 4.0および4.1でこのメソッドを使用したとします。二番目。 Android 4.4以上のAPIレベルのソリューションを見つけましたか?返信してください? –

    +0

    Sagar私は最初の部分のために私の答えを更新しました。私は解決策の上に4.4をチェックしていない。 –

    +0

    こんにちは、私は同じことをしなければならないが、秘密鍵は暗号トークンにある。私はそれを使用できますか? – Indio