Uma excepção é lançada quando se usa o método FormsAuthentication.RedirectFromLoginPage com alguns URLs de retorno que são marcados como inválidos, embora não o sejam. Este método é usado para autenticar e redireccionar um utilizador validado a partir da página de login.
Este problema ocorre quando utilizadores não autenticados tentam aceder a uma página que requer autenticação e cujo URL é parecido com o seguinte:
http://www.example.com/subsite/page.aspx?param=http://www.example.com/subsite2/something/else.aspx
Reparem que o URL inclui outro URL como parâmetro.
O utilizador é de seguida redireccionado para a página de login e o ASP.NET adiciona automaticamente o parâmetro do URL de retorno. O URL da página de autenticação fica então no seguinte formato:
http://www.example.com/login.aspx?ReturnUrl=/subsite/page.aspx?param=http://www.example.com/subsite2/something/else.aspx
Ou seja, é basicamente um URL com um URL de retorno que inclui, nele próprio, um URL como parâmetro query string.
Os métodos internos usados pelo método FormsAuthentication.RedirectFromLoginPage
assumem que este URL é inválido e lançam a seguinte excepção:
System.Web.HttpException The return URL specified for request redirection is invalid.
at System.Web.Security.FormsAuthentication.GetReturnUrl(Boolean useDefaultIfAbsent)
at System.Web.Security.FormsAuthentication.RedirectFromLoginPage(String userName, Boolean createPersistentCookie, String strCookiePath)
at System.Web.Security.FormsAuthentication.RedirectFromLoginPage(String userName, Boolean createPersistentCookie)
Uma forma de contornar este problema é fazer duas chamadas separadas:
FormsAuthentication.SetAuthCookie(username, false);
Page.Response.Redirect(Page.Request["ReturnUrl"]);
A primeira chamada define o cookie de autenticação e a segunda redirecciona o utilizador para o URL de retorno
No entanto, é melhor não fazer desta forma, porque o URL de retorno pode estar vazio e, nesses casos, o utilizador deve ser redireccionado para o DefaultUrl. Uma solução final poderá ser:
string url = Page.Request["ReturnUrl"] as string;
if (!string.IsNullOrEmpty(url))
{
FormsAuthentication.SetAuthCookie(username, false);
Page.Response.Redirect(url);
}
else
{
// there is no URL, RedirectFromLoginPage can be safely used to redirect to the default URL
FormsAuthentication.RedirectFromLoginPage(username, false);
}
Devem colocar isto num método à parte e adicionar try/catch e logging como necessário.