I'm trying to consume one SSL SOAP service but I'm having this error in runtime. These are the steps I have done to install the certificate.
1. Imported the pfx certificate into mmc;2. Gave permissions to Network_Service
I used the extension method to manipulate the version on TLS used but the error persists!
Below is the code i have done in the extension method.
System.Net.ServicePointManager.SecurityProtocol =
SecurityProtocolType.Tls12;
System.Net.ServicePointManager.Expect100Continue = false;
System.Net.ServicePointManager.UseNagleAlgorithm = false;
System.Net.ServicePointManager.DefaultConnectionLimit = 10;
X509Certificate2 clientCert = GetCertificateFromStore(ssCertThumbprint);
var handler = new HttpClientHandler
{
//SslProtocols = SslProtocols.Tls12,
AllowAutoRedirect = false,
UseCookies = false,
AutomaticDecompression =
DecompressionMethods.GZip |
DecompressionMethods.Deflate
};
handler.ClientCertificates.Add(clientCert);
// handler.SslProtocols = SslProtocols.Tls12;
//handler.ServerCertificateCustomValidationCallback =
// (message, cert, chain, errors) => true;
using (var client = new HttpClient(handler))
client.Timeout = TimeSpan.FromSeconds(120);
client.DefaultRequestHeaders.Clear();
client.DefaultRequestHeaders.Add("SOAPAction", ssSoapAction);
client.DefaultRequestHeaders.Host =
"" (Service Host name here)
client.DefaultRequestHeaders.ConnectionClose = true;
var content = new StringContent(
ssSoapRequestXml,
Encoding.UTF8,
"text/xml"
);
var response = client.PostAsync(
"" (Service URL here),
content
).GetAwaiter().GetResult();
//Result;
ssSoapResponseXml =
"HTTP Status: " + response.StatusCode +
" | Headers: " + response.Headers.ToString() +
" | Body: " + response.Content.ReadAsStringAsync().Result;
//ssSoapResponseXml = response.Content.ReadAsStringAsync().Result;
ssIsSuccess = response.IsSuccessStatusCode;
Any idea why i am still getting "Could not create SSL/TLS secure channel" error.
Dear,
There could be multiple reasons for the issue encountered. To help us investigate and identify the root cause, please confirm the following points:
Are you accessing the service from a cloud environment or an on-premise server?
Please confirm whether the SSL configuration is one-way (server-side SSL only) or two-way (mutual SSL).
Ensure that the certificate is accessible from the configured path. If the application is deployed across multiple servers, please verify that the certificate is installed and available on all front-end servers.
Kindly confirm with the service provider whether TLS 1.2 is supported and being used.
Verify that the complete certificate chain is installed. In some cases, the root certificate may be installed, but the intermediate certificate may be missing.
If possible, please validate the service using Postman to check connectivity outside the application.
Please share the service logs for further analysis and root cause identification.
Thanks and regards,
Vignesh Sekar
Hi Asha,
Looking at your code, the certificate loading and HttpClient setup look structurally correct, so the issue is likely something subtle. Here's what I'd check:
1. Verify the certificate is actually loaded with its private key
Add a quick check right after loading the certificate:
if (clientCert == null)
throw new Exception("Certificate not found for thumbprint: " + ssCertThumbprint);
if (!clientCert.HasPrivateKey)
throw new Exception("Certificate found but private key is not accessible.");
If HasPrivateKey is false, the certificate is silently ignored during the TLS handshake and the server sees no client certificate at all. This produces exactly the error you're getting.
Also a minor note on your SecurityProtocol line: you're using = Tls12, which removes all other protocol versions for the entire IIS process. Consider using |= instead (SecurityProtocol |= SecurityProtocolType.Tls12) to add TLS 1.2 without affecting other outbound connections that may need different versions.
2. Check the actual IIS Application Pool identity
You gave permissions to Network_Service, but the OutSystems IIS Application Pool may run under a different account. To verify: open IIS Manager, go to Application Pools, find the pool used by your module (check your module's virtual directory under Default Web Site > Advanced Settings > Application Pool), then click the pool > Advanced Settings > Identity. Whatever account is listed there is the one that needs private key access in certlm.msc > your cert > right-click > All Tasks > Manage Private Keys.
3. Thumbprint hidden character
When you copy the thumbprint from the Windows certificate UI, it often includes an invisible Unicode character (left-to-right mark) at the start. If your GetCertificateFromStore uses FindByThumbprint, this will silently return no results. Paste the thumbprint into Notepad, place the cursor before the first character, and press Delete once. If the cursor doesn't move but a character was deleted, that was the hidden character.
4. Check the certificate chain
Even if the client certificate loads correctly, the remote server may reject the handshake if the intermediate or root CA certificates are missing. Run certutil -dump yourcert.pfx from a command prompt on the server to see everything inside the PFX. If it only contains the client cert without the CA chain, import the issuing CA certificates into the Trusted Root Certification Authorities and Intermediate Certification Authorities stores in certlm.msc.
5. Try uncommenting SslProtocols on the handler
On some .NET Framework configurations, HttpClientHandler needs the TLS version set explicitly on the handler itself, not just on ServicePointManager:
handler.SslProtocols = System.Security.Authentication.SslProtocols.Tls12;
6. Quick isolation test
If the above doesn't help, try temporarily uncommenting ServerCertificateCustomValidationCallback (the line you have commented out that returns true). If that throws a PlatformNotSupportedException (which can happen on .NET Framework under IIS), use ServicePointManager.ServerCertificateValidationCallback = (sender, cert, chain, errors) => true; instead. If the error disappears with either approach, the problem is server certificate trust, not client certificate. That would mean the server's SSL certificate or its CA is not trusted by your OutSystems server. If the error persists even with that callback, the problem is definitely on the client certificate / TLS negotiation side.
One more thing worth mentioning: you're currently building the SOAP request manually with HttpClient and raw XML. This works, but it's the most fragile of the three approaches available in OutSystems. The alternatives are (a) consuming the WSDL natively in Service Studio and using the SOAP Extensibility Forge component to attach the certificate via the OnBeforeRequestAdvanced callback, or (b) generating a WCF proxy via Add Service Reference in Visual Studio and using it inside the extension. Both give you typed request/response objects and, in the case of option (a), structured logging in Service Center. Worth considering once you get past the certificate issue.
Also, if you're still blocked on the WSDL import error from your other post: the WSDL fetch goes through the Platform Server, which in my experience does not present client certificates during the import. The workaround is to download the WSDL file manually (SoapUI can do it since it already connects) and consume it from a local file path in Service Studio.
Can you share the output of checks 1 and 2? That will narrow it down quickly.Hope this helps!