2

I need to handle a user's button click action by sending him a binary file stored in a database and also updating the database and the changes reflect in RadGrid using ajax.

When executing the actions, sending the file and updating the grid, separately it happens just fine, but when trying to do both it returns an error saying the response could not be processed.

I was wondering if is there any alternative to accomplish this.

I have similar pieces of code:

javascript:

<asp:ScriptManager ID="ScriptManager1" runat="server" />
    <script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
         <script type="text/javascript">
             var pbControl = null;
             var prm = Sys.WebForms.PageRequestManager.getInstance();
             prm.add_beginRequest(BeginRequestHandler);

             Sys.WebForms.PageRequestManager.getInstance()
                                        .add_endRequest(EndRequestHandler);

             function BeginRequestHandler(sender, args) {
                 $(".loads").attr("disabled", true);
             }

             function EndRequestHandler(sender, args) {
                 if (args.get_error() != undefined) {
                     var errorMessage = args.get_error().message;
                         args.set_errorHandled(true);
                         errorMessage = errorMessage.replace(
                          "Sys.WebForms.PageRequestManagerServerErrorException:", 
                          "");
                         alert(errorMessage);
                }
                 $(".loads").attr("disabled", false);
              }
        </script>
</asp:ScriptManager>

asp.net:

<asp:UpdatePanel ID="UpdatePanel1" runat="server">
    <ContentTemplate>
        <div class="loads">
            <telerik:RadGrid ID="Grid" runat="server" 
                    OnItemCommand="Grid_ItemCommand">
                <MasterTableView TableLayout="Auto">
                    <Columns>
                        <telerik:GridTemplateColumn>
                            <ItemTemplate>
                                <asp:ImageButton ID="Button" runat="server" 
                                  CommandName="Command" 
                                  CommandArgument='<%# Eval("Code") %>' />
                            </ItemTemplate>
                        </telerik:GridTemplateColumn>
                    </Columns>
                </MasterTableView>
            </telerik:RadGrid>
        </div>
    </ContentTemplate>
</asp:UpdatePanel>

c#:

protected void Grid_ItemCommand(object sender, 
                                Telerik.Web.UI.GridCommandEventArgs e)
{
    if(e.CommandName == "Command")
    {
        // Update database
        DatabaseUpdate();
        Grid.Rebind();

        // Send binary
        HttpResponse response = this.Response;
        byte[] bin = GetBinary(code);

        MemoryStream memStream = null;
        memStream = new MemoryStream(bin);

        response.Clear();
        response.AddHeader("content-disposition", 
            string.Format("attachment; filename={0}", "file.pdf"));
        response.ContentType = string.Format("application/{0}", "pdf");
        response.BufferOutput = false;

        byte[] buffer = new byte[1024];
        int bytesRead = 0;
        while ((bytesRead = memStream.Read(buffer, 0, buffer.Length)) > 0)
        {
            response.OutputStream.Write(buffer, 0, bytesRead);
        }

        response.Flush();
    }
}
Eduardo
  • 45
  • 1
  • 6

1 Answers1

0

Sometimes multiple responses from the server makes a way for them to fight with each other, mainly when you use HttpResponse class. No, problem you can do a trick. Add an empty page for pushing the file, say download.aspx

In your Grid_ItemCommand event just remove the code for sending the file. Only do the database updation.

 protected void Grid_ItemCommand(object sender, elerik.Web.UI.GridCommandEventArgs e)
 {
        if(e.CommandName == "Command")
        {
            // Update database
            DatabaseUpdate();
            Grid.Rebind();
            ScriptManager.RegisterStartupScript(Page, this.GetType(), "download","pushFile();", true);
        }
 }

the last line in the above code calls a script pushFile in aspx page and the below script for opening our newly added page download.aspx

Javascript:

function pushFile()
{
  window.open("download.aspx");
}

Then finally in the code behind of download.aspx add the below code in Page_Load

protected void Page_Load(object sender, EventArgs e)
{
        HttpResponse response = this.Response;
        byte[] bin = GetBinary(code);

        MemoryStream memStream = null;
        memStream = new MemoryStream(bin);

        response.Clear();
        response.AddHeader("content-disposition", 
            string.Format("attachment; filename={0}", "file.pdf"));
        response.ContentType = string.Format("application/{0}", "pdf");
        response.BufferOutput = false;

        byte[] buffer = new byte[1024];
        int bytesRead = 0;
        while ((bytesRead = memStream.Read(buffer, 0, buffer.Length)) > 0)
        {
            response.OutputStream.Write(buffer, 0, bytesRead);
        }

        response.Flush();
}
Balaji
  • 1,375
  • 1
  • 16
  • 30