In my custom Joomla 5 component I've added PHPSpreadsheet via composer. In the Export View (Backend) i have a small adminform for setting up the export and a submit button that toggles the download by simply call the Method in the controller by task:
$route = Route::_('index.php?option=com_component&view=export');
...
<form action="<?php echo $route ?>" method="post" name="adminForm" id="adminForm">
...
<input type="hidden" name="task" value="export.export">
In my Export Model I call it like this:
public function export($settings):bool
{
// Required gets
$this->countries = $this->getCountries();
$this->app = Factory::getApplication();
$fileName = 'export.xlsx';
if(!empty($settings['filename'])){
$fileName = $settings['filename'] . '.xlsx';
}
switch ($settings['export_type']) {
case 'startlist':
default:
$arrayData = $this->exportStartList($settings);
break;
}
if (empty($arrayData)) {
$app = Factory::getApplication();
$app->enqueueMessage(Text::_('COM_COMPONENT_EXPORT_NO_DATA'), 'warning');
return false;
}
$spreadsheet = new Spreadsheet();
$spreadsheet->getActiveSheet()->fromArray($arrayData);
$writer = new Xlsx($spreadsheet);
header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
header('Content-Disposition: attachment; filename="' . urlencode($fileName) . '"');
$writer->save('php://output');
Factory::getApplication()->close();
return true;
}
My Problem is quite easy to explain:
- To get the xlsx as download i have to call "exit" / "jexit" or "Factory::getApplication()->close();" > the download does work. But all enqueued messages got lost because of the changed header / the close itself (which makes sense for the CMS - i'ts closed so why rendering any messages now). The thing is: I've added some warnings if the dataset is not complete - it's not 100% necessary but now i'm at a point where i just WANT it to work :-).
Can anyone give me a hint on how to get both: initiate the download and render my enqueued messages on screen?
My Controller is minimalistic:
class ExportController extends FormController
{
// Optional: Declare view name
protected $default_view = 'export';
public function export()
{
error_log('Exporting in CONTROLLER');
// Do some stuff here
$data = $this->input->post->get('jform', [], 'array');
$model = $this->getModel();
if($model->export($data)) $this->setMessage(Text::_('COM_COMPONENT_EXPORT_SUCCESS'));
$this->setRedirect('index.php?option=com_component&view=export');
}
}
if the $arrayData is empty the message got displayed. I've tried it already with and without redirect in controller - no difference.