如何获取操作的完整 URL?
我正在寻找类似于 GetFullUrl("Action", "Controller")
这样的方法,以返回类似于 http://www.fred.com/Controller/Action
的 URL。
我之所以要这样做,是为了避免在生成自动化电子邮件中硬编码 URL,以便 URL 可以始终相对于站点的当前位置生成。
如何获取操作的完整 URL?
我正在寻找类似于 GetFullUrl("Action", "Controller")
这样的方法,以返回类似于 http://www.fred.com/Controller/Action
的 URL。
我之所以要这样做,是为了避免在生成自动化电子邮件中硬编码 URL,以便 URL 可以始终相对于站点的当前位置生成。
有一个Url.Action重载函数,可以把你所需的协议(如http、https)作为参数传入,如果你指定了它,就可以得到一个完全合格的URL。
以下是一个示例,它在操作方法中使用当前请求的协议:
var fullUrl = this.Url.Action("Edit", "Posts", new { id = 5 }, this.Request.Url.Scheme);
HtmlHelper (@Html) 在 Razor 中还有一个 ActionLink 方法的重载,可以用来创建锚点元素,但是它还需要 hostName 和 fragment 参数。所以我会选择再次使用 @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>
https://127.0.0.1/Home/Index
,但它生成了https://127.0.0.1:444/Home/Index
。它不能有端口。我正在运行Azure模拟器,请帮忙。 - fiberOptics<a href="@Url.Action("Login", "Account", null, Context.Request.Scheme)">登录</a>
- Chris正如Paddy所提到的:如果你使用UrlHelper.Action()
的一个重载并明确指定要使用的协议,生成的URL将是绝对和完全限定的,而不是相对的。
我写了一篇名为“如何使用UrlHelper类构建绝对操作URL的”博客文章,其中建议编写自定义扩展方法以提高可读性:
/// <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")
这是你需要做的事情。
@Url.Action(action,controller, null, Request.Url.Scheme)
这个问题是特定于ASP .NET的,但我相信一些人会从系统无关的JavaScript中受益,这在许多情况下都很有用。
更新:获取页面外部形成的URL的方法在上面的答案中得到了很好的描述。
或者您可以像以下一行代码一样简单解决:
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"
);
Html.Action
并将所在页面的名称和控制器放入其中会感到很尴尬。在这种情况下,我更喜欢使用JavaScript。特别是在系统中,它们是半重写MVT半Web表单半VB脚本半神知道什么 - 要获取当前页面的URL,每次都需要使用不同的方法。
一种使用JavaScript获取URL的方法是window.location.href
,另一种是document.URL
<a href="@Url.Action("Action", "Controller", new { id = Model.Id }, "https")">Click Here</a>
实际上,我使用了web.config的AppSetting,这样我就可以在本地调试时使用http,但是所有的测试和生产环境都使用转换来设置https值。
Request.Url.Schema
使用“当前请求”的模式来确定 HTTP vs HTTPS。如果您的锚标签是由 HTTP 请求生成的,则模式不会是 HTTPS。硬编码安全协议似乎没问题;我认为这样做并不是“作弊”,而且我很惊讶其他答案没有承认在为同时提供 HTTP 和 HTTPS 资源的站点使用 Request.Url.Schema
可能会有问题。如果需要在不同的环境中使用不同的协议,则 App Settings / Web Config 可能是最好的选择。 - Lovethenakedgun 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>
这肯定需要更多的工作,但我放心,因为编译时验证站在我的一边。