Skip to content

Instantly share code, notes, and snippets.

@ByteSizedMarius
Last active October 21, 2024 19:55
Show Gist options
  • Save ByteSizedMarius/09210d5cc0ba5601e9b57fbbe0d967c5 to your computer and use it in GitHub Desktop.
Save ByteSizedMarius/09210d5cc0ba5601e9b57fbbe0d967c5 to your computer and use it in GitHub Desktop.
Flutter/Dart: Check if User CA / User certificate is installed
import 'package:flutter/services.dart';
class CertificateChecker {
static const platform = MethodChannel('channel/certificate');
static Future<bool> isCertificateInstalled(String certificateName) async {
try {
final bool result =
await platform.invokeMethod('checkCertificate', {'name': certificateName});
return result;
} on PlatformException catch (e) {
print("Failed to check certificate: '${e.message}'.");
return false;
}
}
}
import android.content.Intent
import android.os.Build
import android.provider.Settings
import io.flutter.embedding.android.FlutterActivity
import io.flutter.embedding.engine.FlutterEngine
import io.flutter.plugin.common.MethodChannel
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import java.security.KeyStore
import java.security.cert.X509Certificate
class MainActivity : FlutterActivity() {
private val CHANNEL = "channel/certificate"
override fun configureFlutterEngine(flutterEngine: FlutterEngine) {
super.configureFlutterEngine(flutterEngine)
MethodChannel(flutterEngine.dartExecutor.binaryMessenger, CHANNEL).setMethodCallHandler { call, result ->
when (call.method) {
"checkCertificate" -> {
val certificateName = call.argument<String>("name")
if (certificateName != null) {
kotlinx.coroutines.runBlocking {
val isInstalled = isCertificateInstalled(certificateName)
result.success(isInstalled)
}
} else {
result.error("INVALID_ARGUMENT", "Certificate name is required", null)
}
}
else -> {
result.notImplemented()
}
}
}
}
private suspend fun isCertificateInstalled(certificateName: String): Boolean = withContext(Dispatchers.Default) {
val userInstalledCaCertificates: List<X509Certificate> = try {
val keyStore = KeyStore.getInstance("AndroidCAStore")
keyStore.load(null, null)
val aliasList = keyStore.aliases().toList().filter { it.startsWith("user") }
aliasList.map { keyStore.getCertificate(it) as X509Certificate }
} catch (e: Exception) {
emptyList()
}
userInstalledCaCertificates.any { cert ->
cert.issuerDN.name.contains(certificateName, ignoreCase = true)
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment