Obtenir L'URL complète de l'action dans ASP.NET MVC [duplicate]

cette question a déjà une réponse ici:

  • Comment trouver l'url absolue d'une action dans ASP.NET MVC? 9 réponses

Existe-t-il une façon intégrée d'obtenir L'URL complète d'une action?

je cherche quelque chose comme GetFullUrl("Action", "Controller") qui pourrait retournez quelque chose comme http://www.fred.com/Controller/Action .

la raison pour laquelle je cherche ceci est d'éviter le codage dur des URLs dans les e-mails automatisés qui sont générés de sorte que les URLs peuvent toujours être générés par rapport à l'emplacement actuel du site.

343
demandé sur George Stocker 2010-01-05 13:30:09

6 réponses

il y a une surcharge D'Url.Action qui prend votre protocole désiré (par exemple http, https) comme argument - si vous le spécifiez, vous obtenez une URL entièrement qualifiée.

voici un exemple qui utilise le protocole de la requête courante dans une méthode d'action:

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

HtmlHelper (@Html) a également une surcharge de la méthode ActionLink que vous pouvez utiliser dans razor pour créer un élément d'ancrage, mais il nécessite également le nom d'hôte et le fragment paramètre. Donc j'ai juste choisi d'utiliser @Url.Action:

<span>
  Copy
  <a href='@Url.Action("About", "Home", null, Request.Url.Scheme)'>this link</a> 
  and post it anywhere on the internet!
</span>
522
répondu Paddy 2017-11-06 16:12:09

comme Paddy l'a mentionné: si vous utilisez une surcharge de UrlHelper.Action() qui spécifie explicitement le protocole à utiliser, L'URL générée sera absolue et pleinement qualifiée au lieu d'être relative.

j'ai écrit un billet de blog intitulé comment construire des URLs d'action absolue en utilisant la classe UrlHelper dans lequel je suggère d'écrire une méthode d'extension personnalisée pour des raisons de lisibilité:

/// <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);
}

You peut alors simplement l'utiliser comme cela dans votre point de vue:

@Url.AbsoluteAction("Action", "Controller")
129
répondu Marius Schulz 2018-02-09 22:26:23

c'est peut-être juste moi étant vraiment, vraiment difficile, mais j'aime définir les constantes une seule fois. Si vous utilisez l'une des approches définies ci-dessus, votre constante d'action sera définie plusieurs fois.

Pour éviter cela, vous pouvez faire ce qui suit:

    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();
        }
    }

alors créez vos controllers, par exemple le 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);
    }

alors utilisez - le comme:

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

et du votre. CSHTML (ou tout autre code)

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

c'est certainement beaucoup plus de travail, mais je reste tranquille en sachant que la validation du temps de compilation est de mon côté.

0
répondu Jorge Aguirre 2017-01-28 05:56:04

Ce que vous devez faire.

@Url.Action(action,controller, null, Request.Url.Scheme)
0
répondu Salman Zahid 2017-01-31 09:07:48

j'avais un problème avec ça, mon serveur fonctionnait derrière un équilibreur de charge. Le répartiteur de charge terminait la connexion SSL/TLS. Il a ensuite transmis la requête aux serveurs Web en utilisant http.

utilisant L'Url.Action () méthode avec demande.URL.Schema, il a continué à créer une url http, dans mon cas pour créer un lien dans un e-mail automatisé (ce que mon PenTester n'a pas aimé).

j'ai triché un peu, mais c'est exactement ce dont j'avais besoin forcer une url https:

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

j'utilise une toile.configuration de L'application pour que je puisse utiliser http lors du débogage local, mais tous les environnements de test et prod utilisent la transformation pour définir la valeur https.

0
répondu Matt D 2017-05-12 15:51:42

cette question est spécifique à ASP .NET cependant je suis sûr que certains d'entre vous bénéficieront du JavaScript système agnostique qui est bénéfique dans de nombreuses situations.

mise à jour: la façon d'obtenir l'url formée en dehors de la page elle-même est bien décrite dans les réponses ci-dessus.

ou vous pouvez faire un oneliner comme suit:

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

du filtre ou:

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

cependant très souvent, on a besoin d'obtenir l'url de la page actuelle, pour ces cas en utilisant Html.Action et en mettant le nom et le contrôleur de la page vous êtes dans à moi se sent mal à l'aise. Ma préférence dans de tels cas est D'utiliser JavaScript à la place. Cela est particulièrement bon dans les systèmes qui sont Mi - réécrit MVT mi-web-formes mi - VB-script mi-Dieu sait quoi-et pour obtenir L'URL de la page actuelle, il faut utiliser une méthode différente à chaque fois.

une façon d'utiliser JavaScript pour obtenir L'URL est window.location.href un autre - document.URL

0
répondu Matas Vaitkevicius 2017-11-01 12:19:48