Подтвердить что ты не робот

Сайт на сайтах Azure не обрабатывает X509Certificate2

У меня есть сайт на сайтах Azure (без хостинга), и мне нужно обработать сертификаты .pfx с закрытым ключом.

var x509Certificate2 = new X509Certificate2(certificate, password);

Но я столкнулся с следующим исключением:

System.Security.Cryptography.CryptographicException: The system cannot find the file specified.

   at System.Security.Cryptography.CryptographicException.ThrowCryptographicException(Int32 hr)
   at System.Security.Cryptography.X509Certificates.X509Utils._LoadCertFromBlob(Byte[] rawData, IntPtr password, UInt32 dwFlags, Boolean persistKeySet, SafeCertContextHandle& pCertCtx)
   at System.Security.Cryptography.X509Certificates.X509Certificate.LoadCertificateFromBlob(Byte[] rawData, Object password, X509KeyStorageFlags keyStorageFlags)
   at System.Security.Cryptography.X509Certificates.X509Certificate..ctor(Byte[] rawData, String password, X509KeyStorageFlags keyStorageFlags)
   at System.Security.Cryptography.X509Certificates.X509Certificate2..ctor(Byte[] rawData, String password, X509KeyStorageFlags keyStorageFlags)

В статье http://blog.tylerdoerksen.com/2013/08/23/pfx-certificate-files-and-windows-azure-websites/ я обнаружил, что это происходит, потому что по умолчанию система использует локальный каталог пользователя для хранения ключа. Но у сайтов Azure нет локального каталога профиля пользователя. В этой же статье автор предлагает использовать флаг X509KeyStorageFlags.MachineKeySet.

var x509Certificate2 = new X509Certificate2(certificate, password, X509KeyStorageFlags.MachineKeySet);

Но теперь у меня есть другое исключение:

System.Security.Cryptography.CryptographicException: Access denied.

   at System.Security.Cryptography.CryptographicException.ThrowCryptographicException(Int32 hr)
   at System.Security.Cryptography.X509Certificates.X509Utils._LoadCertFromBlob(Byte[] rawData, IntPtr password, UInt32 dwFlags, Boolean persistKeySet, SafeCertContextHandle& pCertCtx)
   at System.Security.Cryptography.X509Certificates.X509Certificate.LoadCertificateFromBlob(Byte[] rawData, Object password, X509KeyStorageFlags keyStorageFlags)
   at System.Security.Cryptography.X509Certificates.X509Certificate..ctor(Byte[] rawData, String password, X509KeyStorageFlags keyStorageFlags)
   at System.Security.Cryptography.X509Certificates.X509Certificate2..ctor(Byte[] rawData, String password, X509KeyStorageFlags keyStorageFlags)

Может кто-нибудь помочь мне понять, почему это происходит и как это исправить?

4b9b3361

Ответ 1

Я думаю, вы нашли обходное решение, но если другие борются с этим, я нашел ответ на этот вопрос в другом вопросе SO:

Как можно построить X509Certificate2 из массива байтов PKCS # 12 throw CryptographicException ( "Система не может найти указанный файл." )?

Магия задает флаги хранения X509KeyStorageFlags. Пример:

var myCertificae = new X509Certificate2(
    certificateData,
    securePasswordString,
    X509KeyStorageFlags.MachineKeySet | 
    X509KeyStorageFlags.PersistKeySet | 
    X509KeyStorageFlags.Exportable);

Ответ 3

Веб-сайты Azure работают в общей среде. Я предполагаю, что конструктор сертификата пытается создать некоторую временную информацию о экземпляре, и у него нет разрешения.

Возможно, вам придется перейти на размещенную службу, чтобы работать в повышенном контексте и выполнять эту работу.

Также, вы подтвердили правильность пароля? Если для этого не требуется пароль, вам, по крайней мере, нужно передать string.Empty для конструктора. Передача в значение NULL также приведет к этому исключению.

Ответ 4

У меня была точно такая же проблема, и я потратил много часов на ее исправление. В статье, в которой упоминается последний вызов стека, относится к функции LoadCertFromFile, но в вашем (и моем) случае это LoadCertFromBlob.

Итак, я искал LoadCertFromBlob и нашел это:

Почему X509Certificate2 иногда не удается создать из blob?

Решение заключалось в том, чтобы перейти в IIS и изменить идентификатор пула приложений с "ApplicationPoolIdentity" на "LocalService", чтобы сертификат был загружен в нужную локальную папку.

Ответ 5

В Azure Websites/Web App/Mobile App вы должны использовать план обслуживания приложений, который позволяет вам импортировать сертификат SSL, поэтому он не будет бесплатным или общим. Вы можете импортировать не только SSL-сертификат, но и пример сертификата сертификации кода и использовать его в signtool или из PowerShell.

Я использовал этот метод в https://vmplace.eu/

Если вы попытаетесь использовать бесплатный или общий план, вы получите сообщение об ошибке - поэтому в Azure в этих планах есть другая версия .NET framework.

Вы также можете обратиться к этому проекту: https://github.com/onovotny/SignService

mvpbuzz