Domanda

I am trying to send an .xlsx sheet to the browser as an attachment, using the example found on cpan cgi.pl, or in the following question: How do I avoid encoding problems with Excel::Writer::XLSX in a CGI environment?.

sub generateMasterList {
    my $command   = $];
    my $workbook  = '';
    my $worksheet = '';
    my $data      = shift;
    my $cgi       = shift;
    my $error     = '';
    my $filename  = "MasterList.xlsx";


    #print "Content-type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\n";
    #print "Content-Disposition: attachment; filename=$filename\n";
    print $cgi->header(-type=>"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", -attachment=>'$filename', -expires=>'-1d');
    binmode STDOUT;
    eval {


        $workbook  = Excel::Writer::XLSX->new(\*STDOUT);
        $worksheet = $workbook->add_worksheet();
    };
    if ($!) {
        $error = "Error Error Error: $!\n";
        return $error;
    }
    else {
        foreach my $i ( 0 .. $#$data ) {
            foreach my $j ( 0 .. $#{ $data->[$i] } ) {

                #print "\n $data->[$i][$j]\n";
                $worksheet->write( $i, $j, $data->[$i][$j] );
            }
        }
        return { success => 1 };
    }

}

The firebug console response from call to the post method displays a bunch of characters along the following lines:

PK�����e8Da]I:O��������[Content_Types].xml���n�0E����*1tQU�E���\{B,������P[Q��M�d��sǎ<-�- �
��'2�:맥x�<�w"CR�(<�b(Fë�d3n�X��(�K���Fa"x�T!5��5MeTz�� oz�[��'�S�!��G���Q����   ��a-lY�P1:�q].��E�7��;;
�6�5��Kh+6}��3���*ыjX%M��"J��]��Ue5�Ǽ��@L�Y�e>��!����=j�O$.�DZ9�GŘ@��q�������6��9�i����ök�(�O�wb��r��?���y��7J|
\��{os��>~PK�����e8D�j%H��&�����xl/workbook.xml�Q�N�0����ij#Z5��KTB�Di�&�4V;���=�T)p�3

In the same response the previous information is followed my a massive array containing my spreadsheet data.

Anyone use this module enough to know why I am not receiving a prompt about an attachment? And what do all the characters represent. Is that the data encoded in some way? I am working with Firefox 12.

È stato utile?

Soluzione 2

I can't see any smoking guns in your code above that would make it fail, but in your similar question to the Excel::Writer::XLSX mailing group, you mentioned using the Dojo javascript library to trigger the download (using Ajax/POST I think).

I've encountered similar issues when trying to initiate binary downloads by POSTing with jQuery Ajax functions, so it's worth checking your Dojo code and if necessary using one of the workarounds for initiating downloads via XHR/Ajax.
I've done this in the past myself using a two-step Ajax conversation, like this:

  1. Browser requests (via Ajax/XHR) that Excel file is built on the server, sending any parameters required via GET/POST, as usual.
  2. Server responds with Json/XML indicating success/failure, and including a URL to where the new binary file can be downloaded, in its response.
  3. Client side code creates a hidden (or out of view) iframe, setting its source as the URL indicated in step 2.

By setting a custom Content-Type, you can hint to the browser that you want a download prompt.

Altri suggerimenti

An XLSX file is basically a zip archive with a bunch of folders and XML files in it. What you are seeing is the binary representation of that ZIP archive.

The code you have commented out should have worked to send the file to the browser, but you need to close off the HTTP header with two newlines:

print "Content-type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\n";
print "Content-Disposition: attachment; filename=$filename\n";
print "\n";

When you tried this without the second \n it would not have output a lot I guess.

Your line using $cgi->header was a smart move, but you are supplying the literal filename $filename because you are using single quotes ('). There is no variable interpolation in those. There is no need to put any quotes at all if it's just the variable you want.

print $cgi->header(-type=>"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", -attachment=>$filename, -expires=>'-1d');

I can't test this right now, but one of these two might solve the problem. If not, I suggest you use something like Live HTTP Headers to look at the headers you are sending. There might be something more wrong.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top