Reputation: 1827
In my project, I need to check and validate client certificate for each users' request and then give them access to calling my APIs. My users are machines (other API or library). They append a certificate(s) to their request and send it to my hosted API.
I implement a custom authentication handler and retrieve client certificates successfully. Right now, I compare client certificate with a list of valid certifications in my appsetting.json
(Thumbprint, Issuer and Serial number).
If all of these three properties are same as the client-certification, I return return Task.FromResult(AuthenticateResult.Success(ticket));
otherwise I return
return Task.FromResult(AuthenticateResult.Fail("certificate is not valid"));
everything works fine but I do not feel good about how I validated client certificate. I would like to know if there is elegant way for validating client certificate rather than my solution in ASP.NET CORE.
Upvotes: 3
Views: 1110
Reputation: 56550
Issuer and Serial number are controllable by an attacker, so they are not suitable for validation purposes.
Thumbprint is a SHA1 of multiple properties of the certificate, including issuer, serial number, public key. That's probably OK, for now, and can't be changed by .NET because it's a Windows feature, but thumbprints are meant for reference, not security.
A better approach would be to compare the certificate Signature and hash, and put a minimum quality on the hash of SHA256 or higher. cert.SignatureAlgorithm.Value;
will give you the algorithm as an OID, you can then new up an System.Security.Cryptography.Oid with that and get use the FriendlyName property to get the algorithm in text, but getting the actual signature isn't supported, you have to restore to 3rd parties like BouncyCastle. So that's probably out, because it seems silly to take a dependency for that.
Really this boils down to how you register the client certificates. What I would do is ask for the certificates (or have a registration process somewhere, like, say nuget has for signing certificates), put them into the X509Certificate2 class then create a SHA256 hash of the RawData property and add that to your allow list. Then do the same for incoming client certificates and compare the SHA256 of the rawdata from the inbound certificate against your allowed list. Of course now you have to cope with certificate expiration ...
Upvotes: 2