I am trying to export the data in my database; in particular all the customers present but also a single chosen customer.
I tried to set the code only that when I click the button to export all clients a file with no name and no extension is saved.
ClientsExport Class
class ClientsExport implements FromCollection
{
private $client = null;
public function __construct($client = null)
{
$this->client = $client;
}
public function collection(Client $client=NULL)
{
if ($this->client) {
return collect([$this->client]);
}
return Client::all();
}
}
Taking a few tries I found that if I remove the if in the code below, then leaving it alone
return Excel::download(new ClientsExport, 'clients.xlsx');
it works properly, So it seems that the problem is giving it the if
ClientController
public function export(Client $client)
{
if($client){
return Excel::download(new ClientsExport($client), $client->surname . ' ' . $client->name . '.xlsx');
} else {
return Excel::download(new ClientsExport, 'clients.xlsx');
}
}
Routes
Route::get('client-export/{client?}', [ClientController::class,'export'])->name('client.export');
View Blade
Button where I want to export all clients
<a href="{{ route('client.export') }}">Export all clients</a>
Button where I want to export the individual client
<a href="{{ route('client.export' , compact('client')) }}">Export</a>
CodePudding user response:
The issue is that when using route model binding, defining your controller method as: public function export(Client $client)
will supply you with a new "empty" instance of \App\Models\Client
when the client id in your route definition is "empty". Hence, the check below in your controller method will always be truthy.
ClientController::export(\App\Models\Client $client)
if($client){
// ...
} else {
// ...
}
To fix that, you will have to explicitly set the Controller method's parameter to NULL
. This will instruct Laravel's route model binding system to supply you with a NULL
$client
variable instead of an "empty" instance of the Client
model (new \App\Models\Client
) when the client id in your route definition is "empty". ie:
ClientController class
// ...
public function export(\App\Models\Client $client = null)
{
}
// ...
FULL SOLUTION
ClientsExport Class
class ClientsExport implements FromCollection
{
public function __construct(private ?\App\Models\Client $client = null)
{
}
public function collection()
{
return is_null($this->client)
? Client::all()
: collect([
$this->client
]);
}
}
ClientController class
// ...
public function export(\App\Models\Client $client = null)
{
return Excel::download(new ClientsExport($client),
is_null($client)
? 'clients.xlsx'
: $client->surname . ' ' . $client->name . '.xlsx'
);
}
// ...