File error on opening spreadsheet created with Spreadsheet::WriteExcel - excel

I was using Spreadsheet::WriteExcel to create xls file using perl. When the range of spreadsheet increased, the Microsoft excel shows an alert before opening the file "File Error: Data may have been lost".
Please help me to solve this.
Here is the code
my $row = 2;
foreach my $sid(array of students objects)
{
my $s = $students->{$sid};
my $cc = 0;
my $wall = f1($x, $y, $z);#f1 is a method returns hash of arrays that have to write on excel having keys #key_array
foreach my $key (#key_array) {
my $t_row = $row;
my $i_c = 0;
my $t_col = 0;
my $m_row = $max_row;
while($m_row > 0){
$t_col = 3+($cc*7);
if($cc == 0){
$ws->write($t_row, 0,
[$s->{first_name}, $s->{last_name}, $s->{l_name}], $fmt_wrap
);
}
if(defined $wall->{$key}->[$i_c] ){
$ws->write($t_row, $t_col, $wall->{$key}->[$i_c], $fmt_wrap);
} else {
$ws->write($t_row, (3+$cc*7),["","","","","","",""], $fmt_wrap);
}
$t_row++;
$i_c++;
$m_row--;
}#while loop
$ws->write($t_row-1, 3+$company_format*$max_step,
[ (scalar keys %{$s->{videos}}), $s->{total_pageviews} ], $fmt
);
$cc++;
$t_row = 2;
}#foreach loop
$row+=$max_row;
}#foreach student array

I have found answer. In the code there was a line which write data into a cell multiple times. So i found that multiple write attempt to a particular cell can cause file corruption.

Related

Sometimes having Excel export problems

I have a problem, I'm importing cycling a Table to Excel.
My code is look like this :
#WINAPI
#Excel
SysExcelApplication excel;
SysExcelWorkbooks books;
SysExcelWorkbook book;
SysExcelWorksheets sheets;
SysExcelWorksheet sheet;
SysExcelCells cells;
SysExcelCell cell;
SysExcelRange columns;
while select myTable
{
cell = sheet.cells().item(row, col);
cell.value(myTable.FieldI);
sheet.columns().autoFit();
col++;
cell = sheet.cells().item(row, col);
cell.value(myTable.FieldII);
sheet.columns().autoFit();
col++;
row++;
col=1;
}
// when the cycle end save my file
But sometimes I give an error look like message debug
"Wrong argument types in variable assignment"
or
"The number of arguments provided is different from the number of arguments accepted by the method"
But the weird thing is if i try againg to re-launch the export I will not get the errors.
I have this problem
I have same code and same data.
When I generate the file the excle rows are perfect.
I have this problem in 50% of these cases.
The rows created are 1700 more less.
What does it depend on? I have a lot rows? Or other?
I share the same question found on web Some question ,I tried to use, but did't solved my problem:
I add more information not slved my problem change settings
Thanks in advice,
enjoy
Yes, when develop any export Excel had this problem, when many rows. If there are few rows it works perfect.
For this cases always change the excel export for CSV export. The code to export csv file never fail and work perfect!
Here I leave an example to export csv file with 5 rows.
Code:
static void ExportCSV(Args _args)
{
Commaio file;
container lineCSV;
#File
str DatosLinea[500];
int _i;
str filename;
Dialog dialog;
DialogField dialogFileName;
;
dialog = new Dialog("Path CSV");
dialogFileName = dialog.addField(ExtendedTypeStr("FilenameSave"),"Path File:");
if (dialog.run())
{
filename = dialogFileName.value();
}
if (!filename)
{
return;
}
file = new Commaio((filename), 'W'); //Path + file name.csv
file.outFieldDelimiter(';');
if( !file || file.status() != IO_Status::Ok)
{
throw error("File Cannot be opened");
}
DatosLinea[1] = "Col 1";
DatosLinea[2] = "Col 2";
DatosLinea[3] = "Col 3";
DatosLinea[4] = "Col 4";
DatosLinea[5] = "Col 5";
_i = 1;
lineCSV = conNull();
while(_i <= 5){
lineCSV += DatosLinea[_i];
_i += 1;
}
file.write(lineCSV);
info("Export end");
}

Convert CSV to Excel gives file corrupted error

I converted multiple csv files into a excel spreadsheet using the perl script below which is basically a modified version of the code in the link, but i cannot open the output excel file, it gives a pop up message "The file is corrupted."
#!/usr/intel/bin/perl -W
use strict;
use Spreadsheet::WriteExcel::Big;
use Text::CSV_XS;
# Check for valid number of arguments
if (($#ARGV < 1) || ($#ARGV > 2)) {
die("Usage: csv2xls csvfile_dir xlsfile\n");
};
my $csvdir = $ARGV[0];
my $outfile = $ARGV[1];
# Create a new Excel workbook
my $workbook = Spreadsheet::WriteExcel::Big->new($outfile);
my $csvfile = "";
my $tab_title = "";
foreach $csvfile (glob("$csvdir/*.csv")) {
print "$csvfile\n";
# Open the Comma Separated Variable file
open (CSVFILE, $csvfile) or die "$csvfile: $!";
$csvfile =~ s/.*\///;
$tab_title = (split(/\./,$csvfile))[0];
print "-D- $tab_title\n";
# Create a new Excel worksheet
my $worksheet = $workbook->add_worksheet($tab_title);
# Create a new CSV parsing object
my $csv = Text::CSV_XS->new;
# Row and column are zero indexed
my $row = 0;
while (<CSVFILE>) {
if ($csv->parse($_)) {
my #Fld = $csv->fields;
print "-D- #Fld\n";
my $col = 0;
foreach my $token (#Fld) {
$worksheet->write($row, $col, $token);
$col++;
}
$row++;
} else {
my $err = $csv->error_input;
print "Text::CSV_XS parse() failed on argument: ", $err, "\n";
}
}
}
How can i fix it?
You need to close your workbook.
$workbook->close();
Also upgrade your Excel module to the latest version, I also faced the similar issue of corrupted excel files which was solved on updating Spreadsheet::WriteExcel.
Also from docs
Note about the requirement for binmode(). An Excel file is comprised
of binary data. Therefore, if you are using a filehandle you should
ensure that you binmode() it prior to passing it to new().You should
do this regardless of whether you are on a Windows platform or not.
This applies especially to users of perl 5.8 on systems where UTF-8 is
likely to be in operation such as RedHat Linux 9. If your program,
either intentionally or not, writes UTF-8 data to a filehandle that is
passed to new() it will corrupt the Excel file that is created.

search for a cell from one excel and search in another excel and print if its not there using perl

I'm new to perl. I have two excel files containing huge no of rows and just two columns. I want to get each cell from one of the excel files and search whether its there in another excel file or not. if its not then print that cell.
I believe that if I get each cell from one of the excel and search it in another and then run a for loop for all the rows it will be done.
I reached upto getting the cell from first excel but how to search whether it is there in the another excel and printing it is the issue.
can anybody help. ??
I'm not entirely sure what you want, but this might give you some ideas. It's completely untested, though.
use strict;
use Spreadsheet::ParseExcel;
my $parser = Spreadsheet::ParseExcel->new();
my $workbook1 = $parser->parse('Book1.xls');
if (!defined $workbook1) { die $parser->error(), ".\n"; }
my $workbook2 = $parser->parse('Book2.xls');
if (!defined $workbook2) { die $parser->error(), ".\n"; }
$worksheet1 = $workbook1->worksheet('Sheet1');
$worksheet2 = $workbook2->worksheet('Sheet1');
my ($row_min1, $row_max1) = $worksheet1->row_range();
my ($col_min1, $col_max1) = $worksheet1->col_range();
for my $row1 ($row_min1 .. $row_max1) {
for my $col1 ($col_min1 .. $col_max1) {
my $cell1 = $worksheet1->get_cell($row1, $col1);
my ($row_min2, $row_max2) = $worksheet2->row_range();
my ($col_min2, $col_max2) = $worksheet2->col_range();
my $found_match = 0;
for my $row2 ($row_min2 .. $row_max2) {
for my $col2 ($col_min2 .. $col_max2) {
my $cell2 = $worksheet2->get_cell($row2, $col2);
if ($cell1->value() eq $cell2->value()) { # or == ?
$found_match = 1;
break;
}
}
break if $found_match;
}
if (!$found_match) {
print $cell1->value, "\n";
}
}
}
This is mostly from here: http://search.cpan.org/dist/Spreadsheet-ParseExcel/lib/Spreadsheet/ParseExcel.pm

displaying the mismatch into the excel using php

I am importing the the csv data into the database, records which are not matching with the dtdc are the mismatch are mismatched records . I am exporting those records into excel.Below is the else condition which we are taking the mismatch records
else{
$mismarchrows_dtdc[] = $row['Postcode'];
$mismatchcount_dtdc = $mismatchcount_dtdc+1;
}
Here i am writing the mismatched records into excel
$fileName_dtdc = 'uploads/csv/already_exist_customer_dtdc-'.time().'.xls';
$fp = fopen($fileName_dtdc, 'w');
$newLineSeparator = "\r\n";
$line1_dtdc = 'postcode'.$newLineSeparator;
fwrite($fp,$line1_dtdc);
foreach($mismarchrows_dtdc as $mrow){
$line2_dtdc = $mrow;
fwrite($fp,$line2_dtdc);
}
now only one column called postcode is only exported into excel, but i 5 more columns like firstname,lastname,middlename in to the excel with data
I tried by keeping like this, But coming in only one column
else{
$mismarchrows_dtdc[] = $row['Postcode'];
$mismarchrows_dtdc1[] .= $row['State'];
$mismatchcount_dtdc = $mismatchcount_dtdc + 1;
}
can anyone help with this !!!!!!!!!!!!!!!!!
I don't know your exact needs, but maybe this will help?
$csv_lines = array();
foreach($mismarchrows_dtdc as $mrow) {
$keys = array_keys($mrow);
$data = array();
foreach ($keys as $key) {
$data[] = $mrow[$key];
}
$csv_lines[] = implode(',',$data);
}
$fileName_dtdc = 'uploads/csv/already_exist_customer_dtdc-'.time().'.xls';
file_put_contents($fileName_dtdc,implode("\r\n",$csv_lines));

Deleting rows in already existing excel file by using perl

guys,
Iam trying to delete used rows in already existing excel file
i tried with below code
use strict;
use warnings;
use Win32::OLE;
my $xl = Win32::OLE->new('Excel.Application');
$xl->{Visible} = 0;
my $nShtsOld = $xl->{SheetsInOldWorkbook};
$xl->{SheetsInOldWorkbook} = 1;
my $wb = $xl->Workbooks->Open('C:\Users\u304079\Desktop\Test_S1_Legacy_US.xlsx');
$xl->{SheetsInOldWorkbook} = $nShtsOld;
my $sht = $wb->Sheets(o);
my $end = $sht->Usedrange->Row->Count;
print $end;
for (my $count = $end; 0 < $count; $count--)
{
my $cell = $sht->{Cells};
if (!defined $cell->{Value})
{
$cell->entireRow->delete;
}
}
# save and exit
$xl->SaveAs('C:\Users\u304079\Desktop\Test_S1_Legacy_US.xlsx');
$xl->close();
but iam unable to do with following code getting error message as
Can't call method "Usedrange" on an undefined value"
It looks like my $sht = $wb->Sheets(o); may be a typo. Should that be a zero 0 instead?

Resources