Изящно обрабатывать взлом URI в ASP.NET - PullRequest
3 голосов
/ 27 февраля 2009

Я написал приложение, которое корректно обрабатывает большинство исключений, с неповрежденным дизайном страницы и красивым сообщением об ошибке. Мое приложение перехватывает их все в событии Page_Error и добавляет исключение к HttpContext.Curent.Context.Items, а затем делает Server.Transfer на странице Error.aspx. Я считаю, что это единственное жизнеспособное решение в ASP.NET, так как, похоже, нет другого способа сделать это централизованным и общим способом.

Я также обрабатываю Application_Error, и там я провожу некоторую проверку исключений, которые произошли, чтобы выяснить, могу ли я справиться с этим изящно или нет. Исключения, которые я нашел, я могу обработать изящно, такие, которые выдают после того, как кто-то взломал URI, чтобы содержать символы, которые .NET Framework считает опасными или просто недопустимыми на уровне файловой системы.

Такие URI могут выглядеть, например, как ::1010*

(обратите внимание на пробел перед косой чертой в конце последнего URI).

Мне бы хотелось, чтобы эти URI отвечали сообщением "404 Not Found" и дружеским сообщением, а также не вызывали отправку какого-либо отчета об ошибке, чтобы избежать векторов DDOS-атак и т.п. Однако я не нашел элегантного способа отловить ошибки такого типа. Теперь я проверяю свойство exception.TargetSite.Name и, если оно равно CheckInvalidPathChars, ValidatePath или CheckSuspiciousPhysicalPath, я считаю его "исключением проверки пути" и отвечаю 404.

Хотя это похоже на взлом. Во-первых, список имен методов, вероятно, не является полным, а во-вторых, существует вероятность того, что имена этих методов будут заменены или переименованы по линии, что приведет к разрыву моего кода.

У кого-нибудь есть идеи, как мне справиться с этим менее жестким и гораздо более перспективным способом?

PS: я использую System.Web.Routing в своем приложении, чтобы иметь чистые и разумные URI, если это имеет какое-либо значение для любого конкретного решения.

Ответы [ 3 ]

3 голосов
/ 27 февраля 2009

Может случиться так, что System.Web.Routing поддерживает какую-то фильтрацию URL, но это довольно легко реализовать самостоятельно.

Посмотрите на интерфейс System.Web.IHttpModule и прочитайте о реализации пользовательских модулей HTTP . Http-модули входят в этот конвейер Asp.Net и запускаются до запуска вашей страницы. Вы можете использовать его для ведения журнала запросов, для изменения запросов и в вашем случае для фильтрации запросов. Модуль маршрутизации Asp.Net также реализован как пользовательский модуль HTTP.

Что вы можете сделать, это реализовать модуль Http, который просматривает запрошенный URL и проверяет, является ли он действительным. Если URL-адрес недействителен, вы можете делать все, что вам нужно, например, перенаправить его на страницу 404 - не найдено, или вы можете просто остановить запрос.

1 голос
/ 28 февраля 2010

Я не думаю, что использование 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)

Я предполагаю, что исключение вызвано шагом "RESOLVE CACHE"

0 голосов
/ 30 марта 2010

Создание пользовательского HttpModule не работает для меня - я все еще получаю ошибку «Недопустимые символы в пути», но ответ на этот вопрос решил проблему:

Оказывается, этого можно избежать, установив allowDoubleEscaping = "false" для requestFiltering в web.Config. То есть:

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

Возможно, не идеальное решение (любые предложения по улучшению лучше приветствуются), но оно решает проблему.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...