3

我编写了一个可以优雅地处理大多数异常的应用程序,页面的设计完好无损,并带有漂亮的错误消息。我的应用程序在事件中捕获了它们,Page_Error并将异常添加到页面HttpContext.Curent.Context.Items,然后执行Server.TransferError.aspx页面。我发现这是 ASP.NET 中唯一可行的解​​决方案,因为似乎没有其他方法可以以集中和通用的方式进行。

我也处理了Application_Error,在那里我对发生的异常进行了一些检查,以确定我是否可以优雅地处理它。我发现我可以优雅地处理的异常是在有人破解 URI 以包含 .NET 框架认为危险的字符或在文件系统级别基本上只是非法的字符之后引发的。

此类 URI 可能如下所示:

  • http://exmample.com/"illegal"
  • http://example.com/illegal"/
  • http://example.com/illegal /

(注意最后一个 URI 末尾斜杠前的空格)。

我希望这些 URI 以“404 Not Found”和友好消息进行响应,并且不会导致发送任何错误报告以避免 DDOS 攻击向量等。但是,我还没有找到一种优雅的方法来捕获这些类型的错误。我现在要做的是检查该exception.TargetSite.Name属性,如果它等于或CheckInvalidPathChars,我认为它是“路径验证异常”并以 404 响应。ValidatePathCheckSuspiciousPhysicalPath

不过,这似乎是一个 hack。首先,方法名称列表可能不完整,其次,这些方法名称有可能被替换或重命名,这将导致我的代码中断。

有谁知道我如何处理这种更少硬编码和更面向未来的方式?

PS:我System.Web.Routing在我的应用程序中使用干净和合理的 URI,如果这对任何给定的解决方案都很重要的话。

4

3 回答 3

3

System.Web.Routing 可能支持某种 url 过滤,但您自己的实现很容易。

查看System.Web.IHttpModule接口并阅读有关实现自定义 HTTP 模块的信息。Http 模块进入该 Asp.Net 管道并在您的页面运行之前运行。您可以使用它来执行请求记录、修改请求以及在您的情况下过滤请求。Asp.Net 路由模块也被实现为自定义 HTTP 模块。

您可以做的是实现一个 Http Module 来查看请求的 url 并检查它是否有效。如果 url 无效,您可以做任何您需要的事情,例如将其重定向到您的 404 - not found 页面,或者您可以停止请求。

于 2009-02-27T09:35:55.607 回答
1

我不认为使用 System.Web.IHttpModule 是 IIS7+ 的正确答案。我正在尝试实现 IHttpModule 来验证路径,但在执行 HttpModule 之前已引发异常。

这是我的异常堆栈:

   [ArgumentException: Illegal characters in path.]
   System.IO.Path.CheckInvalidPathChars(String path) +7493413
   System.IO.Path.Combine(String path1, String path2) +40
   System.Web.Configuration.UserMapPath.GetPhysicalPathForPath(String path, VirtualDirectoryMapping mapping) +114
   System.Web.Configuration.UserMapPath.GetPathConfigFilename(String siteID, VirtualPath path, String& directory, String& baseName) +72
   System.Web.Configuration.UserMapPath.MapPath(String siteID, VirtualPath path) +30
   System.Web.Configuration.UserMapPath.MapPath(String siteID, String path) +31
   System.Web.Hosting.HostingEnvironment.MapPathActual(VirtualPath virtualPath, Boolean permitNull) +297
   System.Web.Hosting.HostingEnvironment.MapPathInternal(VirtualPath virtualPath, Boolean permitNull) +51
   System.Web.CachedPathData.GetConfigPathData(String configPath) +341
   System.Web.CachedPathData.GetVirtualPathData(VirtualPath virtualPath, Boolean permitPathsOutsideApp) +110
   System.Web.HttpContext.GetFilePathData() +36
   System.Web.HttpContext.GetConfigurationPathData() +26
   System.Web.Configuration.RuntimeConfig.GetConfig(HttpContext context) +43
   System.Web.Configuration.CustomErrorsSection.GetSettings(HttpContext context, Boolean canThrow) +41
   System.Web.HttpResponse.ReportRuntimeError(Exception e, Boolean canThrow, Boolean localExecute) +101
   System.Web.HttpRuntime.FinishRequest(HttpWorkerRequest wr, HttpContext context, Exception e) +383

这是 IIS 7.0 应用程序生命周期的链接(http://msdn.microsoft.com/en-us/library/bb470252.aspx

我猜是由“解决缓存”步骤引起的异常

于 2010-02-28T05:14:35.223 回答
0

编写自定义 HttpModule 对我不起作用 - 我仍然收到“路径中的非法字符”错误,但对这个问题的回答解决了这个问题:

事实证明,您可以通过在 web.Config 中为 requestFiltering 设置 allowDoubleEscaping="false" 来避免这种情况。IE:

<configuration>
  <system.webServer>
    <security>
      <requestFiltering allowDoubleEscaping="false" />
    </security>
  </system.webServer>
</configuration>

也许不是完美的解决方案(非常感谢任何更好的解决方案),但它解决了问题。

于 2010-03-30T13:50:18.077 回答