J'ai essayé pendant des jours d'utiliser une vue Web avec un certificat client intégré à l'application, mais il me semble que le sdk Android ne fournit aucun moyen de le faire. Existe-t-il un rappel pour intercepter le défi envoyé par le serveur? Existe-t-il un moyen d'utiliser WebView avec un certificat client et d'effectuer une demande https?
Étant donné que votre problème m'intéresse également, j'ai consulté la documentation de WebView et WebViewClient, j'ai surfé et, en effet, il semble impossible d'authentifier une session WebView à l'aide d'un certificat client, car la méthode requise (ClientCertRequestHandler) n'est pas API publique.
Utilisation d'un WebView Android pour se connecter à un serveur sécurisé avec un certificat client
Une recherche dans les discussions sur la sécurité Android confirme que l'appel n'est effectivement pas disponible:
https://groups.google.com/forum/#!msg/Android-security-discuss/0hzTGaA9swQ/1Oqc8UpGLH8J
et bien que
La version Android 4.0 inclut la prise en charge de l'authentification par certificat client dans le navigateur.
(ref: https://code.google.com/p/Android/issues/detail?id=8196 )
aucune mention de WebViews n'est faite :(
Même s'il existe de nouvelles API pour charger des certificats dans un trousseau:
http://developer.Android.com/reference/Android/security/KeyChain.htmlhttp://nelenkov.blogspot.it/2011/11/using-ics-keychain-api. html
il n'est pas clair si WebView va les utiliser ... Donc, vous devriez essayer la classe KeyChain et voir si vous pouvez vous authentifier correctement (je n'ai pas de moyen simple de tester cela, alors vous êtes seul).
_ {Si KeyChain ne fonctionne pas avec WebViews}, je suppose que tout se résume à quelques solutions de contournement loin d'être parfaites:
Solution 1:
utilisez quand même ClientCertRequestHandler (il est marqué comme caché, mais apparemment toujours utilisable):
https://code.google.com/p/Android/issues/detail?id=53491
Cependant, même en supposant que vous le fassiez, Android Dev. Il se peut que l’équipe modifie/supprime la méthode sans préavis et que votre application cesse de fonctionner avec les versions futures du responsable de la sécurité.
Solution 2:
Si vous pouvez limiter votre cible à Android 4.0 ou version ultérieure, une solution audacieuse (et peu probable ...) consiste à charger le certificat dans la vue Web à partir de votre stockage local à l'aide d'un jeu de fichiers:
Charger le fichier HTML local dans WebView
mais je doute fort que la vue Web se comporte comme le navigateur ...
Solution 3: (ce qui devrait fonctionner mais demande beaucoup d'effort)
Gérez chaque connexion https en arrière-plan à l'aide de HTTPClient ou HttpURLConnection, puis transmettez les données à WebView:
http://chariotsolutions.com/blog/post/https-with-client-certificates-on/
Tu as ma sympathie.
Si vous avez juste besoin d'ignorer les demandes de certificat SSL dans la vue Web, cela a fonctionné pour moi sur Lollipop:
Dans votre client d'affichage Web, écrivez:
@Override
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
handler.proceed(); // Ignore SSL certificate errors
}
Ceci est utile pour déboguer des vues Web sur des environnements qa/dev/stage.
Dans API 21 (Android Lollipop) et les versions ultérieures, vous pouvez remplacer le paramètre WebViewClient.onReceivedClientCertRequest (vue WebView, demande ClientCertRequest) . Dans la méthode, utilisez votre gestionnaire de clés pour obtenir la clé privée et la chaîne de certificats, puis appelez request.proceed () .
Pour gérer correctement la validation du certificat SSL afin d'empêcher le rejet de l'application par Google Play conformément à la stratégie de sécurité mise à jour, modifiez votre code pour appeler SslErrorHandler.proceed () lorsque le certificat présenté par le serveur répond à vos attentes et appelez SslErrorHandler.cancel () sinon.
Par exemple, j’ajoute une boîte de dialogue d’alerte pour que l’utilisateur soit confirmé et semble que Google n’affiche plus d’avertissement.
@Override
public void onReceivedSslError(WebView view, final SslErrorHandler handler, SslError error) {
final AlertDialog.Builder builder = new AlertDialog.Builder(this);
String message = "SSL Certificate error.";
switch (error.getPrimaryError()) {
case SslError.SSL_UNTRUSTED:
message = "The certificate authority is not trusted.";
break;
case SslError.SSL_EXPIRED:
message = "The certificate has expired.";
break;
case SslError.SSL_IDMISMATCH:
message = "The certificate Hostname mismatch.";
break;
case SslError.SSL_NOTYETVALID:
message = "The certificate is not yet valid.";
break;
}
message += " Do you want to continue anyway?";
builder.setTitle("SSL Certificate Error");
builder.setMessage(message);
builder.setPositiveButton("continue", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
handler.proceed();
}
});
builder.setNegativeButton("cancel", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
handler.cancel();
}
});
final AlertDialog dialog = builder.create();
dialog.show();
}
Après cela, aucun avertissement ne sera affiché.
WebView sur Android 4.4 basé sur Chronium a introduit un bogue: lorsque le serveur demande un certificat client, WebView arrête le processus de chargement. La méthode onPageFinished sera immédiatement appelée, mais aucune page ne sera affichée.
Nous ne pouvons pas accéder au certificat client dans la Webview, Un problème Google a été soulevé pour le même . https://code.google.com/p/Android/issues/detail?id=53491
Le certificat SSL auto-signé fonctionne pour moi
Veuillez vérifier votre réponse https://stackoverflow.com/a/49003522/5058630