Anyway, this is (for me) an Azure message after attempting to connect to a WCF service which has client certificate TLS enabled. What it is simply saying is that the service requires a client certificate but IIS (which is serving the site from Azure) has not been configured to require a client certificate.
There are a couple of steps to fix this on Azure (a similar process is required for IIS but I will focus on Azure).
- I will not describe any certification process but obviously you will need to set up certificates at both the service side (so the service can verify the client) and also at the client side. In Azure this generally consists of adding the relevant certificates to both the Azure portal (by uploading the relevant certificate) and in the project itself by adding the certificate(s) to the certificates list in the relevant web role.
- You will need to unlock the relevant application host section to permit the web config to include the client certificate requirement. You can do this by creating a startup batch file in your web project (make sure you save it as ASCII rather than Unicode apparently) and then ensure this is copied to the output directory in properties (I called mine startup.cmd). Then add this batch file to a startup task in the csdef file. I had to do this in the XML file rather than the gui.
- The code inside the startup.cmd file should be %windir%\System32\inetsrv\appcmd.exe unlock config /section:system.webServer/security/access
- The code inside the csdef file to get this to run (inserted between <webrole> and <sites>) was
<Startup> <Task commandLine="startup.cmd" executionContext="elevated" taskType="simple"></Task> </Startup>
- This code will allow you to add the following under system.webserver in your web.config:
- In my case, I do not want to insist on a client certificate for all connections, which is why I put sslnegotiatecert rather than sslrequirecert but you might put something else in here. I also always require ssl for the service but this is kind of taken care of under Azure by only creating an ssl endpoint.
- I think there are various ways of controlling client certificates. I think by default the service will accept any client certificate that is trusted (including its parent certificates) on the server/azure portal. Otherwise, you can specify exactly which certificates to require to provide more fine control of who can and can't connect.
- If you try and connect to the service in the browser, you should be prompted with a "choose certificate" dialog otherwise your client app can set this up in configuration or in code.
<security> <access sslFlags="Ssl, SslNegotiateCert" /> </security>