ASP.NET Core 2.1 получает текущее имя и порт в Startup.cs

Я хочу зарегистрировать мой WebAPI для обнаружения службы Consul, и для этого я должен предоставить URL моего WebAPI (например: http://service1.com) и конечную точку проверки работоспособности (http://service1.com/health/check). Как я могу получить этот URL?

Я нашел этот кусок кода:

var features = app.Properties["server.Features"] as FeatureCollection;
var addresses = features.Get<IServerAddressesFeature>();
var address = addresses.Addresses.First();               
var uri = new Uri(address);

Возвращает 127.0.0.1:16478 вместо localhost: 5600. Я думаю, что первый используется dotnet.exe, а второй - IIS, который пересылает 5600 в 16478. Как я могу получить localhost: 5600 в Startup.cs?

Ответ 1

Я не думаю, что это возможно, поскольку в производстве обычно используется обратный прокси-сервер, который обрабатывает публичный адрес, а само приложение не должно быть открыто для публики и, следовательно, должно быть осведомлено о публичном адресе. Но могут быть некоторые обходные пути:

  1. URL-адрес места - это своего рода файл конфигурации, который можно обновить на этапах развертывания, чтобы получить правильный URL-адрес.
  2. Приложение может получить полный URL-адрес запроса , например, поэтому после первого фактического запроса к приложению мы можем получить имя хоста.

Ответ 2

Ну, есть несколько решений этой проблемы. Ваш адрес:

string myurl = $"{this.Request.Scheme}://{this.Request.Host}{this.Request.PathBase}";

Возвращает 127.0.0.1:16478 вместо localhost: 5600

Вы правильно поняли, да. Один из IIS, другой из dotnet. Итак, у вас есть проблема с попыткой получить правильный URL. Итак, что произойдет, если ваш сервис находится за обратным прокси? https://en.wikipedia.org/wiki/Reverse_proxy

Тогда ваш сервис не будет напрямую подключен к интернету, но запросы, сделанные на определенный URL, будут переданы с обратного прокси на ваш сервис. Кроме того, вы можете настроить обратный прокси-сервер для пересылки дополнительных заголовков, указывающих, откуда поступил исходный запрос. Я думаю, что большинство обратных прокси используют X-Forwarded-For (некоторые из них используют X-Original-Host и т.д.).

Так что, если у вас установлен правильный заголовок на RP, вы можете получить URL-адрес следующим образом:

url = url.RequestContext.HttpContext.Request.Headers["X-Forwarded-For"]

URL имеет тип UrlHelper. Чтобы упростить этот метод, вы можете создать метод расширения (GetHostname (этот URL UrlHelper)), а затем использовать его в вашем контроллере или где угодно. Надеюсь, это поможет

Ответ 3

РЕДАКТИРОВАТЬ: я перечитал ваш вопрос. Вы хотели знать, как это сделать в Startup.cs. Вы можете, но с меньшим количеством откатов. Ваш единственный выбор - конфигурация или необработанный DNS.GetHostName(), которые не идеальны. Вместо этого, при любом запросе к вашему сервису, лениво регистрируйте ваш API. Это когда у вас есть контекст. До этого ваш сервис ничего не знает Джон Сноу. Первым запросом к вашему API, скорее всего, будет проверка работоспособности, поэтому с регистрации у консула начнется регистрация.

Решение, которое я использовал, представляет собой комбинацию конфигурации и заголовков в альтернативном сценарии.

Сначала положитесь на заголовок X-Forwarded-For. Если есть случаи, когда это не применимо или вам необходимо... вы можете вернуться к настройке.

Это работает для вашего случая использования, обнаружения. Тем не менее, это также работает, когда вы хотите генерировать ссылки по любой причине (например, для гипермедиа для JSON API или вашей собственной реализации REST).

Откат может быть полезен, когда происходят изменения конфигурации, и у вас есть источник динамической конфигурации, который не требует повторного развертывания.

В мире ASP.NET Core вы можете создать класс и внедрить его в свои контроллеры и службы. Этот класс будет иметь метод, который знает, что сначала нужно попытаться выполнить конфигурацию (чтобы увидеть, требуется ли переопределение), а затем заголовок X-Forwarded-For, и, если ни один из них не подходит, перейдите к HttpContext.Request для получения соответствующих частей URI.

То, что вы делаете, это позволяет вашему API быть безконтекстным и гибким (изменяться), давая ему некоторую контекстную информацию о том, где "он живет".

Ответ 4

Это происходит, когда вы пытаетесь получить текущий URL в Startup.cs. Я сталкивался с этой проблемой раньше. То, что я сделал в качестве решения для моей проблемы. Я только что объявил пользовательскую настройку в AppSettings в файле web.config (для локального) и web.release.config (для живого) как после


в web.config

<appSettings>
    <add key="MyHost" value="http://localhost:5600" />
</appSettings>

в web.release.config

<appSettings>
    <add key="MyHost" value="http://myLiveURL.com" />
</appSettings>

в startup.cs

string hostSetting = ConfigurationSettings.AppSettings["MyHost"];

И другой хост в файле релиза. так что мне помогло то, что я могу получить локальный URL-адрес на локальном веб-сайте из web.config и прямой URL-адрес из web.release.config.

если вы используете Azure для жизни. это будет проще для жизни (вам не нужно добавлять файл настроек web.release.config). добавить настройки приложения в настройках приложения на вашем веб-сайте https://docs.microsoft.com/en-us/azure/app-service/configure-common

В случае ASP.NET Core вы можете использовать appsettings.json вместо web.config