I am trying to use a new feature of Windows 8.1 and Windows Phone 8.1, namely certificate stores and the ability to use client certificates to authenticate clients on the server side. However, I am having problems with this functionality.
I have a basic WCF test service that runs on IIS express. IIS express is configured to support SSL and client certificates. In the IIS configuration file (configurationhost.config), I installed this:
<access sslFlags="SslRequireCert" /> (tried also SslNegotiateCert) <clientCertificateMappingAuthentication enabled="true" />
I added the client certificate to the Windows RT application as shown below:
//Install the self signed client cert to the user certificate store string CACertificate = null; try { Uri uri = new Uri("ms-appx:///Assets/AdventureWorksTestClient1.pfx"); var file = await Windows.Storage.StorageFile.GetFileFromApplicationUriAsync(uri); IBuffer buffer = await FileIO.ReadBufferAsync(file); using (DataReader dataReader = DataReader.FromBuffer(buffer)) { byte[] bytes = new byte[buffer.Length]; dataReader.ReadBytes(bytes); // convert to Base64 for using with ImportPfx CACertificate = System.Convert.ToBase64String(bytes); } await CertificateEnrollmentManager.UserCertificateEnrollmentManager.ImportPfxDataAsync( CACertificate, "", ExportOption.Exportable, KeyProtectionLevel.NoConsent, InstallOptions.None, "ClientCert1"); } catch (Exception ex) {...
Then I use HttpBaseProtocolFilter, to which I add the client certificate as follows:
IReadOnlyCollection<Certificate> certs = await CertificateStores.FindAllAsync(query); HttpBaseProtocolFilter bpf = new HttpBaseProtocolFilter(); if (certs.Count > 0) { cert = certs.ElementAt(0); bpf.ClientCertificate = cert; } HttpClient httpClient = new HttpClient(bpf); ....
And then request:
var resp = await httpClient.GetAsync(new Uri(serviceURL));
This line of code throws this exception:
{System.Exception: Exception from HRESULT: 0x80072F7D at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task) at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task) at System.Runtime.CompilerServices.TaskAwaiter`1.GetResult() at JumpStartCertificateDemo.MainPage.<btnCallService_Click>d__0.MoveNext()}
I am 100% sure that I imported the correct certificates also on localhost (local computer), as well as on the application side. Calling a service through a browser is working correctly. (I am invited to provide a client certificate), so there must be some problem with the provision of the client certificate in the application.
Can someone help me with this please? Thank.