Недавно я перенес веб-сайт на новую CMS (Umbraco). Многие ссылки изменились, но их можно легко исправить, выполнив поиск шаблонов в URL-адресе, поэтому я хотел бы написать что-то, что будет перенаправлять на правильную страницу, если старая не будет найдена. Это не проблема.
Как я могу получить запрошенный URL-адрес после того, как браузер будет перенаправлен на мою пользовательскую страницу 404. Я пробовал использовать:
request.ServerVariables("HTTP_REFERER") 'sorry i corrected the typo from system to server.
Но это не сработало.
Есть идеи?
Сайт находится на IIS 6.0. Мы рассматривали возможность использования 301 редиректа, но у нас нет никакого способа узнать, какие страницы люди добавили в закладки, а существует несколько сотен страниц, поэтому никто не хочет тратить время на создание 301.





Обновите, вы действительно хотите забрать:
VB.NET:
Request.QueryString("aspxerrorpath")
C#:
Request.QueryString["aspxerrorpath"];
Это должно быть в квадратных скобках вместо фигурных скобок: Request.QueryString ["aspxerrorpath")
Спасибо! В принятом ответе использовался C#, и первым тегом вопроса также является C#, что объясняет мое замешательство, но я исправлюсь и надеюсь, что мой комментарий может помочь другим разработчикам на C#.
Как насчет:
Request.ServerVariables("HTTP_REFERER");
Извините, это была опечатка. Я использую ServerVariables
A lot of the links have changed, but they can be easily corrected by searching for patters in the url
Рассматривали ли вы возможность перезаписи URL-адресов вместо того, чтобы отправлять пользователей на номер 404? Таким образом, ваши пользователи (и поисковые системы, если это важно для вас в данном случае) получат 301 или 302 вместо того, чтобы проходить через ваш обработчик 404. Обычно на ваших серверах быстрее и менее напряженно обрабатывать перезапись на уровне URL-адреса, чем запускать свой код и обрабатывать его там.
Microsoft выпустила Модуль перезаписи URL для IIS 7, и есть достойное введение в него здесь и здесь.
Для IIS 6 существует хорошее вступление здесь для перезаписи URL, работающего с ним, немного отличается от IIS7.
Пример правила перезаписи:
# will contain the contents of (.*) - everything after new-dir/
RewriteRule /new-dir/(.*) /find_old_page.asp?code=
there are a few hundred pages, so no one is keen on spending the time to create the 301's
Прелесть правил перезаписи в том, что вам не нужно явно перечислять все ваши страницы, но вы можете писать правила, которые следуют тому же шаблону. Недавно нам пришлось сделать что-то подобное, и удивительно, сколько из перемещенных URL-адресов можно было обработать парой простых правил.
Я думаю, что вместо использования страницы 404 правильнее было бы перенаправить с помощью кода 301 - перемещен навсегда.
Я понимаю, что это своего рода взлом, но клиент уже запустил веб-сайт, и мы ищем быстрое исправление ситуации. Они не хотят посвящать кого-то на следующий день или около того для создания нескольких сотен редиректов.
Вам не нужно создавать их вручную, просто сделайте их с помощью перезаписи URL.
Я делаю в основном то же самое, что вы просите на специальной странице обработки ошибок 404. В IIS 6 исходный URL-адрес находится в строке запроса. В приведенном ниже коде показано, как получить исходный URL-адрес и затем перенаправить пользователя. В моем случае я переключился со старого ASP на новый ASP.NET, поэтому все страницы .asp пришлось перенаправить на страницы .aspx. Кроме того, некоторые URL-адреса изменились, поэтому я ищу ключевые слова в старом URL-адресе и вперед.
//did the error go to a .ASP page? If so, append x (for .aspx) and
//issue a 301 permanently moved
//when we get an error, the querystring will be "404;<complete original URL>"
string targetPage = Request.RawUrl.Substring(Request.FilePath.Length);
if ((null == targetPage) || (targetPage.Length == 0))
targetPage = "[home page]";
else
{
//find the original URL
if (targetPage[0] == '?')
{
if (-1 != targetPage.IndexOf("?aspxerrorpath = "))
targetPage = targetPage.Substring(15); // ?aspxerrorpath=
else
targetPage = targetPage.Substring(5); // ?404;
}
else
{
if (-1 != targetPage.IndexOf("errorpath = "))
targetPage = targetPage.Substring(14); // aspxerrorpath=
else
targetPage = targetPage.Substring(4); // 404;
}
}
string upperTarget = targetPage.ToUpper();
if ((-1 == upperTarget.IndexOf(".ASPX")) && (-1 != upperTarget.IndexOf(".ASP")))
{
//this is a request for an .ASP page - permanently redirect to .aspx
targetPage = upperTarget.Replace(".ASP", ".ASPX");
//issue 301 redirect
Response.Status = "301 Moved Permanently";
Response.AddHeader("Location",targetPage);
Response.End();
}
if (-1 != upperTarget.IndexOf("ORDER"))
{
//going to old order page -- forward to new page
Response.Redirect(WebRoot + "/order.aspx");
Response.End();
}
Вот что мы делаем при инициализации на наших 404 страницах:
Dim AttemptedUrl As String = Request.QueryString("aspxerrorpath")
If Len(AttemptedUrl) = 0 Then AttemptedUrl = Request.Url.Query
AttemptedUrl = LCase(AttemptedUrl)
CheckForRedirects(AttemptedUrl)
Затем CheckforRedirects имеет настраиваемую логику для сопоставления старых URL-адресов с новыми URL-адресами.
Я бы сказал, что это предпочтительный подход (в отличие от 301 или перезаписи URL-адресов), если у вас достаточно внутренней информации, чтобы сопоставить большое количество URL-адресов из старой системы с новой системой - например, если у вас есть таблица, которая сопоставляет старые идентификаторы с новыми идентификаторами или что-то подобное.
Однако если есть согласованный шаблон, который вы можете использовать для сопоставления старых URL-адресов с новыми URL-адресами с помощью регулярного выражения, тогда переопределение URL-адресов будет лучшим вариантом.
Чтобы основываться на предложении перезаписи, Umbraco уже использует UrlRewriting.NET, и в него могут быть добавлены новые перезаписи.
\config\UrlRewriting.config
Надеюсь это поможет
@ GThompson83 - см. Обновление к моему ответу.