Получение полного URL действия в ASP.NET MVC [дубликат]


этот вопрос уже есть ответ здесь:

есть ли встроенный способ получения полного URL-адреса действия?

Я ищу что-то вроде GetFullUrl("Action", "Controller") Что бы вернуть что-то вроде http://www.fred.com/Controller/Action.

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

6 343

6 ответов:

происходит перегрузка URL-адрес.Действие, которое принимает желаемый протокол (например, http, https) в качестве аргумента - если вы укажете это, вы получите полный URL-адрес.

вот пример, который использует протокол текущего запроса в метод действия:

var fullUrl = this.Url.Action("Edit", "Posts", new { id = 5 }, this.Request.Url.Scheme);

HtmlHelper (@Html) также имеет перегрузку метода ActionLink, который можно использовать в razor для создания элемента привязки, но он также требует имя хоста и параметры фрагмента. Поэтому я бы просто решил использовать @URL-адрес.Действие снова:

<span>
  Copy
  <a href='@Url.Action("About", "Home", null, Request.Url.Scheme)'>this link</a> 
  and post it anywhere on the internet!
</span>

как Пэдди отметил: если вы используете перегрузку UrlHelper.Action() что явно указывает протокол для использования, созданный URL-адрес будет абсолютным и полным, а не относительным.

Я написал сообщение в блоге под названием как построить абсолютные URL-адреса действий с помощью класса UrlHelper в котором я предлагаю написать пользовательский метод расширения для удобства чтения:

/// <summary>
/// Generates a fully qualified URL to an action method by using
/// the specified action name, controller name and route values.
/// </summary>
/// <param name="url">The URL helper.</param>
/// <param name="actionName">The name of the action method.</param>
/// <param name="controllerName">The name of the controller.</param>
/// <param name="routeValues">The route values.</param>
/// <returns>The absolute URL.</returns>
public static string AbsoluteAction(this UrlHelper url,
    string actionName, string controllerName, object routeValues = null)
{
    string scheme = url.RequestContext.HttpContext.Request.Url.Scheme;

    return url.Action(actionName, controllerName, routeValues, scheme);
}

вы можете просто использовать его, как это в вашем вид:

@Url.AbsoluteAction("Action", "Controller")

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

чтобы избежать этого, вы можете сделать следующее:

    public class Url
    {
        public string LocalUrl { get; }

        public Url(string localUrl)
        {
            LocalUrl = localUrl;
        }

        public override string ToString()
        {
            return LocalUrl;
        }
    }

    public abstract class Controller
    {
        public Url RootAction => new Url(GetUrl());

        protected abstract string Root { get; }

        public Url BuildAction(string actionName)
        {
            var localUrl = GetUrl() + "/" + actionName;
            return new Url(localUrl);
        }

        private string GetUrl()
        {
            if (Root == "")
            {
                return "";
            }

            return "/" + Root;
        }

        public override string ToString()
        {
            return GetUrl();
        }
    }

затем создайте свои контроллеры, скажем, например DataController:

    public static readonly DataController Data = new DataController();
    public class DataController : Controller
    {
        public const string DogAction = "dog";
        public const string CatAction = "cat";
        public const string TurtleAction = "turtle";

        protected override string Root => "data";

        public Url Dog => BuildAction(DogAction);
        public Url Cat => BuildAction(CatAction);
        public Url Turtle => BuildAction(TurtleAction);
    }

тогда просто используйте его как:

    // GET: Data/Cat
    [ActionName(ControllerRoutes.DataController.CatAction)]
    public ActionResult Etisys()
    {
        return View();
    }

и из вашего .cshtml (или любой код)

<ul>
    <li><a href="@ControllerRoutes.Data.Dog">Dog</a></li>
    <li><a href="@ControllerRoutes.Data.Cat">Cat</a></li>
</ul>

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

Это то, что вам нужно сделать.

@Url.Action(action,controller, null, Request.Url.Scheme)

У меня была проблема с этим, мой сервер работал за балансировщиком нагрузки. Балансировщик нагрузки завершал соединение SSL / TLS. Затем он передал запрос на веб-серверы с помощью http.

С помощью Url-адреса.Метод действия() с запросом.Url-адрес.Схема, он продолжал создавать HTTP-url, в моем случае, чтобы создать ссылку в автоматизированной электронной почте (что моему пентестеру не понравилось).

возможно, я немного обманул, но это именно то, что мне нужно, чтобы заставить https url:

<a href="@Url.Action("Action", "Controller", new { id = Model.Id }, "https")">Click Here</a>

Я на самом деле использовать веб.config AppSetting, поэтому я могу использовать http при отладке локально, но все среды тестирования и prod используют преобразование для установки значения https.

этот вопрос специфичен для ASP .NET однако я уверен, что некоторые из вас выиграют от системного агностического javascript, который полезен во многих ситуациях.

обновление: способ получения url-адреса, сформированного за пределами самой страницы, хорошо описан в ответах выше.

или вы могли бы сделать oneliner следующим образом:

new UrlHelper(actionExecutingContext.RequestContext).Action(
    "SessionTimeout", "Home", 
    new {area = string.Empty}, 
    actionExecutingContext.Request.Url!= null? 
    actionExecutingContext.Request.Url.Scheme : "http"
);

от фильтра или:

new UrlHelper(this.Request.RequestContext).Action(
    "Details", 
    "Journey", 
    new { area = productType }, 
    this.Request.Url!= null? this.Request.Url.Scheme : "http"
);

однако довольно часто нужно получить url текущей страницы, для тех случаи использования Html.Action и положить его имя и контроллер страницы вы находитесь в меня чувствует себя неловко. В таких случаях я предпочитаю использовать JavaScript. Это особенно хорошо в системах, которые наполовину переписаны MVT наполовину веб-формы наполовину VB-скрипт наполовину Бог знает что-и чтобы получить URL текущей страницы, нужно каждый раз использовать другой метод.

один из способов-использовать JavaScript для получения URL-адреса window.location.href другой - document.URL