У нас проблема с другом при загрузке личного сертификата в httpHandler.
Мы используем ядро .net и нам нужно разместить все приложения в облаке.
Основная цель - получить сообщение из SQS ивыполнить некоторые указанные снимки API после использования данных.
У нас проблема с сертификатом с открытым / закрытым ключом.Мы попробовали, я думаю, все возможные способы его загрузки.
public async Task<HttpResponseMessage> VisitHttps()
{
// Proceed for an invalid cerficate
ServicePointManager.ServerCertificateValidationCallback +=
(sender, certificate, chain, sslPolicyErrors) => true;
// Add the certificate
var handler = new HttpClientHandler();
var cert = GetMyCert();
if (cert != null)
{
handler.ClientCertificates.Add(cert);
handler.ClientCertificateOptions = ClientCertificateOption.Manual;
handler.SslProtocols = System.Security.Authentication.SslProtocols.Tls12;
//handler.PreAuthenticate = true;
}
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls;
HttpClient cclient = new HttpClient(handler)
{
//BaseAddress = new Uri("https://someurl.com")
};
cclient.DefaultRequestHeaders.Accept.Clear();
cclient.DefaultRequestHeaders.Accept.Add(new
MediaTypeWithQualityHeaderValue("application/json"));
return await cclient.GetAsync("https://some-url.com/ping"); }
И метод GetMyCert () выглядит следующим образом:
string currentLocation = $"{AppDomain.CurrentDomain.BaseDirectory}key-public.crt";
//var xcert = new X509Certificate2(currentLocation, "password");
////var currentLocationPriv = $"{AppDomain.CurrentDomain.BaseDirectory}key-private.crt";
////var privcert = new X509Certificate2(currentLocationPriv, "password", X509KeyStorageFlags.EphemeralKeySet);
//var certStore = new X509Store(StoreName.My, StoreLocation.CurrentUser);
//certStore.Open(OpenFlags.ReadWrite);
//certStore.Add(xcert);
//certStore.Close();
//return xcert;
X509Store store = new X509Store("My", StoreLocation.CurrentUser);
X509Certificate2 cert;
cert = new X509Certificate2(File.ReadAllBytes(currentLocation), "password", X509KeyStorageFlags.MachineKeySet);
bool result = cert.Verify();
var r2 = result;
return cert;
закомментированные строки - это отклонения от того, что мы пытались сделать.
Мы понятия не имеем, что еще мы можемдолжен попытаться решить эту проблему.
Любые рекомендации будут более чем приветствоваться
РЕДАКТИРОВАТЬ:
Я пытался зарегистрировать это в классе запуска, но, похоже, все равно не работает.Я всегда получал пустое поле секретного ключа внутри сертификата.И hasPrivateKey помечен как ложный.
private void CreateCert(IServiceCollection services)
{
string currentLocation = $"{AppDomain.CurrentDomain.BaseDirectory}key-public.crt";
var certificate = new X509Certificate2(currentLocation, "password");
services.AddHttpClient("TestClient", client =>
{
client.BaseAddress = new Uri("https://someurl.com");
})
.ConfigurePrimaryHttpMessageHandler(() =>
{
var handler = new HttpClientHandler();
handler.ClientCertificates.Add(certificate);
return handler;
});
}
Мой тестовый код:
[Fact]
public async Task ShouldPong()
{
var testClient = new TestClient()
{
BaseAddress = new Uri("https://someurl.com")
};
var result = await testClient.GetAsync("/ping");
result.StatusCode.Should().Be(HttpStatusCode.OK);
}
TestClient:
public class TestClient : HttpClient
{
public TestClient()
:base()
{
}
public TestClient(HttpMessageHandler handler)
: base(handler)
{
}
}
РЕДАКТИРОВАТЬ:
Проблема была решена при изменениифайлы .crt в файл .pfx.Поскольку API, который мы использовали, был размещен на nginx.