无法从同一主机上的Web应用程序泊坞窗访问docker托管的SQL Server

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了无法从同一主机上的Web应用程序泊坞窗访问docker托管的SQL Server相关的知识,希望对你有一定的参考价值。

在同一个虚拟机(远程,ubuntu)上,我有

  • 在Docker中运行的SQL Server
  • 在docker中运行的.NET Core 2.2(IdentityServer)应用程序
  • jwilder.nginx-proxy的一个实例,用作机器上每个Web应用程序的反向代理
  • 众多其他.NET核心应用程序

我可以使用机器IP +端口和域名连接到我的所有网站,这意味着反向代理按预期工作,并且码头工具配置良好

我可以使用本地计算机上的SSMS连接到SQL Server,这意味着SQL Server docker正确地在端口1433上转发TCP连接

IdentityServer .NET Core 2 Web应用程序在本地计算机上运行时能够连接到SQL Server。

远程docker IdentityServer应用程序无法访问SQL Server实例,并出现以下错误(为清楚起见,缩短了 - 删除了堆栈跟踪)

System.Data.SqlClient.SqlException (0x80131904)

建立与SQL Server的连接时发生与网络相关或特定于实例的错误。服务器未找到或无法访问。验证实例名称是否正确,以及SQL Server是否配置为允许远程连接。

(提供者:TCP Provider, error: 40 - 无法打开与SQL Server的连接)[...]

我知道SQL服务器正在运行并且可以从Internet访问,我知道应用程序的代码没有错,因为我测试了它们。

所以我推断它必须是阻止连接的IdentityServer docker。所以我尝试过:

  • 在IdentityServer docker上使用--expose 20命令
  • 除了已经暴露的端口80之外,打开将容器内的端口20映射到-p 45264:20外部的某个端口
  • 我最初使用映射两侧的端口1433,但由于它不起作用,我尝试使用外部的其他端口(20)。没有改变什么

以下是IdentityServer使用的连接字符串(隐藏敏感数据):

Data Source=***.***.***.***,20;Initial Catalog=Identity;Persist Security Info=True;User ID=**;Password=******************

为什么我的IdentityServer docker无法访问SQL Server docker,而SQL Server本身是完全可访问的?如何使此设置有效?

答案

将SQL Server包装到Docker时,首先要预测的是连接方式。 SQL Server更喜欢命名管道,您必须将模式显式设置为tcp

如果在本地完成连接,请不要使用localhost,将其更改为127.0.0.1。另外写明确的tcp:前缀可能会有所帮助,如下所示:Server=tcp:x.y.z.q,1433

另一答案

据我所知,您在单独的docker容器中运行Sql Server和IdentityServer(具有连接问题)。

如果是这样,那么引用localhost(即127.0.0.1)是不正确的。因为在这种情况下IdentityServer会尝试连接到自身。如果IdentityServer已在主机上运行,​​那么这将起作用,因为您将SQL Server端口转发给它。但在您的情况下,您应该连接到SQL服务器容器IP。考虑到以上所有内容,我看到了三个选项供您解决:

  1. 您可以通过运行docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' <sql_container_name_or_id>获取SQL Server容器的IP地址
  2. 通过docker run --ip <static_ip_value> <sql_container_name_or_id>运行带有静态IP的SQL容器,然后使用您在连接字符串中指定的静态IP。
  3. 通过docker run --hostname <sql_host_name> <sql_container_name_or_id>运行具有指定主机名的SQL容器,然后在连接字符串中使用指定的主机名。

这取决于你走哪条路。

另一答案

使用tcp,127.0.0.1和主机端口进行连接。在身份服务器docker设置中提到它依赖于sql数据库服务器容器。像这样,

identityservice:
   ...
   depends_on:
      - sqldataservice

这样,数据库容器将首先可用。

"ConnectionString": "Server=tcp:127.0.0.1,8433;Database=dbname;User Id=sa;Password=abc@1234;"
另一答案

我最终放弃了使用单个主机让它工作,所以我只是决定让SQL Server在一台单独的机器上运行。

以上是关于无法从同一主机上的Web应用程序泊坞窗访问docker托管的SQL Server的主要内容,如果未能解决你的问题,请参考以下文章

Azure 应用服务泊坞窗容器“服务不可用”

作曲家内存限制泊坞窗

多容器泊坞窗(AWS)链接是单向的吗?

sh MacOSX泊坞窗 - 输入泊坞窗实例

从容器内部构建并推送泊坞窗图像

sh 标记并推送泊坞窗图像到泊坞窗集线器