santer / exporter
Laravel 包,用于在给定的模板中轻松导出 Word 文档。本包基于 PHPWord。
Requires
- php: ^7.4|^8.0|^8.2|^8.2
- laravel/framework: ^8.0|^9.0|^10|^11
- phpoffice/phpword: ^v1.2
README
用于在 Laravel 中轻松导出 Word 文档的包。本包基于 phpoffice/phpword。
目录
安装
Exporter 通过 Composer 安装。要在项目中添加对 Exporter 的依赖,可以
运行以下命令以使用最新稳定版本
composer require santwer/exporter
或者如果您想使用最新 master 版本
composer require santwer/exporter:dev-master
当然,您也可以手动编辑 composer.json 文件
{ "require": { "santwer/exporter": "v0.3.*" } }
配置(可选)
要使用 PDF 导出,需要安装 LibreOffice。WordTemplateExporter 使用 soffice 命令将 docx 文件转换为 pdf。
sudo apt-get install libreoffice
Windows
从 这里 下载并安装 LibreOffice。也将 soffice 命令的路径添加到系统环境变量中。
export PATH=$PATH:/path/to/soffice
如何使用 ExportClasses
用法
您可以使用以下方式使用 WordExporter Facade。导出文件的格式由文件扩展名确定。支持的格式是 .docx 和 .pdf。
use WordExporter\Facades\WordExporter; // Download as a Word file WordExporter::download(new MyExportClass(), 'final-word.docx'); // Store the exported file WordExporter::store(new MyExportClass(), 'path/to/save/export.docx'); // Store the exported file with an certain filename WordExporter::storeAs(new MyExportClass(), 'path/to/save/', 'export.docx'); // Store the exported file with an certain filename as a batch WordExporter::batchStore( new Exportable(new MyExportClass(), 'path/to/save/', 'export.docx'), new Exportable(new MyExportClass1(), 'path/to/save/', 'export1.docx'), new Exportable(new MyExportClass2(), 'path/to/save/', 'export2.pdf'), ); // Queue it for later processing WordExporter::queue(new MyExportClass(), 'path/to/save/export.docx');
创建新的导出
您可以使用以下 Artisan 命令创建新的导出
php artisan make:word {className}
将 {className} 替换为新导出类的名称。
接口
$export 对象可以通过以下接口实现
每个接口都定义了需要根据导出过程的具体要求实现的方法。这些方法通常涉及返回一个键值对数组,其中键代表 Word 模板中的占位符,值是替换这些占位符的数据。
示例
Word 文件
${TownDateFormat}
${customer}
${name}, ${email}
${deliveryAddress.street}, ${deliveryAddress.city} ${deliveryAddress.postcode}
${/customer}
控制器
namespace App\Http\Controllers; use App\Http\Export\FirstExport; use Santwer\Exporter\Facade\WordExport; class HomeController extends Controller { public function index() { return WordExport::download(new FirstExport(), 'myExport.docx'); } }
导出类
namespace App\Http\Export; use Santwer\Exporter\Concerns\FromWordTemplate; use Santwer\Exporter\Concerns\GlobalTokens; use Santwer\Exporter\Concerns\TokensFromCollection; use Illuminate\Support\Collection; class FirstExport implements FromWordTemplate, TokensFromCollection, GlobalTokens { public function items(): Collection { return collect([ [ 'name' => 'Jane Smith', 'email' => 'jane.smith@example.com', 'deliveryAddress' => [ 'street' => 'Main Street', 'city' => 'Metropolis', 'postcode' => '543210', ], ], [ 'name' => 'Alice Johnson', 'email' => 'alice.johnson@example.com', 'deliveryAddress' => [ 'street' => 'Elm Street', 'city' => 'Springfield', 'postcode' => '987654', ], ], [ 'name' => 'Bob Williams', 'email' => 'bob.williams@example.com', 'deliveryAddress' => [ 'street' => 'Oak Avenue', 'city' => 'Townsville', 'postcode' => '135792', ], ], ]); } public function blockName():string { return 'customer'; } public function values(): array { return [ 'TownDateFormat' => 'Townsville, '. now()->format('Y-m-d'), ]; } public function itemTokens($item) : array { return $item; } public function wordTemplateFile(): string { return 'uploads/myDocFile.docx'; } }
图表
要替换 Word 模板中的图表,可以使用 WithCharts
接口。此接口要求实现 charts
方法,该方法应返回一个键值对数组,其中键代表 Word 模板中的占位符,值是替换这些占位符的数据。您可以在 这里 找到有关图表的所有信息。
可能类型有 'pie', 'doughnut', 'line', 'bar', 'stacked_bar', 'percent_stacked_bar', 'column', 'stacked_column', 'percent_stacked_column', 'area', 'radar', 'scatter'
namespace App\Http\Export; use Santwer\Exporter\Concerns\FromWordTemplate; use Santwer\Exporter\Concerns\GlobalTokens; use Santwer\Exporter\Concerns\WithCharts; use Santwer\Exporter\Concerns\TokensFromCollection; use Illuminate\Support\Collection; class FirstExport implements FromWordTemplate, TokensFromCollection, GlobalTokens, WithCharts { public function charts(): array { return [ 'radar' => function () { $categories = array('A', 'B', 'C', 'D', 'E'); $series1 = [1, 3, 2, 5, 4]; $chart = new Chart('radar', $categories, $series1, [ 'width' => 1000000*5, 'height' => 1000000*5, 'showLegend' => true ],'Series 1'); $chart->addSeries($categories, [3, 4, 5, 1, 2], 'Series 2'); return $chart; }, ]; } public function items(): Collection { return collect([ ]); } ... }
图片
要替换 Word 模板中的图片,可以使用 WithImages
接口。此接口要求实现 images
方法,该方法应返回一个键值对数组,其中键代表 Word 模板中的占位符,值是替换这些占位符的数据。
有关设置图片的更多详细信息,您可以在 这里 找到。
namespace App\Http\Export; use Santwer\Exporter\Concerns\FromWordTemplate; use Santwer\Exporter\Concerns\GlobalTokens; use Santwer\Exporter\Concerns\WithImages; use Santwer\Exporter\Concerns\TokensFromCollection; use Illuminate\Support\Collection; class FirstExport implements FromWordTemplate, TokensFromCollection, GlobalTokens, WithImages { public function images(): array { return [ 'CompanyLogo' => public_path('images/logo.jpg'), 'UserLogo' => 'path' => public_path('images/logo.jpg'), 'width' => 100, 'height' => 100, 'ratio' => false, 'image1' => function () { return [ 'path' => public_path('images/image1.jpg'), 'width' => 100, 'height' => 100, 'ratio' => false, ]; }, ]; } public function items(): Collection { return collect([ ]); } ... }
表格
在Word模板中替换表格时,您可以使用WithTables
接口。此接口需要实现tables
方法,该方法应返回一个键值对数组,其中键代表Word模板中的占位符,值是要替换这些占位符的数据。
注意:在导出PDF时,至少需要设置列宽。未设置列宽可能不会显示。
namespace App\Http\Export; use Santwer\Exporter\Concerns\FromWordTemplate; use Santwer\Exporter\Concerns\GlobalTokens; use Santwer\Exporter\Concerns\WithTables; use Santwer\Exporter\Concerns\TokensFromCollection; use Illuminate\Support\Collection; class FirstExport implements FromWordTemplate, TokensFromCollection, GlobalTokens, WithTables { public function tables(): array { return [ 'table1' => function () { return [ 'headers' => [['width' => 3000, 'text' => 'Name'], 'Email', 'Address'], 'rows' => [ ['Jane Smith', 'jane@smith.com', 'Main Street'], ['Alice Johnson', 'alice@johnson.com', 'Elm Street'], ['Bob Williams', 'bob@williams.com', 'Oak Avenue'], ], 'style' => [ 'borderSize' => 6, 'borderColor' => 'green', 'width' => 6000, ], ]; }, ]; } public function items(): Collection { return collect([ ]); } ... }
在查询中使用
添加特性Exportable
use Santwer\Exporter\Exportable; class User { use Exportable; ... }
默认情况下,所有变量都可在模型中使用。添加一个关注特殊导出字段的关注点。
use Santwer\Exporter\Exportable; use Santwer\Exporter\Concerns\HasTokens; ... class User implements HasTokens { use Exportable; ... public function exportTokens(): array { return [ 'name' => $this->name, 'email' => $this->email, ]; } }
您可以为每个模型添加一个固定的模板。
use Santwer\Exporter\Exportable; use Santwer\Exporter\Concerns\HasTemplate; ... class User implements HasTemplate { use Exportable; ... public function exportTemplate(): string { return '/template.docx'; } }
您还可以为在模板中使用模型定义自己的区块名称。
use Santwer\Exporter\Exportable; ... class User implements HasTemplate { use Exportable; ... protected $exportBlock = 'customer'; }
基本导出
export()会返回下载响应。
return User::where(...) ->template('templatefile.docx') ->export();
如果您在模型中定义了导出模板。
return User::where(...) ->export();
return User::where(...) ->template('templatefile.docx') ->store('storage/path');
return User::where(...) ->template('templatefile.docx') ->storeAs('storage/path', 'name.docx');
在执行查询后或Find-命令后的模型上设置导出命令也是可能的。
return User::where(...) ->first() ->export('filename.docx', ['template' =>' templatefile.docx']);
return User::find(1234) ->export('filename.docx', ['template' =>' templatefile.docx']);
导出为 PDF
通常,使用format = pdf选项可以导出PDF。安装libreOffice执行这些操作是很重要的。
return User::where(...) ->template('templatefile.docx') ->export(['format' => 'pdf']);
对于短期使用,可以调用作为PDF的导出函数。
return User::where(...) ->exportPdf();
return User::where(...) ->exportFirstPdf();
自动加载关系
在导出之前,该包会检查已定义的关系。如果没有相关的变量,它将自动删除不需要的关系。此行为可以在配置中更改。为此,需要在config/中设置一个名为exporter.php的配置文件。
return [ 'removeRelations' => false, ]
此外,该包还会检查尚未加载的关系。在导出之前,它会自动加载关系。因此,可以减少导出代码从
return User::with('posts') ->with('posts.comments') ->with('posts.comments.user') ->template('templatefile.docx') ->export();
到
return User::template('templatefile.docx')->export();
如果关系已经加载,则不会受到影响。
变量
可以设置不受模型或查询影响的变量。
use Santwer\Exporter\Processor\GlobalVariables; ... GlobalVariables::setVariable('Date', now()->format('d.m.Y'));
use Santwer\Exporter\Processor\GlobalVariables; ... GlobalVariables::setVariables([ 'Time' => now()->format('H:i'), 'Date' => now()->format('Y-m-d'), ]);
模板变量/块
在模板中,该包始终寻找循环/区块(除全局变量外)。默认情况下,区块名称是表的名称。也可以使用自己的名称。
use Santwer\Exporter\Exportable; ... class User implements HasTemplate { use Exportable; ... protected $exportBlock = 'customer'; }
要导出具有名称和电子邮件地址的客户,需要添加区块。
${customer}
${name}, ${email}
${/customer}
如果客户中有关系。
use Santwer\Exporter\Exportable; ... class User implements HasTemplate { use Exportable; ... protected $exportBlock = 'customer'; public function deliveryAddress() { return $this->hasOne(Address::class); } }
${customer}
${name}, ${email}
${deliveryAddress.street}, ${deliveryAddress.city} ${deliveryAddress.postcode}
${/customer}
如果有一个与条目集合的关系。
use Santwer\Exporter\Exportable; ... class User implements HasTemplate { use Exportable; ... protected $exportBlock = 'customer'; public function orders() { return $this->hasOne(Order::class); } public function deliveryAddress() { return $this->hasOne(Address::class); } }
${customer}
${name}, ${email}
${orders}
${orders.product_id} ${orders.order_date}
${deliveryAddress.street}, ${deliveryAddress.city} ${deliveryAddress.postcode}
${/orders}
${/customer}
对于每个关系,它都会添加其关系区块名称。
条件关系变量
可以定义与多个条目相关联的变量。因此,可以将其缩减为一个关系,并在关系中获取特定的值。
它只会选择一个条目。
${customer}
${name}, ${email}
Order 15: ${orders:15.product_id} ${orders:15.order_date}
${/customer}
然而,可以设置一个where条件来获取条目。
${customer}
${name}, ${email}
Order 15: ${orders:product_id,=,4.product_id} ${orders:product_id,=,4.order_date}
${/customer}
如果条目未找到,则模型的值将为null。
模板
模板应该是DOCX或DOC格式。如果没有存储选项,文件将克隆并保存在sys_temp_folder中。对于PDF导出,需要使用LibreOffice。因此,需要可执行的soffice命令。
对于模板处理,它使用phpoffice/phpword 更多信息可以在这里找到