ASP.NET MVC相对路径

ASP.NET MVC Relative Paths

在我的应用程序中,我经常需要使用相对路径。例如,当我引用jquery时,我通常这样做:

1
<script type="text/javascript" src="../Scripts/jquery-1.2.6.js">

现在我正在向MVC过渡,我需要考虑页面相对于根目录可能具有的不同路径。在过去,这当然是URL重写的一个问题,但我设法通过使用一致的路径来解决它。

我知道标准解决方案是使用绝对路径,例如:

1
<script type="text/javascript" src="/Scripts/jquery-1.2.6.js">

但这对我来说并不像在开发周期中那样有效,我必须部署到一个测试机器上,在这个机器上,应用程序将在一个虚拟目录中运行。根相对路径在根更改时不起作用。另外,出于维护的原因,在部署测试期间,我不能简单地更改所有路径——这本身就是一个噩梦。

那么,最好的解决方案是什么?

编辑:

由于这个问题仍然在接收视图和答案,我认为应该谨慎地更新它,以注意到在RazorV2中,对根相对URL的支持已经成熟,因此您可以使用

1
<img src="~/Content/MyImage.jpg">

如果没有任何服务器端语法,视图引擎将自动用当前站点根目录替换~/。


试试这个:

1
<script type="text/javascript" src="<%=Url.Content("~/Scripts/jquery-1.2.6.js")%>">

或者使用mvcontrib执行以下操作:

1
<%=Html.ScriptInclude("~/Content/Script/jquery.1.2.6.js")%>


虽然是一篇旧文章,但新读者应该知道Razor2和更高版本(MVC4+中的默认版本)完全解决了这个问题。

带剃刀1的旧MVC3:

1
Application home page

带有Razor 2和更高版本的新MVC4:

1
Application home page

没有像语法那样笨拙的剃刀功能。没有非标准标记。

在任何HTML属性中用波浪线("~")前缀一个路径,都会告诉Razor2通过替换正确的路径"使其工作"。太棒了。


断开变化-MVC 5

注意MVC 5的突破性变化(摘自MVC 5发行说明)

Url Rewrite and Tilde(~)

After upgrading to ASP.NET Razor 3 or ASP.NET MVC 5, the tilde(~)
notation may no longer work correctly if you are using URL rewrites.
The URL rewrite affects the tilde(~) notation in HTML elements such as
,


MVC 3的Razor视图引擎使使用在运行时正确解析的虚拟根相对路径变得更加容易和清晰。只需将url.content()方法放到href属性值中,它就会正确解析。

1
Application home page

我使用一个简单的助手方法。您可以在视图和控制器中轻松地使用它。

Markup:

1
About Us

辅助方法:

1
2
3
4
5
6
7
8
9
10
11
public static string Root()
{
    if (HttpContext.Current.Request.Url.Host =="localhost")
    {
        return"";
    }
    else
    {
        return"/productionroot";
    }
}

这篇文章对如何处理ASP.NET路径有一个非常完整的总结。


我使用了一种不同的方法,基于一篇类似的文章,但是代码要少得多…

http://a.shinnew.me/post/6042784654/relative-paths-in-asp-net-mvc-javascript


像Chris一样,我真的不能忍受将膨胀的服务器端标签放在我的干净标记中,仅仅是为了告诉这个愚蠢的东西从根向上看。这应该是一个非常简单,合理的要求。但我也不喜欢这样一个想法:为了做这样一件简单的事情,我必须去写任何定制的C类,为什么我必须这样做?真是浪费时间。

对于我来说,我只是妥协于"完美",并将虚拟目录的根路径名硬编码到我的路径引用中。像这样:

1
<script type="text/javascript" src="/MyProject/Scripts/jquery-1.2.6.js">

解析URL不需要服务器端处理或C代码,这对性能最好,尽管我知道不管怎样它都可以忽略不计。而且在我干净的标记中没有膨胀的、丑陋的服务器端混乱。

我只需要知道这是硬编码的,当它迁移到适当的域而不是http://mydevserver/myproject时需要删除它。/

干杯