我有一个带有.NET应用程序的docker容器,代码如下:
var pgsql = OpenDbConnection("Server=localhost;Database=postgres;Username=postgres;Password=MyPass;Port=5432");
private static NpgsqlConnection OpenDbConnection(string connectionString)
{
NpgsqlConnection connection;
Console.Error.WriteLine("Connecting to DB");
while (true)
{
try
{
connection = new NpgsqlConnection(connectionString);
connection.Open();
break;
}
catch (SocketException e)
{
Console.WriteLine("{0} Exception caught.", e);
Thread.Sleep(1000);
}
catch (DbException)
{
Console.Error.WriteLine("Waiting for db - db error");
Thread.Sleep(1000);
}
}
return connection;
}
我有一个与官方Postgres容器不同的容器,我从命令
开始docker run --name localpg -e POSTGRES_PASSWORD=MyPass -d postgres -p 5432:5432
现在我可以从pgAdmin与主机localhost
,用户和密码postgres
以及密码MyPass
建立联系。
但是,如果我尝试使用命令docker run worker
从同一台计算机上运行上面的.NET代码,我会遇到以下异常:
System.Net.Sockets.SocketException: Unknown error -1
at Npgsql.NpgsqlConnector.Connect(NpgsqlTimeout timeout)
at Npgsql.NpgsqlConnector.RawOpen(NpgsqlTimeout timeout)
at Npgsql.NpgsqlConnector.Open(NpgsqlTimeout timeout)
at Npgsql.ConnectorPool.Allocate(NpgsqlConnection conn, NpgsqlTimeout timeout)
at Npgsql.NpgsqlConnection.OpenInternal()
at Worker.Program.OpenDbConnection(String connectionString) Exception caught.
有什么想法吗?
修改
遵循Dan的建议我将连接字符串更改为
var pgsql = OpenDbConnection("Server=localpg;Database=postgres;Username=postgres;Password=MyPass;Port=5432");
但仍无效(InternalSocketException: No such device or address
)。
$ docker network ls
NETWORK ID NAME DRIVER SCOPE
ad8fa68b5dab bridge bridge local
984027aadc2a host host local
5604001734fa none null local
使用docker run worker
启动应用容器(不使用撰写)。
答案 0 :(得分:3)
这里有两个容器,一个运行.Net应用程序,另一个运行Postgres数据库。从您的.Net应用程序容器的角度来看,本地主机(.Net容器)上没有运行Postgres,但您正在尝试连接到localhost:
var pgsql = OpenDbConnection("Server=localhost;Database=postgres; ...");
您的两个容器是分开的,每个容器都有自己的 localhost。要连接到Postgres容器,请使用其名称,就好像它是主机名一样。根据您在问题中发布的docker run
命令判断,您应该使用:
var pgsql = OpenDbConnection("Server=localpg;Database=postgres; ...");
您可以使用pgAdmin在localhost:5432
上连接到Postgres的原因是您已将端口5432从Docker导出到外部主机(运行Docker的计算机)。这就是-p 5432:5432
在docker run
命令中正在做的事情。
在该系统的localhost上,端口5432绑定到容器中的Postgres。 (这是第三个本地主机,与每个容器内部的localhost分开。)