ASP.NET MVC 상대 경로
애플리케이션에서 저는 종종 상대 경로를 사용해야 합니다.예를 들어, JQuery를 참조할 때는 보통 다음과 같이 참조합니다.
<script type="text/javascript" src="../Scripts/jquery-1.2.6.js"></script>
이제 MVC로 전환할 때는 루트와 관련하여 페이지가 가질 수 있는 다양한 경로를 고려해야 합니다.과거에는 물론 URL을 다시 쓰는 문제였지만, 일관된 경로를 사용하여 해결할 수 있었습니다.
표준 솔루션은 다음과 같은 절대 경로를 사용하는 것입니다.
<script type="text/javascript" src="/Scripts/jquery-1.2.6.js"></script>
하지만 개발 주기 동안에는 앱이 가상 디렉터리에서 실행될 테스트 시스템에 배포해야 하기 때문에 이것은 저에게 효과가 없습니다.루트 상대 경로는 루트가 변경될 때 작동하지 않습니다.또한 유지보수상의 이유로 테스트를 배포하는 동안 모든 경로를 단순히 변경할 수는 없습니다. 이는 그 자체로 악몽이 될 것입니다.
그렇다면 가장 좋은 해결책은 무엇일까요?
편집:
이 질문은 여전히 조회와 답변을 받고 있기 때문에 Razor V2의 경우 루트 관련 URL에 대한 지원이 포함되어 있으므로 사용할 수 있도록 업데이트하는 것이 신중할 수 있다고 생각했습니다.
<img src="~/Content/MyImage.jpg">
서버 측 구문 없이도 뷰 엔진이 자동으로 ~/ 현재 사이트 루트를 대체합니다.
사용해 보십시오.
<script type="text/javascript" src="<%=Url.Content("~/Scripts/jquery-1.2.6.js")%>"></script>
또는 MvcContrib을 사용하여 다음 작업을 수행합니다.
<%=Html.ScriptInclude("~/Content/Script/jquery.1.2.6.js")%>
이전 게시물이지만, 새로운 독자는 레이저 2 이상(MVC4+의 기본값)이 이 문제를 완전히 해결한다는 것을 알아야 합니다.
레이저 1이 장착된 이전 MVC3:
<a href="@Url.Content("~/Home")">Application home page</a>
레이저 2 이상이 장착된 새로운 MVC4:
<a href="~/Home">Application home page</a>
어색한 레이저 함수와 유사한 구문이 없습니다.비표준 마크업 태그가 없습니다.
HTML 속성의 경로 앞에 타일드(~)를 붙이면 레이저 2가 올바른 경로를 대체하여 "그냥 작동하도록" 지시합니다.훌륭해.
변화를 깨는 - MVC 5
MVC 5(MVC 5 릴리스 노트에서)의 급격한 변경 사항을 주의하십시오.
URL 다시 쓰기 및 타일드(~)
ASP 3 ASP5로 한 후 ASP.NET Razor 3 는 ASP를 가 더 이상 수 .NET MVC 5로 업그레이드한 후 URL 다시 쓰기를 사용하는 경우 타일드(~) 표기법이 더 이상 올바르게 작동하지 않을 수 있습니다.URL 다시 쓰기는 다음과 같은 HTML 요소의 타일드(~) 표기법에 영향을 미칩니다.
<A/>
,<SCRIPT/>
,<LINK/>
결과적으로 타일드는 더 이상 루트 디렉토리에 매핑되지 않습니다.예를 들어 asp.net/content 에 대한 요청을 asp.net 에 다시 쓰는 경우 href 특성은
<A href="~/content/"/>
/ 대신 /content/content/로 확인됩니다.이러한 변경을 억제하려면 각 웹 페이지 또는 Global.asax의 Application_BeginRequest에서 IIS_WasUrlRewrited 컨텍스트를 false로 설정합니다.
그들은 실제로 어떻게 하는지 설명하지 않지만, 저는 다음과 같은 답을 찾았습니다.
7 IIS 7에 을 입력합니다.
Global.asax
:
protected void Application_BeginRequest(object sender, EventArgs e)
{
Request.ServerVariables.Remove("IIS_WasUrlRewritten");
}
참고: 확인할 수 있습니다.Request.ServerVariables
는 실로포 다니합함이 들어 있습니다.IIS_WasUrlRewritten
이것이 당신의 문제인지 확인하기 위해 먼저.
PS.는 이런 있고 를 상황이 했습니다. 나는 내게 이런 일이 일어나고 있는 상황이 있다고 생각했고, 나는 점점.src="~/content/..."
URL이 HTML에 생성되었지만 코드를 컴파일할 때 새로 고쳐지지 않은 것으로 나타났습니다.레이아웃 및 페이지 cshtml 파일을 편집하고 다시 저장하는 것이 작동을 유발했습니다.
ASP ASP를 합니다.NET에서는 주로 사용합니다.<img src='<%= VirtualPathUtility.ToAbsolute("~/images/logo.gif") %>' alt="Our Company Logo"/>
ASP MVCASP.NET MVC에서 하지 않아야 하는
<script src="<%=ResolveUrl("~/Scripts/jquery-1.2.6.min.js") %>" type="text/javascript"></script>
제가 사용한 것입니다.예제와 일치하도록 경로를 변경합니다.
가치 있는 것은, 저는 경로를 해결하기 위해 앱에 서버 태그를 버리는 것이 정말 싫다는 것입니다. 그래서 저는 좀 더 조사를 해보고 링크를 다시 쓰는 데 이전에 시도했던 것인 응답 필터를 사용하기로 결정했습니다.이렇게 하면 모든 절대 경로에 알려진 접두사를 붙여놓고 응답을 사용하여 런타임에 이 접두사를 바꿀 수 있습니다.개체를 필터링하고 불필요한 서버 태그에 대해 걱정할 필요가 없습니다.코드는 다른 사람에게 도움이 될 경우를 대비하여 아래에 게시되어 있습니다.
using System;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;
using System.Web;
namespace Demo
{
public class PathRewriter : Stream
{
Stream filter;
HttpContext context;
object writeLock = new object();
StringBuilder sb = new StringBuilder();
Regex eofTag = new Regex("</html>", RegexOptions.IgnoreCase | RegexOptions.Compiled);
Regex rootTag = new Regex("/_AppRoot_", RegexOptions.IgnoreCase | RegexOptions.Compiled);
public PathRewriter(Stream filter, HttpContext context)
{
this.filter = filter;
this.context = context;
}
public override void Write(byte[] buffer, int offset, int count)
{
string temp;
lock (writeLock)
{
temp = Encoding.UTF8.GetString(buffer, offset, count);
sb.Append(temp);
if (eofTag.IsMatch(temp))
RewritePaths();
}
}
public void RewritePaths()
{
byte[] buffer;
string temp;
string root;
temp = sb.ToString();
root = context.Request.ApplicationPath;
if (root == "/") root = "";
temp = rootTag.Replace(temp, root);
buffer = Encoding.UTF8.GetBytes(temp);
filter.Write(buffer, 0, buffer.Length);
}
public override bool CanRead
{
get { return true; }
}
public override bool CanSeek
{
get { return filter.CanSeek; }
}
public override bool CanWrite
{
get { return true; }
}
public override void Flush()
{
return;
}
public override long Length
{
get { return Encoding.UTF8.GetBytes(sb.ToString()).Length; }
}
public override long Position
{
get { return filter.Position; }
set { filter.Position = value; }
}
public override int Read(byte[] buffer, int offset, int count)
{
return filter.Read(buffer, offset, count);
}
public override long Seek(long offset, SeekOrigin origin)
{
return filter.Seek(offset, origin);
}
public override void SetLength(long value)
{
throw new NotImplementedException();
}
}
public class PathFilterModule : IHttpModule
{
public void Dispose()
{
return;
}
public void Init(HttpApplication context)
{
context.ReleaseRequestState += new EventHandler(context_ReleaseRequestState);
}
void context_ReleaseRequestState(object sender, EventArgs e)
{
HttpApplication app = sender as HttpApplication;
if (app.Response.ContentType == "text/html")
app.Response.Filter = new PathRewriter(app.Response.Filter, app.Context);
}
}
}
MVC 3용 Razor view 엔진을 사용하면 런타임에 적절하게 해결된 가상 루트 상대 경로를 훨씬 더 쉽고 간편하게 사용할 수 있습니다.URL을 삭제하십시오.content() 메서드를 href 특성 값으로 변환하면 제대로 해결됩니다.
<a href="@Url.Content("~/Home")">Application home page</a>
Chris와 마찬가지로, 저는 단순히 뿌리부터 위를 바라보기 위해 제 깨끗한 마크업 안에 비대해진 서버 측면 태그를 넣어야 하는 것을 정말 참을 수 없습니다.그것은 매우 간단하고 합리적인 요구사항일 것입니다.하지만 저는 그런 간단한 일을 하기 위해 맞춤형 C# 수업을 작성하는 노력을 해야 한다는 생각도 싫어요. 왜 그래야 하죠?정말 시간 낭비야.
저는 단순히 "완벽함"을 훼손하고 경로 참조 내에서 가상 디렉터리의 루트 경로 이름을 하드 코딩했습니다.이런 식으로.
<script type="text/javascript" src="/MyProject/Scripts/jquery-1.2.6.js"></script>
URL을 해결하는 데 서버 측 처리나 C# 코드가 필요하지 않으므로 성능에 가장 좋습니다. 그래도 무시해도 될 것으로 알고 있습니다.서버 쪽의 더부룩하고 추악한 혼돈은 제 깨끗한 마크업에서 찾아볼 수 없습니다.
저는 이것이 하드 코드화되어 있고 그것이 http://MyDevServer/MyProject/ 대신 적절한 도메인으로 마이그레이션될 때 제거되어야 한다는 것을 알고 살아야 할 것입니다.
건배.
저는 간단한 도우미 방법을 사용합니다.보기 및 컨트롤러에서 쉽게 사용할 수 있습니다.
마크업:
<a href=@Helper.Root()/about">About Us</a>
도우미 방법:
public static string Root()
{
if (HttpContext.Current.Request.Url.Host == "localhost")
{
return "";
}
else
{
return "/productionroot";
}
}
언급URL : https://stackoverflow.com/questions/317315/asp-net-mvc-relative-paths
'source' 카테고리의 다른 글
UIPageViewController에서 프로그래밍 방식으로 페이지를 넘길 수 있습니까? (0) | 2023.06.13 |
---|---|
NSData를 6진수 문자열로 직렬화하는 가장 좋은 방법 (0) | 2023.06.13 |
tsconfig.json에서 'jsx' 속성의 용도는 무엇입니까? (0) | 2023.06.13 |
UIScrollView에서 스크롤 표시기를 숨길 수 있는 방법이 있습니까? (0) | 2023.06.13 |
ASP.NET MVC에서 전체 영역에 대한 권한을 설정하려면 어떻게 해야 합니까? (0) | 2023.06.08 |