关于laravel:Laravel6-配合-Maatwebsite\Excel-实现-Excel-导出

相比导入,我的项目中导出场景更多,估摸着当初有十多个导出了,之前写了导入,这会才把导出补上。

装置之前说过,这里说一下配置,尽管已有默认配置,但还是有批改配置的场景,所以倡议生成配置文件。

配置

//生成config/excel.php
php artisan vendor:publish --provider="Maatwebsite\Excel\ExcelServiceProvider"

配置只提一个,其余正文蛮细的,

'csv' => [
    'delimiter'              => ',',
    'enclosure'              => '"',
    'line_ending'            => PHP_EOL,
    // 导出csv中文乱码,把use_bom设为true即可
    'use_bom'                => true,
    'include_separator_line' => false,
    'excel_compatibility'    => false,
],

接下来,来实现一个导出的demo阐明下罕用的一些点。

DEMO

php artisan make:export MultiExport

生成文件如下:

<?php

namespace App\Exports;

use Maatwebsite\Excel\Concerns\FromCollection;

class MultiExport implements FromCollection
{
    /**
    * @return \Illuminate\Support\Collection
    */
    public function collection()
    {
        //
    }
}
  • 自定义sheet,减少 WithTitle
  • 自定义列名,减少WithHeadings
  • 不想应用Collection,替换FromCollection应用FromArray
  • 多个sheet,替换FromCollection应用WithMultipleSheets

通过革新:

<?php
/**
 * 多重导出
 */
namespace App\Exports;

use App\Exports\MultiExportA;
use App\Exports\MultiExportB;
use Maatwebsite\Excel\Concerns\WithMultipleSheets;

class MultiExport implements WithMultipleSheets
{
    private $date;

    public function __construct($date)
    {
        $this->date = $date;
    }


    public function sheets(): array
    {
        $sheets = [];

        $sheets[] = new MultiExportA($this->date);
        $sheets[] = new MultiExportB($this->date);

        return $sheets;
    }
}

---
// MultiExportA,MultiExportB类比即可
<?php

namespace App\Exports;

use Maatwebsite\Excel\Concerns\FromArray;
use Maatwebsite\Excel\Concerns\WithHeadings;
use Maatwebsite\Excel\Concerns\WithTitle;
use App\Models\ExportA;

class MultiExportA implements FromArray, WithTitle, WithHeadings
{
    private $date;

    public function __construct($date, $cityId)
    {
        $this->date = $date;
    }

    public function headings(): array
    {
        return [
            'ID',
            '名称',
            '价格',
            '手机'
        ];
    }


    /**
    * @return array
    */
    public function array() : array
    {
        $data = ExportA::where('date', $this->date)
            ->get()
            ->toArray();

        $ret = [];
        foreach ($data as $val) {
            // 一段神奇的代码计算出了价格
            $price = ...;
            $ret[] = [
                'id' => $val['id']."\t",
                'name' => $val['name'],
                'price' => $price,
                // 转换为文本,编码excel应用了迷信计数法
                'mobile' => $val['mobile']."\t",
            ];
        }
        return $ret;
    }

    /**
     * @return string
     */
    public function title(): string
    {
        return '表格A';
    }
}

应用

// 保留
$obj = new MultiExport($date);
Excel::store($obj, 'MultiExport'.$date.'.xlsx');

// 下载csv
Excel::download($obj, 'MultiExport'.$date.'.csv', \Maatwebsite\Excel\Excel::CSV, ['Content-Type' => 'text/csv']);

问题思考

当数据量过大的时候,导出时很可能会内存溢出了。倡议:

  • 应用其余高性能的组件,或者应用原生代码流式输入到浏览器,也能够间接应用其余语言(比方go)编写
  • 文件过大,Excel关上大数据量文件也很鸡肋,容易卡死甚至解体,尝试分文件导出,比方1w一个文件
  • 局部导出过程可能有计算,能够提前计算好,导出时间接读表,应用LazyCollection, 应用 Lazy Collections 来进步 Laravel Excel 读取的性能(轻松反对百万数据)

评论

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

这个站点使用 Akismet 来减少垃圾评论。了解你的评论数据如何被处理