我有一个 SQL 服务器版本
12.0.6205
以及 .Net Core 3.1(或 6)Web Api 控制器中的以下代码:
var builder = new SqlConnectionStringBuilder
{
DataSource = DataSource,
UserID = UserID,
Password = Password,
InitialCatalog = InitialCatalog,
ApplicationIntent = ApplicationIntent.ReadWrite,
// Same result if true/true
Encrypt = false,
TrustServerCertificate = false
};
var connection = new SqlConnection(builder.ToString());
using (var cmd = new SqlCommand() { Connection = connection, CommandText = "SELECT TOP 1 * FROM [dbo].[Table]" })
{
connection.Open(); // Breaks here
var reader = cmd.ExecuteReader();
Console.WriteLine(reader.HasRows);
}
此代码在本地运行没有问题,但在 Azure 的应用程序服务中执行时,在打开以下连接时会中断:
System.Data.SqlClient.SqlException (0x80131904): A connection was successfully established with the server, but then an error occurred during the pre-login handshake. (provider: SSL Provider, error: 31 - Encryption(ssl/tls) handshake failed)
如果创建的话,我也能够在本地重现错误 基于
appsvc/dotnetcore
(任何标签) 的 docker 镜像
FROM mcr.microsoft.com/appsvc/dotnetcore:3.1-latest_20220105.1
ENV ASPNETCORE_URLS=http://+:80
EXPOSE 8080
WORKDIR /home/site/wwwroot/
COPY . .
ENTRYPOINT ["dotnet", "Test.dll"]
就像 @DraggonDragger 所说,这是一个 TLS 问题,但在我的具体情况下,我不能依赖更新的 SQL 服务器来允许 TLS 1.2,因此我必须在应用程序中允许 TLS 1.0。
我最终遵循了这个答案:https://stackoverflow.com/a/61523341/17892120;
本质上,对于 docker 镜像,添加这一行就足够了:
RUN sed -i 's/DEFAULT@SECLEVEL=2/DEFAULT@SECLEVEL=1/g' /etc/ssl/openssl.cnf
对于 Azure 的应用服务,我们可以添加
sed -i 's/DEFAULT@SECLEVEL=2/DEFAULT@SECLEVEL=1/g' /etc/ssl/openssl.cnf && dotnet Test.dll
用于启动命令。
为了将来参考,GitHub 中也有关于此的讨论,link。
RUN sed -i 's/DEFAULT@SECLEVEL=2/DEFAULT@SECLEVEL=1/g' /etc/ssl/openssl.cnf
到 ENTRYPOINT 正上方的 Dockerfile
在GitHub中发现了类似的问题,即 SQL Server Pre-Login Handshake with Docker Image 中的 TLS HandShake Failure。
此外,此错误通常发生在 docker 映像容器、Unix 客户端或 Windows 客户端等客户端环境中,其中 TLS 1.2 是支持的最低 TLS 协议。
在受支持的 SQL Server1 版本上安装最新更新,并确保服务器上启用 TLS 1.2 协议。
如果您使用的是 Windows 并使用 Docker for SQL Server:
sudo docker run -e "ACCEPT_EULA=Y" -e 'MSSQL_SA_PASSWORD=YourStrongPassword' -p 1434:1433 --name sql1 --hostname sql1 -d mcr.microsoft.com/mssql/server
确保端口映射避免与 Windows 上的其他服务发生冲突。如有必要,请使用不同的外部端口(例如 1434)以避免冲突。请注意,SQL Server 的 SSL 端口默认为 1433。使用映射端口连接 SSMS 并确保相应配置 TLS 设置。