DEV Community

Cover image for Multiple Sheets Excel Export in Laravel
Rafli Zocky
Rafli Zocky

Posted on • Originally published at Medium on

Multiple Sheets Excel Export in Laravel

This example uses the maatwebsite/excel package.

composer require maatwebsite/excel:^3.1
Enter fullscreen mode Exit fullscreen mode

1. Route

Route::get('/export-excel', [App\Http\Controllers\MyController::class, 'excel'])->name('export-excel');
Enter fullscreen mode Exit fullscreen mode

2. Simple View

Date input and a button that triggers the download.

<div class="mb-4 form-group col-lg-4">
    <label class="form-label">Start Date</label>
    <input type="text" name="start_date" id="start_date" class="form-control" required>
</div>
<div class="mb-4 form-group col-lg-4">
    <label class="form-label">End Date</label>
    <input type="text" name="end_date" id="end_date" class="form-control" required>
</div>

<button type="button" class="btn btn-primary exportExcel">Excel</button>

$(document).on('click', '.exportExcel', function() { 
  var start = $('#start_date').val(); 
  var end = $('#end_date').val(); 

  window.location.href = {{ route('export-excel') }}?start=${start}&end=${end}; 
});
Enter fullscreen mode Exit fullscreen mode

3. Controller

Note: if the query is taking long, then its better to separate the sheets. Just create separate files and try to use FromQuery and WithChunkReading.

use Illuminate\Http\Request;
use Maatwebsite\Excel\Facades\Excel;
use App\Excels\Exports\MyExport;
use Illuminate\Support\Facades\DB;

class MyController extends Controller
{
    public function excel(Request $request)
    {
        $start = $request->start_date;
        $end = $request->end_date;

        // Sheet 1
        $sheet1 = DB::table('users')
            ->select('name','email')
            ->whereBetween('created_at', [$start, $end])
            ->get()
            ->map(fn($r) => [$r->name, $r->email]);

        // Sheet 2
        $sheet2 = DB::table('orders')
            ->select('invoice','total')
            ->whereBetween('created_at', [$start, $end])
            ->get()
            ->map(fn($r) => [$r->invoice, $r->total]);

        return Excel::download(new MyExport($sheet1, $sheet2), 'report.xlsx');
    }
}
Enter fullscreen mode Exit fullscreen mode

4. Export (Multiple Sheets)

namespace App\Excels\Exports;

use Maatwebsite\Excel\Concerns\WithMultipleSheets;
use App\Excels\Exports\Sheets\MySheet;

class MyExport implements WithMultipleSheets
{
    public function __construct(
        protected $sheet1,
        protected $sheet2
    ) {}
    public function sheets(): array
    {
        return [
            new MySheet($this->sheet1, 'Users'),
            new MySheet($this->sheet2, 'Orders'),
        ];
    }
}
Enter fullscreen mode Exit fullscreen mode

5. Sheet Class

Each instance represents one Excel tab.

namespace App\Excels\Exports\Sheets;

use Maatwebsite\Excel\Concerns\FromArray;
use Maatwebsite\Excel\Concerns\WithTitle;
use Illuminate\Support\Collection;
class MySheet implements FromArray, WithTitle
{
    public function __construct(
        protected $data,
        protected $title
    ) {}

    public function array(): array
    {
        if ($this->title === 'Users') {
            return [
                ['NAME', 'EMAIL'],
                ...$this->data->toArray(),
            ];
        }

        return [
            ['INVOICE', 'TOTAL'],
            ...$this->data->toArray(),
        ];
    }

    public function title(): string
    {
        return $this->title;
    }
}
Enter fullscreen mode Exit fullscreen mode

Need help building your app? I’m available for freelance web & Android development — raflizocky.netlify.app

☕ Support my writing: paypal.me/raflizocky · saweria.co/raflizocky

Top comments (0)