How can I pin a certificate with Square OKHTTP?

前端 未结 5 1469
生来不讨喜
生来不讨喜 2020-11-30 17:04

I think I need to create a new SSL Socket Factory? Also, I don\'t want to use the global SSL Context (https://github.com/square/okhttp/issues/184) for obvious reasons.

5条回答
  •  醉酒成梦
    2020-11-30 17:33

    This is easier than I thought with OkHttp.

    Follow these steps:

    1. Get the public sha1 keys. The OkHttp documentation gives us a clear way to do this complete with sample code. In case it goes away, here it is pasted in below:

    For example, to pin https://publicobject.com, start with a broken configuration:

    String hostname = "publicobject.com";
    CertificatePinner certificatePinner = new CertificatePinner.Builder()
        .add(hostname, "sha1/BOGUSPIN")
        .build();
    OkHttpClient client = new OkHttpClient();
    client.setCertificatePinner(certificatePinner);
    
    Request request = new Request.Builder()
        .url("https://" + hostname)
        .build();
    client.newCall(request).execute();   
    

    As expected, this fails with a certificate pinning exception:

    javax.net.ssl.SSLPeerUnverifiedException: Certificate pinning failure!
    Peer certificate chain: sha1/DmxUShsZuNiqPQsX2Oi9uv2sCnw=: CN=publicobject.com, OU=PositiveSSL sha1/SXxoaOSEzPC6BgGmxAt/EAcsajw=: CN=COMODO RSA Domain Validation Secure Server CA sha1/blhOM3W9V/bVQhsWAcLYwPU6n24=: CN=COMODO RSA Certification Authority sha1/T5x9IXmcrQ7YuQxXnxoCmeeQ84c=: CN=AddTrust External CA Root

    Pinned certificates for publicobject.com:

    sha1/BOGUSPIN
    at com.squareup.okhttp.CertificatePinner.check(CertificatePinner.java)
    at com.squareup.okhttp.Connection.upgradeToTls(Connection.java)
    at com.squareup.okhttp.Connection.connect(Connection.java)
    at com.squareup.okhttp.Connection.connectAndSetOwner(Connection.java)

    Follow up by pasting the public key hashes from the exception into the certificate pinner's configuration:

    Side note: If you are doing this on Android you will get a separate exception if you are doing this on a UI thread, so make sure you do this on a background thread.

    2. Configure your OkHttp Client:

    OkHttpClient client = new OkHttpClient();
    client.setCertificatePinner(new CertificatePinner.Builder()
           .add("publicobject.com", "sha1/DmxUShsZuNiqPQsX2Oi9uv2sCnw=")
           .add("publicobject.com", "sha1/SXxoaOSEzPC6BgGmxAt/EAcsajw=")
           .add("publicobject.com", "sha1/blhOM3W9V/bVQhsWAcLYwPU6n24=")
           .add("publicobject.com", "sha1/T5x9IXmcrQ7YuQxXnxoCmeeQ84c=")
           .build());
    

    That's all there is to it!

提交回复
热议问题