使用子域时使用 EADDRINUSE

EADDRINUSE when using subdomains

假设您有 2 个 ASP.NET 核心项目;一个 API 和一个网站。 我想在本地(同时,因为网站使用 api)使用以下 url:devapi.website.comdev.website.com.

目前,只有当我在 Program.cs 文件中为两个项目指定不同的端口号(并在我的浏览器中使用所述端口号)时,我才能让它工作:

API

var host = new WebHostBuilder()
     .UseUrls("http://devapi.website.com:81")
     .UseKestrel()
     .UseContentRoot(Directory.GetCurrentDirectory())
     .UseIISIntegration()
     .UseStartup<Startup>()
     .Build();

网站

var host = new WebHostBuilder()
     .UseUrls("http://dev.website.com:82")
     .UseKestrel()
     .UseContentRoot(Directory.GetCurrentDirectory())
     .UseIISIntegration()
     .UseStartup<Startup>()
     .Build();

在我的主机文件中:

127.0.0.1 devapi.website.com
127.0.0.1 dev.website.com

如果我在 Program.cs 中指定相同的端口号(或者,事实上,根本 none - 我想使用端口 80),一个项目将 运行 而另一个将抛出

Microsoft.AspNetCore.Server.Kestrel.Internal.Networking.UvException: Error -4091 EADDRINUSE address already in use

启动时。

如何在不指定不同端口号的情况下同时 运行 这 2 个项目?

您尝试执行的操作是不可能的,至少在没有解决方法的情况下是不可能的。原因如下:

将 Kestrel 绑定到像 dev.website.com 这样的 DNS 名称对 Kestrel 侦听请求的方式没有任何影响。它仍然必须占用一个端口(默认为 80)。如果您尝试将两个 Kestrel 实例绑定到 80,则首先启动的那个实际上会获得端口,而另一个会出错。

将名称添加到您的主机文件并不重要;所做的只是让 devapi.website.comdev.website.com 都解析为 127.0.0.1。您只有一个端口 80 可以绑定。在您的计算机上 运行 两个 HTTP 服务器的唯一方法是将它们绑定到不同的端口。

您可以通过稍微不同的方式实现相同的功能:

  1. 将您的 Kestrel 实例绑定到单独的端口 - 80/8150080/50080
  2. 使用像 ngrok or localtunnel 这样的隧道工具来创建终止于这些端口的独立隧道。

例如,使用 localtunnel,

lt --port 50080
lt --port 50081

您将获得两个 URL,例如 https://gqgh.localtunnel.me and https://fydh.localtunnel.me,它们将指向您单独的 Kestrel 服务器。它们不在您的域中(可能是 non-starter,具体取决于您的情况),但至少它们是单独的 public URL。