I am building a Web Api (using ASP.NET Web API), that connects via Secure WebSockets to an endpoint that our client exposed (wss://client-domain:4747/app/engineData
). They gave me their certificates all in .pem format (root.pem
and client.pem
), and a private key (client_key.pem
).
In order to get this done I did the following:
1) Converted client.pem
and client_key.pem
to a single .pfx
file (used this here: Convert a CERT/PEM certificate to a PFX certificate)
2) I used the library System.Net.WebSockets
, and wrote the following code:
private void InitWebSockesClient()
{
client = new ClientWebSocket();
client.Options.SetRequestHeader(HEADER_KEY, HEADER_VALUE); //Some headers I need
AddCertificatesSecurity();
}
private void AddCertificatesSecurity()
{
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls
| SecurityProtocolType.Tls11
| SecurityProtocolType.Tls12;
// I KNOW THIS SHOULDNT BE USED ON PROD, had to use it to make it
// work locally.
ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };
X509Certificate2 x509 = new X509Certificate2();
// this is the pfx I converted from client.pem and client_key
byte[] rawData = ReadFile(certificatesPath + @"\cert.pfx");
x509.Import(rawData, "123456", X509KeyStorageFlags.UserKeySet);
X509Certificate2Collection certificateCollection = new X509Certificate2Collection(x509);
client.Options.ClientCertificates = certificateCollection;
}
And when I want to connect I call:
public async Task<bool> Connect()
{
Uri uriToConnect = new Uri(URL);
await client.ConnectAsync(uriToConnect, CancellationToken.None);
return client.State == WebSocketState.Open;
}
This works fine locally. But whenever I deploy my Web Api on Azure (App Service) and make an HTTP request to it, it throws:
System.Net.WebSockets.WebSocketException - Unable to connect to the remote server.
And the inner exception:
System.Net.WebException - The request was aborted: Could not create SSL/TLS secure channel.
I enabled WebSockets on the AppService instance.
If I delete the line that always return true for the certificate validation, it doesn't work even locally, and the message says something like:
The remote certificate is invalid according to the validation procedure.
So definitely I got something wrong with the certificates, those three .pem files are being used right now in a similar [![enter image description here][1]][1]app in a node.js and work fine, the WSS connection is established properly. I don't really know what usage give to each one, so I am kind of lost here.
These are the cipher suites of the domain I want to connect: https://i.stack.imgur.com/ZFbo3.png