103 lines
3.4 KiB
PHP
103 lines
3.4 KiB
PHP
<?php
|
|
|
|
namespace App\Service\Import;
|
|
|
|
use PhpOffice\PhpSpreadsheet\IOFactory;
|
|
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
|
|
|
|
use Box\Spout\Reader\Common\Creator\ReaderEntityFactory;
|
|
|
|
|
|
class ExcelFileTransformer
|
|
{
|
|
public function transform(string $filePath, string $type = 'csv', int $headerPosition = 3): string
|
|
{
|
|
if (!file_exists($filePath)) {
|
|
throw new \RuntimeException("Le fichier n'existe pas.");
|
|
}
|
|
|
|
$extension = strtolower(pathinfo($filePath, PATHINFO_EXTENSION));
|
|
|
|
if ($extension === 'xls') {
|
|
$filePath = $this->convertXlsToXlsx($filePath);
|
|
} elseif ($extension === 'xlsx') {
|
|
$filePath = $this->purgeXlsx($filePath);
|
|
} else {
|
|
throw new \RuntimeException("Format non pris en charge : .$extension");
|
|
}
|
|
|
|
$reader = ReaderEntityFactory::createXLSXReader();
|
|
$reader->open($filePath);
|
|
|
|
$tmpCsvPath = tempnam(sys_get_temp_dir(), 'converted_') . '.' . $type;
|
|
$handle = fopen($tmpCsvPath, 'w');
|
|
|
|
$rowIndex = 1;
|
|
foreach ($reader->getSheetIterator() as $sheet) {
|
|
if ($sheet->getName() !== '__ACTIVE_SHEET__') {
|
|
continue;
|
|
}
|
|
foreach ($sheet->getRowIterator() as $row) {
|
|
if ($rowIndex++ < $headerPosition) {
|
|
continue;
|
|
}
|
|
|
|
$cells = array_map(function($cell) {
|
|
$value = $cell->getValue();
|
|
if ($value instanceof \DateTime) {
|
|
return $value->format('Y-m-d H:i');
|
|
}
|
|
return $value;
|
|
}, $row->getCells());
|
|
|
|
fputcsv($handle, $cells);
|
|
}
|
|
break;
|
|
}
|
|
$reader->close();
|
|
fclose($handle);
|
|
|
|
return $tmpCsvPath;
|
|
}
|
|
|
|
private function convertXlsToXlsx(string $xlsFilePath): string
|
|
{
|
|
if (!file_exists($xlsFilePath)) {
|
|
throw new \RuntimeException("Le fichier XLS n'existe pas : $xlsFilePath");
|
|
}
|
|
$reader = IOFactory::createReader('Xls');
|
|
$reader->setReadDataOnly(false);
|
|
$spreadsheet = $reader->load($xlsFilePath);
|
|
$activeSheet = $spreadsheet->getSheet($spreadsheet->getActiveSheetIndex());
|
|
$originalTitle = $activeSheet->getTitle();
|
|
$activeSheet->setTitle('__ACTIVE_SHEET__');
|
|
$xlsxFilePath = tempnam(sys_get_temp_dir(), 'converted_') . '.xlsx';
|
|
$writer = new Xlsx($spreadsheet);
|
|
$writer->setPreCalculateFormulas(false);
|
|
$writer->save($xlsxFilePath);
|
|
$activeSheet->setTitle($originalTitle);
|
|
return $xlsxFilePath;
|
|
}
|
|
|
|
private function purgeXlsx(string $filePath): string
|
|
{
|
|
$reader = IOFactory::createReader('Xlsx');
|
|
$reader->setReadDataOnly(false);
|
|
$spreadsheet = $reader->load($filePath);
|
|
|
|
$activeSheet = $spreadsheet->getSheet($spreadsheet->getActiveSheetIndex());
|
|
$originalTitle = $activeSheet->getTitle();
|
|
$activeSheet->setTitle('__ACTIVE_SHEET__');
|
|
|
|
$purgedPath = tempnam(sys_get_temp_dir(), 'purged_') . '.xlsx';
|
|
$writer = new Xlsx($spreadsheet);
|
|
$writer->setPreCalculateFormulas(false);
|
|
$writer->save($purgedPath);
|
|
|
|
// Optionally restore original title in memory
|
|
$activeSheet->setTitle($originalTitle);
|
|
|
|
return $purgedPath;
|
|
}
|
|
}
|