Ответ 1
У меня была эта проблема, но она не была связана с модулями перезаписи URL.
В моем случае я случайно закрепил экземпляр UrlHelper в статическом поле, а позже запросы встретили удаленный экземпляр из более ранних запросов.
По какой-то причине, когда некоторые боты посещают сайт, генерация URL-адреса с помощью метода UrlHelper.Action
вызывает исключение null из System.Web.HttpServerVarsCollection.Get
. Я выполнил некоторую отладку, и стек вызовов начал происходить с попыткой получить "HTTP_X_ORIGINAL_URL" из коллекции HttpContextBase.Request.ServerVariables
.
Если я посещаю тот же адрес непосредственно из браузера - никаких проблем. Страница - это сервер, и никакая ошибка не регистрируется. Кажется, что это происходит при посещении ботом.
Не уверен, что это релевантно или нет, но сайт был просто перенесен в IIS 7.5. Все еще используется .NET 2.0 в интегрированном режиме.
Рассматривая код, который обращается на Reflector, единственным местом, где исключение null может происходить непосредственно в методе Get
, является вызов this._request.FetchServerVariables
. Как будто полный запрос не был настроен должным образом.
Кто-нибудь еще столкнулся с этой проблемой или обнаружил обходной путь? Почему запрос должен быть настроен по-разному при посещении ботом?
ОБНОВЛЕНИЕ. Некоторые дополнительные отладки показали, что HttpServerVarsCollection был удален, а также его родительский объект HttpRequest. Теперь вопрос заключается в следующем: как объект запроса, возвращаемый HttpContext.Current, должен быть открыт до завершения запроса?
Метод HttpServerVarsCollection.Get
public override string Get(string name)
{
if (!this._populated)
{
string simpleServerVar = this.GetSimpleServerVar(name);
if (simpleServerVar != null)
{
return simpleServerVar;
}
this.Populate();
}
if (this._iis7workerRequest == null)
{
return this.GetServerVar(base.BaseGet(name));
}
string serverVar = this.GetServerVar(base.BaseGet(name));
if (string.IsNullOrEmpty(serverVar))
{
// Only place null reference can happen
serverVar = this._request.FetchServerVariable(name);
}
return serverVar;
}
Полная трассировка стека
NullReferenceException: Object reference not set to an instance of an object.]
System.Web.HttpServerVarsCollection.Get(String name) +8645730
System.Collections.Specialized.NameValueCollection.get_Item(String name) +7
System.Web.Mvc.PathHelpers.GenerateClientUrlInternal(HttpContextBase httpContext, String contentPath) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\PathHelpers.cs:39
System.Web.Mvc.PathHelpers.GenerateClientUrl(HttpContextBase httpContext, String contentPath) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\PathHelpers.cs:21
System.Web.Mvc.UrlHelper.GenerateUrl(String routeName, String actionName, String controllerName, RouteValueDictionary routeValues, RouteCollection routeCollection, RequestContext requestContext, Boolean includeImplicitMvcValues) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\UrlHelper.cs:136
System.Web.Mvc.UrlHelper.GenerateUrl(String routeName, String actionName, String controllerName, RouteValueDictionary routeValues) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\UrlHelper.cs:101
System.Web.Mvc.UrlHelper.Action(String actionName, String controllerName, Object routeValues) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\UrlHelper.cs:51
www.CmsExtensions.Document(UrlHelper urlHelper, String path) in C:\Dev\Site\www\Code\CmsExtensions.cs:33
www.CmsExtensions.Document(UrlHelper urlHelper, Document document) in C:\Dev\Site\www\Code\CmsExtensions.cs:20
www.<>c__DisplayClass17.<Load>b__c(Document d) in C:\Dev\Site\www\Global.asax.cs:251
Fringine.Cms.DocumentContentParser.ReplaceDocumentRefs(IResolvingDocumentCache cache, Match match) +258
Fringine.Cms.<>c__DisplayClass4.<ParseContent>b__2(Match m) +17
System.Text.RegularExpressions.RegexReplacement.Replace(MatchEvaluator evaluator, Regex regex, String input, Int32 count, Int32 startat) +234
System.Text.RegularExpressions.Regex.Replace(String input, MatchEvaluator evaluator, Int32 count, Int32 startat) +28
System.Text.RegularExpressions.Regex.Replace(String input, MatchEvaluator evaluator) +38
System.Text.RegularExpressions.Regex.Replace(String input, String pattern, MatchEvaluator evaluator, RegexOptions options) +47
Fringine.Cms.DocumentContentParser.ParseContent(String content, IResolvingDocumentCache cache) +83
Fringine.Cms.ResolvingDocumentCache.<Parse>b__0(String d) +21
Fringine.Cms.DocumentCache.GetParsedData(String id, String content, IDocumentService documentService, Func`2 parser) +216
Fringine.Cms.ResolvingDocumentCache.Parse(String id, String content) +67
Fringine.Cms.CachedDocument.GetSummary() +966
Fringine.Cms.CachedDocument.get_Summary() +19
ASP.views_document_widget_feeddocumentsummary_ascx.__Render__control1(HtmlTextWriter __w, Control parameterContainer) +841
System.Web.UI.Control.RenderChildrenInternal(HtmlTextWriter writer, ICollection children) +256
System.Web.UI.Control.RenderChildren(HtmlTextWriter writer) +19
System.Web.UI.Control.Render(HtmlTextWriter writer) +10
System.Web.UI.Control.RenderControlInternal(HtmlTextWriter writer, ControlAdapter adapter) +27
System.Web.UI.Control.RenderControl(HtmlTextWriter writer, ControlAdapter adapter) +99
System.Web.UI.Control.RenderControl(HtmlTextWriter writer) +25
System.Web.UI.Control.RenderChildrenInternal(HtmlTextWriter writer, ICollection children) +134
System.Web.UI.Control.RenderChildren(HtmlTextWriter writer) +19
System.Web.UI.Page.Render(HtmlTextWriter writer) +29
System.Web.Mvc.ViewPage.Render(HtmlTextWriter writer) in C:\Dev\Site\MVC\Microsoft\src\SystemWebMvc\Mvc\ViewPage.cs:107
System.Web.UI.Control.RenderControlInternal(HtmlTextWriter writer, ControlAdapter adapter) +27
System.Web.UI.Control.RenderControl(HtmlTextWriter writer, ControlAdapter adapter) +99
System.Web.UI.Control.RenderControl(HtmlTextWriter writer) +25
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +1266
У меня была эта проблема, но она не была связана с модулями перезаписи URL.
В моем случае я случайно закрепил экземпляр UrlHelper в статическом поле, а позже запросы встретили удаленный экземпляр из более ранних запросов.
Я знаю, что этот вопрос довольно старый, но я недавно оказался в очень похожей ситуации, когда мой UrlHelper давал мне нулевое ссылочное исключение в System.Web.HttpServerVarsCollection.Get.
Проблема была действительно HTTP_X_ORIGINAL_URL, и эта конкретная переменная сервера поступает из модуля URL Rewrite 2.0 в IIS.
Интересно, что этот модуль был установлен, но не использовался. Тем не менее, этого было достаточно, чтобы вызвать проблему. При удалении этой ошибки ошибка исчезла.
Если вам нужно переписать URL-адрес, там есть другие модули, или вы можете сделать это на уровне приложения.
Надеюсь, что это поможет.
Я столкнулся с этим, в моем случае смог решить, переключившись на использование метода расширения без расширений UrlHelper. У меня был один метод расширения, вызывающий другой, но передача UrlHelper во второй метод.
Этот путь был сломан:
public static string Script(this UrlHelper helper, string fileName)
{
return Asset(helper, "~/js/", fileName);
}
private static string Asset(this UrlHelper helper, string path, string fileName)
{
return helper.Content(string.Format("{0}/{1}/{2}",
path,
Version,
fileName));
}
Этот способ работает:
public static string Script(this UrlHelper helper, string fileName)
{
return Asset(helper, "~/js/", fileName);
}
private static string Asset(UrlHelper helper, string path, string fileName)
{
return helper.Content(string.Format("{0}/{1}/{2}",
path,
Version,
fileName));
}
Обратите внимание на разницу в сигнатуре функции метода Asset.