Partilhar via


Personalizando a Manipulação de Erro para o Controle UpdatePanel do ASP.NET

Quando ocorre um erro durante atualizações parcial de página em controles UpdatePanel, o comportamento padrão é que uma caixa de mensagem do navegador é exibida com um mensagem de erro.Este tutorial mostra como personalizar o modo como o erro é apresentado ao usuário e como personalizar a mensagem de erro.

Pré-requisitos

Para implementar os procedimentos no seu próprio ambiente de desenvolvimento você precisa:

  • Microsoft Visual Studio 2005 ou Microsoft Visual Web Developer Express Edition.

  • Um site da Web ASP.NET com AJAX ativado.

Personalizando a Manipulação de Erro no código do servidor

Para começar, você irá personalizar a manipulação de erro usando código do servidor na página.

Para personalizar manipulação de erro no código do servidor

  1. Crie uma nova página e alterne para modo de Design.

  2. Na guia Extensões AJAX da caixa de ferramentas, clique duas vezes em controle ScriptManager e no controle UpdatePanel para adicioná-los para a página.

  3. Adicione o seguinte controles dentro do controle UpdatePanel:

    • Dois controles TextBox.

    • Um controle Label

    • Um controle Buttonconjunto o seu Text propriedade para calcular.

    • Texto dentro do controle UpdatePanel.

  4. clicar duas vezes no botão Calculate e adicione o seguinte código para seu manipulador de eventos:

    Protected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs)
        Try
            Dim a As Int32
            a = Int32.Parse(TextBox1.Text)
            Dim b As Int32
            b = Int32.Parse(TextBox2.Text)
            Dim res As Int32 = a / b
            Label1.Text = res.ToString()
        Catch ex As Exception
            If (TextBox1.Text.Length > 0 AndAlso TextBox2.Text.Length > 0) Then
                ex.Data("ExtraInfo") = " You can't divide " & _
                  TextBox1.Text & " by " & TextBox2.Text & "."
            End If
            Throw ex
        End Try
    
    End Sub
    
    protected void Button1_Click(object sender, EventArgs e)
    {
        try
        {
            int a = Int32.Parse(TextBox1.Text);
            int b = Int32.Parse(TextBox2.Text);
            int res = a / b;
            Label1.Text = res.ToString();
        }
        catch (Exception ex)
        {
            if (TextBox1.Text.Length > 0 && TextBox2.Text.Length > 0)
            {
                ex.Data["ExtraInfo"] = " You can't divide " +
                    TextBox1.Text + " by " + TextBox2.Text + ".";
            }
            throw ex;
        }        
    }
    

    O código contém uma declaração try-catch.No bloco try, o código executa divisão nos valores inseridos nas caixas de texto.Se a operação falhar, o código no bloco catch adiciona as sequências de caracteres extras de informações em ExtraInfo para a exceção e, em seguida, regenera a exceção sem tratá-la.

  5. Alterne para o modo de exibição Design e selecione o controle ScriptManager.

  6. Na barra de ferramentas da Janela Propriedades, clique no botão eventos e, em seguida, clique duas vezes na caixa AsyncPostBackError para criar um manipulador para o evento.

  7. Adicione o seguinte código para o manipulador de eventos AsyncPostBackError:

    Protected Sub ScriptManager1_AsyncPostBackError(ByVal sender As Object, ByVal e As System.Web.UI.AsyncPostBackErrorEventArgs)
        If (e.Exception.Data("ExtraInfo") <> Nothing) Then
            ScriptManager1.AsyncPostBackErrorMessage = _
               e.Exception.Message & _
               e.Exception.Data("ExtraInfo").ToString()
        Else
            ScriptManager1.AsyncPostBackErrorMessage = _
               "An unspecified error occurred."
        End If
    End Sub
    
    protected void ScriptManager1_AsyncPostBackError(object sender, AsyncPostBackErrorEventArgs e)
    {
        if (e.Exception.Data["ExtraInfo"] != null)
        {
            ScriptManager1.AsyncPostBackErrorMessage =
                e.Exception.Message +
                e.Exception.Data["ExtraInfo"].ToString();
        }
        else
        {
            ScriptManager1.AsyncPostBackErrorMessage =
                "An unspecified error occurred.";
        }
    }
    

    O código verifica se o item de dados ExtraInfo está definido para a exceção.Se estiver, a propriedade AsyncPostBackErrorMessage é definida como a valor da sequência de caracteres.Caso contrário, uma mensagem de erro padrão é criada.

  8. Salve suas alterações e, em seguida, pressione CTRL + F5 para exibir a página em um navegador.

  9. Adicionar um número maior que zero a cada caixa de texto e, em seguida, clicar no botão Calculate para demonstrar um postback bem-sucedido.

  10. alterar o texto segundo caixa valor como 0 e clicar no botão Calcular para criar uma condição de erro.

    O navegador exibe um caixa de mensagem que contém a mensagem que foi definida no código de servidor.

    Observação:

    O estilo do caixa de mensagem depende de qual navegador você estiver usando, mas a mensagem é a mesma em todos os navegadores.

    <%@ Page Language="VB" %>
    
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
     "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <script >
        Protected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs)
            Try
                Dim a As Int32
                a = Int32.Parse(TextBox1.Text)
                Dim b As Int32
                b = Int32.Parse(TextBox2.Text)
                Dim res As Int32 = a / b
                Label1.Text = res.ToString()
            Catch ex As Exception
                If (TextBox1.Text.Length > 0 AndAlso TextBox2.Text.Length > 0) Then
                    ex.Data("ExtraInfo") = " You can't divide " & _
                      TextBox1.Text & " by " & TextBox2.Text & "."
                End If
                Throw ex
            End Try
    
        End Sub
        Protected Sub ScriptManager1_AsyncPostBackError(ByVal sender As Object, ByVal e As System.Web.UI.AsyncPostBackErrorEventArgs)
            If (e.Exception.Data("ExtraInfo") <> Nothing) Then
                ScriptManager1.AsyncPostBackErrorMessage = _
                   e.Exception.Message & _
                   e.Exception.Data("ExtraInfo").ToString()
            Else
                ScriptManager1.AsyncPostBackErrorMessage = _
                   "An unspecified error occurred."
            End If
        End Sub
    </script>
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head >
        <title>Partial-Page Update Error Handling Example</title>
    </head>
    <body>
        <form id="form1" >
            <div>
                <asp:ScriptManager ID="ScriptManager1"  OnAsyncPostBackError="ScriptManager1_AsyncPostBackError">
                </asp:ScriptManager>
                <asp:UpdatePanel ID="UpdatePanel1" >
                    <ContentTemplate>
                        <asp:TextBox ID="TextBox1"  Width="39px"></asp:TextBox>
                        /
                        <asp:TextBox ID="TextBox2"  Width="39px"></asp:TextBox>
                        =
                        <asp:Label ID="Label1" ></asp:Label><br />
                        <asp:Button ID="Button1"  OnClick="Button1_Click" Text="calculate" />
                    </ContentTemplate>
                </asp:UpdatePanel>
            </div>
        </form>
    </body>
    </html>
    
    <%@ Page Language="C#" %>
    
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
     "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <script >
        protected void Button1_Click(object sender, EventArgs e)
        {
            try
            {
                int a = Int32.Parse(TextBox1.Text);
                int b = Int32.Parse(TextBox2.Text);
                int res = a / b;
                Label1.Text = res.ToString();
            }
            catch (Exception ex)
            {
                if (TextBox1.Text.Length > 0 && TextBox2.Text.Length > 0)
                {
                    ex.Data["ExtraInfo"] = " You can't divide " +
                        TextBox1.Text + " by " + TextBox2.Text + ".";
                }
                throw ex;
            }        
        }
        protected void ScriptManager1_AsyncPostBackError(object sender, AsyncPostBackErrorEventArgs e)
        {
            if (e.Exception.Data["ExtraInfo"] != null)
            {
                ScriptManager1.AsyncPostBackErrorMessage =
                    e.Exception.Message +
                    e.Exception.Data["ExtraInfo"].ToString();
            }
            else
            {
                ScriptManager1.AsyncPostBackErrorMessage =
                    "An unspecified error occurred.";
            }
        }
    </script>
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head >
        <title>Partial-Page Update Error Handling Example</title>
    </head>
    <body>
        <form id="form1" >
            <div>
                <asp:ScriptManager ID="ScriptManager1"  OnAsyncPostBackError="ScriptManager1_AsyncPostBackError">
                </asp:ScriptManager>
                <asp:UpdatePanel ID="UpdatePanel1" >
                    <ContentTemplate>
                        <asp:TextBox ID="TextBox1"  Width="39px"></asp:TextBox>
                        /
                        <asp:TextBox ID="TextBox2"  Width="39px"></asp:TextBox>
                        =
                        <asp:Label ID="Label1" ></asp:Label><br />
                        <asp:Button ID="Button1"  OnClick="Button1_Click" Text="calculate" />
                    </ContentTemplate>
                </asp:UpdatePanel>
            </div>
        </form>
    </body>
    </html>
    

Usando Scripts de Cliente para Personalizar o Tratamento de Erros

O procedimento anterior demonstrou como personalizar erros durante a renderização parcial da página, definindo propriedades do controle ScriptManager.O procedimento a seguir trabalha com a personalização usando o a classe de cliente PageRequestManager para exibir a mensagem de erro em um elemento <div> em vez de em uma caixa de mensagem do navegador.

Para personalizar manipulação de erro em script de cliente

  1. Na página criada anteriormente, alterne para Modo de exibição Source.

  2. Adicione a seguinte marcação à página.

        <div id="AlertDiv">
            <div id="AlertMessage">
            </div>
            <br />
            <div id="AlertButtons">
                <input id="OKButton" type="button" value="OK"  onclick="ClearErrorState()" />
            </div>
        </div>
    </div>
    
        <div id="AlertDiv">
            <div id="AlertMessage">
            </div>
            <br />
            <div id="AlertButtons">
                <input id="OKButton" type="button" value="OK"  onclick="ClearErrorState()" />
            </div>
        </div>
    </div>
    

    A marcação inclui elementos que você pode usar para exibir erros de renderização parcial da página.Ele define um elemento <div> chamado AlertDiv que contém dois outros elementos <div>.Um dos elementos <div> aninhados contém um controle <input> que permitirá que os usuários ocultem o elemento <div>.

  3. Adicione a seguinte marcação de estilo no elemento <head>:

    <style type="text/css">
    #UpdatePanel1 {
      width: 200px; height: 50px;
      border: solid 1px gray;
    }
    #AlertDiv{
    left: 40%; top: 40%;
    position: absolute; width: 200px;
    padding: 12px; 
    border: #000000 1px solid;
    background-color: white; 
    text-align: left;
    visibility: hidden;
    z-index: 99;
    }
    #AlertButtons{
    position: absolute; right: 5%; bottom: 5%;
    }
    </style>
    
    <style type="text/css">
    #UpdatePanel1 {
      width: 200px; height: 50px;
      border: solid 1px gray;
    }
    #AlertDiv{
    left: 40%; top: 40%;
    position: absolute; width: 200px;
    padding: 12px; 
    border: #000000 1px solid;
    background-color: white; 
    text-align: left;
    visibility: hidden;
    z-index: 99;
    }
    #AlertButtons{
    position: absolute; right: 5%; bottom: 5%;
    }
    </style>
    

    Os estilos tornam as informações de erro se diferenciarem visualmente do restante da página de conteúdo.

  4. Alterne para modo de design e verifique se sua página se assemelha com a que está a seguir:

  5. Na lista drop-down na parte superior da janela Propriedades, selecionar o DOCUMENT elemento (que representa o <body> elemento da página) e defina seu Id propriedade para bodytag.

  6. Alterne para modo de origem.

  7. Adicione o seguinte bloco <script> em qualquer lugar após o elemento <asp:ScriptManager>.

    <script type="text/javascript" language="javascript">
    var divElem = 'AlertDiv';
    var messageElem = 'AlertMessage';
    var bodyTag = 'bodytag';
    Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
    function ToggleAlertDiv(visString)
    {
         if (visString == 'hidden')
         {
             $get(bodyTag).style.backgroundColor = 'white';                         
         }
         else
         {
             $get(bodyTag).style.backgroundColor = 'gray';                         
    
         }
         var adiv = $get(divElem);
         adiv.style.visibility = visString;
    
    }
    function ClearErrorState() {
         $get(messageElem).innerHTML = '';
         ToggleAlertDiv('hidden');                     
    }
    function EndRequestHandler(sender, args)
    {
       if (args.get_error() != undefined)
       {
           var errorMessage;
           if (args.get_response().get_statusCode() == '200')
           {
               errorMessage = args.get_error().message;
           }
           else
           {
               // Error occurred somewhere other than the server page.
               errorMessage = 'An unspecified error occurred. ';
           }
           args.set_errorHandled(true);
           ToggleAlertDiv('visible');
           $get(messageElem).innerHTML = errorMessage;
       }
    }
    </script>
    
    <script type="text/javascript" language="javascript">
    var divElem = 'AlertDiv';
    var messageElem = 'AlertMessage';
    var bodyTag = 'bodytag';
    Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
    function ToggleAlertDiv(visString)
    {
         if (visString == 'hidden')
         {
             $get(bodyTag).style.backgroundColor = 'white';                         
         }
         else
         {
             $get(bodyTag).style.backgroundColor = 'gray';                         
    
         }
         var adiv = $get(divElem);
         adiv.style.visibility = visString;
    
    }
    function ClearErrorState() {
         $get(messageElem).innerHTML = '';
         ToggleAlertDiv('hidden');                     
    }
    function EndRequestHandler(sender, args)
    {
       if (args.get_error() != undefined)
       {
           var errorMessage;
           if (args.get_response().get_statusCode() == '200')
           {
               errorMessage = args.get_error().message;
           }
           else
           {
               // Error occurred somewhere other than the server page.
               errorMessage = 'An unspecified error occurred. ';
           }
           args.set_errorHandled(true);
           ToggleAlertDiv('visible');
           $get(messageElem).innerHTML = errorMessage;
       }
    }
    </script>
    

    Este código faz o seguinte:

    • Define um manipulador para o evento endRequest da classe PageRequestManager.No manipulador, o código exibirá o elemento AlertDiv<div> se houver uma condição de erro.

    • Defina a função ToggleAlertDiv, que oculta ou mostra o elemento AlertDiv e altera a cor da página com base em uma condição de erro.

    • Define a função ClearErrorState, que oculta a interface do usuário da mensagem de erro

  8. Salve suas alterações e, em seguida, pressione CTRL + F5 para exibir a página em um navegador.

  9. Adicionar um número maior que zero a cada caixa de texto e, em seguida, clicar no botão Calculate para demonstrar um postback bem-sucedido.

  10. Altere o valor da segundo caixa de texto para 0 e, em seguida, clicar no botão Calculate para demonstrar uma condição de erro.

    O elemento personalizado AlertDiv é exibido ao invés da caixa de mensagem do navegador.A figura a seguir mostra um exemplo da condição de erro.

    <%@ Page Language="VB" %>
    
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
     "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <script >
        Protected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs)
            Try
                Dim a As Int32
                a = Int32.Parse(TextBox1.Text)
                Dim b As Int32
                b = Int32.Parse(TextBox2.Text)
                Dim res As Int32 = a / b
                Label1.Text = res.ToString()
            Catch ex As Exception
                If (TextBox1.Text.Length > 0 AndAlso TextBox2.Text.Length > 0) Then
                    ex.Data("ExtraInfo") = " You can't divide " & _
                      TextBox1.Text & " by " & TextBox2.Text & "."
                End If
                Throw ex
            End Try
    
        End Sub
        Protected Sub ScriptManager1_AsyncPostBackError(ByVal sender As Object, ByVal e As System.Web.UI.AsyncPostBackErrorEventArgs)
            If (e.Exception.Data("ExtraInfo") <> Nothing) Then
                ScriptManager1.AsyncPostBackErrorMessage = _
                   e.Exception.Message & _
                   e.Exception.Data("ExtraInfo").ToString()
            Else
                ScriptManager1.AsyncPostBackErrorMessage = _
                   "An unspecified error occurred."
            End If
        End Sub
    </script>
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head id="Head1" >
        <title>UpdatePanel Error Handling Example</title>
        <style type="text/css">
        #UpdatePanel1 {
          width: 200px; height: 50px;
          border: solid 1px gray;
        }
        #AlertDiv{
        left: 40%; top: 40%;
        position: absolute; width: 200px;
        padding: 12px; 
        border: #000000 1px solid;
        background-color: white; 
        text-align: left;
        visibility: hidden;
        z-index: 99;
        }
        #AlertButtons{
        position: absolute; right: 5%; bottom: 5%;
        }
        </style>
    </head>
    <body id="bodytag">
        <form id="form1" >
            <div>
                <asp:ScriptManager ID="ScriptManager1"  OnAsyncPostBackError="ScriptManager1_AsyncPostBackError">
                </asp:ScriptManager>
                <script type="text/javascript" language="javascript">
                var divElem = 'AlertDiv';
                var messageElem = 'AlertMessage';
                var bodyTag = 'bodytag';
                Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
                function ToggleAlertDiv(visString)
                {
                     if (visString == 'hidden')
                     {
                         $get(bodyTag).style.backgroundColor = 'white';                         
                     }
                     else
                     {
                         $get(bodyTag).style.backgroundColor = 'gray';                         
    
                     }
                     var adiv = $get(divElem);
                     adiv.style.visibility = visString;
    
                }
                function ClearErrorState() {
                     $get(messageElem).innerHTML = '';
                     ToggleAlertDiv('hidden');                     
                }
                function EndRequestHandler(sender, args)
                {
                   if (args.get_error() != undefined)
                   {
                       var errorMessage;
                       if (args.get_response().get_statusCode() == '200')
                       {
                           errorMessage = args.get_error().message;
                       }
                       else
                       {
                           // Error occurred somewhere other than the server page.
                           errorMessage = 'An unspecified error occurred. ';
                       }
                       args.set_errorHandled(true);
                       ToggleAlertDiv('visible');
                       $get(messageElem).innerHTML = errorMessage;
                   }
                }
                </script>
                <asp:UpdatePanel ID="UpdatePanel1" >
                    <ContentTemplate>
                        <asp:TextBox ID="TextBox1"  Width="39px"></asp:TextBox>
                        /
                        <asp:TextBox ID="TextBox2"  Width="39px"></asp:TextBox>
                        =
                        <asp:Label ID="Label1" ></asp:Label><br />
                        <asp:Button ID="Button1"  OnClick="Button1_Click" Text="calculate" />
                    </ContentTemplate>
                </asp:UpdatePanel>
                <div id="AlertDiv">
                    <div id="AlertMessage">
                    </div>
                    <br />
                    <div id="AlertButtons">
                        <input id="OKButton" type="button" value="OK"  onclick="ClearErrorState()" />
                    </div>
                </div>
            </div>
        </form>
    </body>
    </html>
    
    <%@ Page Language="C#" %>
    
    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <script >
    
        protected void Button1_Click(object sender, EventArgs e)
        {
            try
            {
                int a = Int32.Parse(TextBox1.Text);
                int b = Int32.Parse(TextBox2.Text);
                int res = a / b;
                Label1.Text = res.ToString();
            }
            catch (Exception ex)
            {
                if (TextBox1.Text.Length > 0 && TextBox2.Text.Length > 0)
                {
                    ex.Data["ExtraInfo"] = " You can't divide " +
                        TextBox1.Text + " by " + TextBox2.Text + ".";
                }
                throw ex;
            }
        }
    
        protected void ScriptManager1_AsyncPostBackError(object sender, AsyncPostBackErrorEventArgs e)
        {
            if (e.Exception.Data["ExtraInfo"] != null)
            {
                ScriptManager1.AsyncPostBackErrorMessage =
                    e.Exception.Message +
                    e.Exception.Data["ExtraInfo"].ToString();
            }
            else
            {
                ScriptManager1.AsyncPostBackErrorMessage =
                    "An unspecified error occurred.";
            }
        }
    </script>
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head id="Head1" >
        <title>UpdatePanel Error Handling Example</title>
        <style type="text/css">
        #UpdatePanel1 {
          width: 200px; height: 50px;
          border: solid 1px gray;
        }
        #AlertDiv{
        left: 40%; top: 40%;
        position: absolute; width: 200px;
        padding: 12px; 
        border: #000000 1px solid;
        background-color: white; 
        text-align: left;
        visibility: hidden;
        z-index: 99;
        }
        #AlertButtons{
        position: absolute; right: 5%; bottom: 5%;
        }
        </style>
    </head>
    <body id="bodytag">
        <form id="form1" >
            <div>
                <asp:ScriptManager ID="ScriptManager1"  OnAsyncPostBackError="ScriptManager1_AsyncPostBackError">
                </asp:ScriptManager>
                <script type="text/javascript" language="javascript">
                var divElem = 'AlertDiv';
                var messageElem = 'AlertMessage';
                var bodyTag = 'bodytag';
                Sys.WebForms.PageRequestManager.getInstance().add_endRequest(EndRequestHandler);
                function ToggleAlertDiv(visString)
                {
                     if (visString == 'hidden')
                     {
                         $get(bodyTag).style.backgroundColor = 'white';                         
                     }
                     else
                     {
                         $get(bodyTag).style.backgroundColor = 'gray';                         
    
                     }
                     var adiv = $get(divElem);
                     adiv.style.visibility = visString;
    
                }
                function ClearErrorState() {
                     $get(messageElem).innerHTML = '';
                     ToggleAlertDiv('hidden');                     
                }
                function EndRequestHandler(sender, args)
                {
                   if (args.get_error() != undefined)
                   {
                       var errorMessage;
                       if (args.get_response().get_statusCode() == '200')
                       {
                           errorMessage = args.get_error().message;
                       }
                       else
                       {
                           // Error occurred somewhere other than the server page.
                           errorMessage = 'An unspecified error occurred. ';
                       }
                       args.set_errorHandled(true);
                       ToggleAlertDiv('visible');
                       $get(messageElem).innerHTML = errorMessage;
                   }
                }
                </script>
                <asp:UpdatePanel ID="UpdatePanel1" >
                    <ContentTemplate>
                        <asp:TextBox ID="TextBox1"  Width="39px"></asp:TextBox>
                        /
                        <asp:TextBox ID="TextBox2"  Width="39px"></asp:TextBox>
                        =
                        <asp:Label ID="Label1" ></asp:Label><br />
                        <asp:Button ID="Button1"  OnClick="Button1_Click" Text="calculate" />
                    </ContentTemplate>
                </asp:UpdatePanel>
                <div id="AlertDiv">
                    <div id="AlertMessage">
                    </div>
                    <br />
                    <div id="AlertButtons">
                        <input id="OKButton" type="button" value="OK"  onclick="ClearErrorState()" />
                    </div>
                </div>
            </div>
        </form>
    </body>
    </html>
    

Revisão

Este tutorial mostrou maneiras pelas quais você pode estender a manipulação de erro durante a renderização parcial de páginas.No código do servidor você pode personalizar a manipulação de erro definindo a propriedade AsyncPostBackErrorMessage e manipulando o evento AsyncPostBackError do controle ScriptManager.Você pode personalizar a entrega de erro em código de cliente manipulando o evento endRequest da classe PageRequestManager.

Consulte também

Conceitos

Trabalhando com eventos PageRequestManager

Referência

Classe Sys.WebForms.PageRequestManager

Sys.WebForms.PageRequestManager endRequest eventos