Подписывайтесь на наш Telegram канал и будьте в курсе всех событий.

Быстрый экспорт данных в Excel-файлы с помощью FastExcelLaravel

Работа с Excel-файлами в проектах на Laravel — довольно частая задача: отчёты, выгрузка заказов, импорт товаров, интеграции с банками и маркетплейсами. Популярный пакет PhpSpreadsheet даёт огромные возможности, но при больших объёмах данных может быть чудовищно медленным и жутко прожорливым по памяти.

Альтернативой является библиотека avadim/fast-excel-laravel, построенная на основе библиотек FastExcelWriter и FastExcelReader. Она заточена под скорость и минимальное потребление памяти, что особенно важно при работе с десятками или сотнями тысяч строк.

Про FastExcelWriter я уже писал на Хабре. В этой статье опишу, использовать пакет для экспорта данных именно в Laravel-приложении.

Установка

Тут все стандартно:

composer require avadim/fast-excel-laravel

После установки сервис-провайдер и фасад будут зарегистрированы автоматически через Laravel Package Discovery. Если нужно, можно добавить фасад вручную:

'aliases' => [
    'FastExcel' => Avadim\FastExcelLaravel\Facades\Excel::class,
],

Экспорт моделей в Excel

Предположим, у нас есть таблица users, и мы хотим выгрузить всех пользователей в Excel. Самый простой и короткий вариант будет такой:

use Avadim\FastExcelLaravel\Excel;
use App\Models\User;

// Создаем Excel-таблицу с листом, который называется Users
$excel = \Excel::create(‘Users’);
// Экспортируем данные класса
$excel->sheet()->exportModel(User::class);
// Сохраняем в файл в storage
$excel->saveTo('app/public/users.xlsx');

Результат: будет создан файл users.xlsx со всеми пользователями.

Но в файле будут только сами данные, без заголовков. Если хотим, чтобы в первой строке были добавлены заголовки (поля модели), то нужно добавить вызов метода withHeadings(). Кроме того, в этом же методе можем указать, какие именно поля надо выводить в таблицу:

$excel->sheet()
->withHeadings(['id', 'name' => 'Имя'])
->exportModel(User::class);

В этом примере название поля 'id’ будет выводиться, как есть, а в заголовке столбца, куда будет записываться 'name’, будет указано 'Имя'.

Кстати, метод exportModel() позволяет выводить модели из таблиц, содержащих десятки и сотни тысяч записей без особых проблем, в отличие от PhpSpreadsheet.

Экспорт массивов и коллекций

Библиотека позволяет выводить в файл не только модели, но и просто массивы и коллекции Laravel. Для этого используется универсальный метод writeData()

$users = User::where('age', '>', 35)->get();
$excel->sheet()->writeData($users);

И вы можете передать в writeData() не только массив или коллекцию, но и генератор, который в цикле будет возвращать данные для для записи в таблицу:

$excel->sheet()->writeData(function () {
    foreach (User::cursor() as $user) {
        yield $user;
    }
});

Между прочим, если нам не нужно сохранять файл, а нужно сразу отдавать его пользователю, то вместо метода saveTo() нужно вызывать download()

Стилизация

Excel позволяет задавать стили для заголовков, для столбцов, для строк данных:

use Avadim\FastExcelLaravel\Excel;
use avadim\FastExcelWriter\Style;
use App\Models\User;

// Задаем стили для столбцов
$excel->sheet()
    ->setColStyle('B', [Style::WIDTH => 20])
    ->setColStyle('C', [Style::FONT_SIZE => 12, Style::FONT_COLOR => '#f00']);

$excel->sheet()->withHeadings()
    ->applyFontStyleBold() // шрифт заголовка
    ->applyBorder('thin') // границы заголовка
    ->exportModel(User::class);

Подробнее о том, как задаются стили, можно почитать в документации к пакету avadim/fast-excel-writer: https://github.com/aVadim483/fast-excel-writer/blob/master/docs/04-styles.md

И вообще, если вам нужен контроль за формированием Excel-таблицы на более низком уровне (выводить данные по строкам и даже по ячейкам, стилизовать каждую ячейку вывода, добавлять графики, условное форматирование и т.д.), то обратитесь к документации пакета avadim/fast-excel-writer – все его возможности применимы и здесь.