2014-04-07 8 views
6

Ich erhalte eine unerwartete Ausnahme, wenn meine URL ein Anführungszeichen enthält, wenn meine Ansicht eine untergeordnete Aktion enthält.MVC untergeordnete Aktion wirft ungültige Zeichen in Pfad

http://mysite.info/home/index/"

Wenn die Ansicht für diese Aktion kein Kind Aktion funktioniert alles einwandfrei enthält. Wenn es eine untergeordnete Aktion enthält (z. B. @ Html.Action ("Menu")), erhalte ich beim Aufruf von Html.Action die Ausnahme "System.ArgumentException: Unzulässige Zeichen im Pfad".

Blick auf this post das doppelte Anführungszeichen gehört nicht zu den Standard ungültigen Zeichen. Es scheint mir, dass sich eine Handlung mit oder ohne Kinderhandlung gleich verhalten sollte. Entweder ist ein Doppelzitat gültig oder nicht.

Darüber hinaus bin ich mir nicht sicher, wie man diesen scheinbaren doppelten Standard am besten umgehen kann. Ich zögere, die Liste der ungültigen Zeichen so zu ändern, dass sie "enthält (die Standardeinstellungen sind aus einem bestimmten Grund). Kindaktionen sind sehr nützlich, also möchte ich sie nicht verwenden. Ein Versuch, jede Kindaktion einzufangen, ist hacky .

Ich versuche nicht aktiv, Anführungszeichen in meinen Routen zu verwenden, aber wenn "nicht in der Liste der unzulässigen Zeichen ist, dann sollte es nicht zu einer Ausnahme führen, oder?

Beispiel

Controller:

public class HomeController : Controller 
{ 
    public ActionResult WithChildAction() // throws exception with quote in path 
    { 
     return View(); 
    } 

    public ActionResult WithoutChildAction() // works with quote in path 
    { 
     return View(); 
    } 

    public ActionResult ChildAction() 
    { 
     return View(); 
    } 
} 

WithChildAction.cshtml:

<h2>With Child Action</h2> 

@Html.Action("ChildAction") 

WithoutChildAction.cshtml:

<h2>Without Child Action</h2> 

ChildAction.cshtml:

<h2>Child Action</h2> 

Stack Trace

[ArgumentException: Illegal characters in path.] 
    System.IO.Path.CheckInvalidPathChars(String path, Boolean checkAdditional) +11113918 
    System.Security.Permissions.FileIOPermission.CheckIllegalCharacters(String[] str) +30 
    System.Security.Permissions.FileIOPermission.AddPathList(FileIOPermissionAccess access, AccessControlActions control, String[] pathListOrig, Boolean checkForDuplicates, Boolean needFullPath, Boolean copyPathList) +97 
    System.Security.Permissions.FileIOPermission..ctor(FileIOPermissionAccess access, String path) +63 
    System.Web.InternalSecurityPermissions.PathDiscovery(String path) +29 
    System.Web.HttpRequest.MapPath(VirtualPath virtualPath, VirtualPath baseVirtualDir, Boolean allowCrossAppMapping) +149 
    System.Web.HttpRequest.MapPath(VirtualPath virtualPath) +33 
    System.Web.HttpServerUtility.Execute(IHttpHandler handler, TextWriter writer, Boolean preserveForm, Boolean setPreviousPage) +44 
    System.Web.HttpServerUtility.Execute(IHttpHandler handler, TextWriter writer, Boolean preserveForm) +28 
    System.Web.HttpServerUtilityWrapper.Execute(IHttpHandler handler, TextWriter writer, Boolean preserveForm) +19 
    System.Web.Mvc.Html.ChildActionExtensions.ActionHelper(HtmlHelper htmlHelper, String actionName, String controllerName, RouteValueDictionary routeValues, TextWriter textWriter) +461 
    System.Web.Mvc.Html.ChildActionExtensions.Action(HtmlHelper htmlHelper, String actionName, String controllerName, RouteValueDictionary routeValues) +83 
    System.Web.Mvc.Html.ChildActionExtensions.Action(HtmlHelper htmlHelper, String actionName, Object routeValues) +29 
    ASP._Page_Areas_Site_Views_Content_File_cshtml.Execute() in c:\inetpub\Websites\MyWebsite\Source\Areas\Site\Views\Content\File.cshtml:22 
    System.Web.WebPages.WebPageBase.ExecutePageHierarchy() +199 
    System.Web.Mvc.WebViewPage.ExecutePageHierarchy() +104 
    System.Web.WebPages.WebPageBase.ExecutePageHierarchy(WebPageContext pageContext, TextWriter writer, WebPageRenderingBase startPage) +78 
    System.Web.Mvc.RazorView.RenderView(ViewContext viewContext, TextWriter writer, Object instance) +235 
    System.Web.Mvc.BuildManagerCompiledView.Render(ViewContext viewContext, TextWriter writer) +107 
    System.Web.Mvc.ViewResultBase.ExecuteResult(ControllerContext context) +291 
    System.Web.Mvc.ControllerActionInvoker.InvokeActionResult(ControllerContext controllerContext, ActionResult actionResult) +13 
    System.Web.Mvc.ControllerActionInvoker.InvokeActionResultFilterRecursive(IList`1 filters, Int32 filterIndex, ResultExecutingContext preContext, ControllerContext controllerContext, ActionResult actionResult) +56 
    System.Web.Mvc.ControllerActionInvoker.InvokeActionResultFilterRecursive(IList`1 filters, Int32 filterIndex, ResultExecutingContext preContext, ControllerContext controllerContext, ActionResult actionResult) +420 
    System.Web.Mvc.ControllerActionInvoker.InvokeActionResultWithFilters(ControllerContext controllerContext, IList`1 filters, ActionResult actionResult) +52 
    System.Web.Mvc.Async.<>c__DisplayClass2b.<BeginInvokeAction>b__1c() +173 
    System.Web.Mvc.Async.<>c__DisplayClass21.<BeginInvokeAction>b__1e(IAsyncResult asyncResult) +100 
    System.Web.Mvc.Async.WrappedAsyncResult`1.CallEndDelegate(IAsyncResult asyncResult) +10 
    System.Web.Mvc.Async.WrappedAsyncResultBase`1.End() +49 
    System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeAction(IAsyncResult asyncResult) +27 
    System.Web.Mvc.Controller.<BeginExecuteCore>b__1d(IAsyncResult asyncResult, ExecuteCoreState innerState) +13 
    System.Web.Mvc.Async.WrappedAsyncVoid`1.CallEndDelegate(IAsyncResult asyncResult) +36 
    System.Web.Mvc.Async.WrappedAsyncResultBase`1.End() +54 
    System.Web.Mvc.Controller.EndExecuteCore(IAsyncResult asyncResult) +39 
    System.Web.Mvc.Controller.<BeginExecute>b__15(IAsyncResult asyncResult, Controller controller) +12 
    System.Web.Mvc.Async.WrappedAsyncVoid`1.CallEndDelegate(IAsyncResult asyncResult) +28 
    System.Web.Mvc.Async.WrappedAsyncResultBase`1.End() +54 
    System.Web.Mvc.Controller.EndExecute(IAsyncResult asyncResult) +29 
    System.Web.Mvc.Controller.System.Web.Mvc.Async.IAsyncController.EndExecute(IAsyncResult asyncResult) +10 
    System.Web.Mvc.MvcHandler.<BeginProcessRequest>b__5(IAsyncResult asyncResult, ProcessRequestState innerState) +21 
    System.Web.Mvc.Async.WrappedAsyncVoid`1.CallEndDelegate(IAsyncResult asyncResult) +36 
    System.Web.Mvc.Async.WrappedAsyncResultBase`1.End() +54 
    System.Web.Mvc.MvcHandler.EndProcessRequest(IAsyncResult asyncResult) +31 
    System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.EndProcessRequest(IAsyncResult result) +9 
    System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +9690164 
    System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +155 
+0

Was ist der Stack-Trace? –

+0

@ErikFunkenbusch Stack-Trace hinzugefügt. – jdehlin

+0

Wie Sie aus der Stack-Ablaufverfolgung sehen können, kommt der Fehler von MapPath und passiert tatsächlich außerhalb von MVC. Dies ist Code in der Basis-HttpHandler und das sollte gleich sein, unabhängig davon, ob es eine reguläre oder untergeordnete Aktion ist. –

Antwort

1

Html.Action hat einen Scheck, der die aktuelle Route verarbeitet, um zu sehen, ob es in einem Bereich befindet. Dieser Prozess gibt den Zugriff auf den virtuellen Pfad (Dateisystem) zurück. Quotes sind im Dateisystem nicht erlaubt und werfen somit den Fehler.

bool usingAreas; 
VirtualPathData vpd = htmlHelper.RouteCollection 
    .GetVirtualPathForArea(htmlHelper.ViewContext.RequestContext, null /* name */, routeValues, out usingAreas); 

Mit dem Routecollection Extensions Code hier:

http://aspnetwebstack.codeplex.com/SourceControl/latest#src/System.Web.Mvc/RouteCollectionExtensions.cs

Sie die Routevalues ​​zu handhaben in der Lage sein und die Bereichsnamen festlegen, den Fehler zu vermeiden, aber nicht Zeichen Dateisystem, das die ungültigen der erste Platz wäre ideal.

+0

Wenn man weiter schaut, ist es vorbei an der Bereichsüberprüfung. Es versucht tatsächlich auszuführen, also wird etwas nicht genauso wie ursprünglich gereinigt. – neehouse

+0

Nur gedacht, dass ich habe ist, dass es auf Browser-Anfrage codiert ist, wird entschlüsselt und nicht auf Child Aktion Anfrage codiert. – neehouse

2

eine mögliche Lösung gefunden durch die folgende in web.config Einstellung:

<httpRuntime relaxedUrlToFileSystemMapping="true"/> 

Diese gefährliche scheint so die Fehler ignorieren Ich werde einfach.