Developer
Developer

Reputation: 41

How to pin public key of SSL certificate in flutter?

Could someone help me on implementing SSL public key pinning in flutter? I have searched a lot in google but I did not find a proper article that explains how this can be implemented.

Kindly help !!!

Upvotes: 3

Views: 3487

Answers (2)

naman kashyap
naman kashyap

Reputation: 730

You can use certificate_pinning_httpclient: ^0.0.3 it allow us to use public key pinning and you can also add backup key init

static const String publicKey =
      "Xs+pjRp23QkmXeH31KEAjM1aWvxpHT6vYy+q2ltqtaM="; // Add your own public key
static const String backupKey =
      "Xs+pjRp23QkmXeH31KEAjM1aWvxpHT6vYy+q2ltqtaM="; // you can also add backup key

 import 'package:certificate_pinning_httpclient/certificate_pinning_httpclient.dart';

// with http
final client = IOClient(CertificatePinningHttpClient(
        [publicKey,backupKey]));

// with Dio
final _dio = Dio();
(_dio.httpClientAdapter as IOHttpClientAdapter).onHttpClientCreate =
    (client) => CertificatePinningHttpClient(
        ["S4kZuhQQ1DPcMOCYFQXD0gG+UW0zmyVx6roNWpRl65I="]);

Upvotes: 1

Amir Panahandeh
Amir Panahandeh

Reputation: 9049

There is a package called http_certificate_pinning which provides 3 different APIs to use. You can check it here.

1-As an interceptor for Dio:

import 'package:http_certificate_pinning/certificate_pinning_interceptor.dart';
  
  // Add CertificatePinningInterceptor in dio Client
  Dio getClient(String baseUrl, List<String> allowedSHAFingerprints){
      var dio =  Dio(BaseOptions(baseUrl: baseUrl))
        ..interceptors.add(CertificatePinningInterceptor(allowedSHAFingerprints));
      return dio;
  }

  myRepositoryMethod(){ 
    dio.get("myurl.com");
  }

2-Creating an http client:

import 'package:http_certificate_pinning/secure_http_client.dart';
  
  // Uses SecureHttpClient to make requests
  SecureHttpClient getClient(List<String> allowedSHAFingerprints){
      final secureClient = SecureHttpClient.build(certificateSHA256Fingerprints);
      return secureClient;
  }

  myRepositoryMethod(){ 
    secureClient.get("myurl.com");
  }  

3-Checking if the handshake happens correctly and do whatever you want:

import 'package:http_certificate_pinning/http_certificate_pinning.dart';
  
Future myCustomImplementation(String url, Map<String,String> headers, List<String> allowedSHAFingerprints) async {
  try{
    final secure = await HttpCertificatePinning.check(
      serverURL: url,
      headerHttp: headers,
      sha: SHA.SHA256,
      allowedSHAFingerprints:allowedSHAFingerprints,
      timeout : 50
    );

    if(secure.contains("CONNECTION_SECURE")){
      return true;
    }else{
      return false;
    }
  }catch(e){
    return false;
  }
}

Upvotes: 1

Related Questions