در این آموزش، نحوه اکسپورت دادههای اکسل و CSV با استفاده از پکیج maatwebsite/excel را بررسی میکنیم. معمولا در بعضی از پروژههای لاراولی نیاز به ایمپورت و اکسپورت رکوردها در دیتابیس داریم. پکیج maatwebsite/excel انجام اینکار را برای ما ساده میسازد. البته پکیجهای خوب دیگری مانند rap2hpoutre/fast-excel نیز هستند که خیلی کاربردی هستند.
اکسپورت داده های اکسل و CSV در لاراول 6
برای مطالعه و اجرای این آموزش، بهتر است با قابلیتهای اولیه لاراول آشنایی داشته باشید.
هنگامی که در اپلیکیشن خود از این پکیج استفاده میکنید، بهتر است بدانید که فانکشنهای پکیج در پشت صحنه چه کاری انجام میدهند. دانستن این موضوع باعث میشود حس راحتی و اعتماد به نفس بیشتری در اثر استفاده از حداکثر پتانسیل این ابزار داشته باشد.
Laravel Excel 3.1
پکیج Laravel Excel یک ورژن PhpSpreadsheet متناسب سازی شده با لاراول است: ساده اما قدرتمند برای ساده سازی اکسپورت و ایمپورت.
PhpSpreadsheet یک لایبرری نوشته شده به PHP است که مجموعهای کلاس را ارائه میدهد که امکان این را برای ما فراهم میکند تا فایلهای spreadsheet در فرمتهای مختلف مانند Excel و LibreOffice را بخوانید و بنویسید.
امکانات Laravel Excel
- به راحتی میتوانید کالکشنها را در فایلهای اکسل اکسپورت کنید.
- برای پرفورمنس بهتر میتوانید کوئریها را با چانک کردن اتوماتیک اکسپورت کنید.
- برای پرفورمنس بهتر میتوانید اکسپورتها را در صف قرار دهید.
- به راحتی میتوانید ویوهای بلید را در اکسل اکسپورت کنید.
- به راحتی میتوانید اکسل را به کالکشنها ایمپورت کنید.
- فایل اکسل را میتوانید در چانکها بخوانید.
- ایمپورت insertها در batchها را میتوانید هندل کنید.
نیازمندی ها
- PHP:
^7.0
- Laravel:
^5.5
- PhpSpreadsheet:
^1.6
- PHP extension
php_zip
enabled - PHP extension
php_xml
enabled - PHP extension
php_gd2
enabled
گام 1. نصب
پکیج زیر را در فایل composer.json پروژه لاراول خود قرار دهید. این کار را با کامند زیر میتوانید انجام دهید. این کامند این پکیج و پکیجهای مورد نیاز آن را دانلود میکند.
composer require maatwebsite/excel
➜ laravel6 git:(master) ✗ composer require maatwebsite/excel
Using version ^3.1 for maatwebsite/excel
./composer.json has been updated
Loading composer repositories with package information
Updating dependencies (including require-dev)
Package operations: 4 installs, 0 updates, 0 removals
- Installing markbaker/matrix (1.1.4): Downloading (100%)
- Installing markbaker/complex (1.4.7): Downloading (100%)
- Installing phpoffice/phpspreadsheet (1.9.0): Downloading (100%)
- Installing maatwebsite/excel (3.1.17): Downloading (100%)
phpoffice/phpspreadsheet suggests installing mpdf/mpdf (Option for rendering PDF with PDF Writer)
phpoffice/phpspreadsheet suggests installing tecnickcom/tcpdf (Option for rendering PDF with PDF Writer)
phpoffice/phpspreadsheet suggests installing jpgraph/jpgraph (Option for rendering charts, or including charts with PDF or HTML Writers)
Writing lock file
Generating optimized autoload files
> Illuminate\Foundation\ComposerScripts::postAutoloadDump
> @php artisan package:discover --ansi
Discovered Package: barryvdh/laravel-dompdf
Discovered Package: facade/ignition
Discovered Package: fideloper/proxy
Discovered Package: laravel/tinker
Discovered Package: laravel/ui
Discovered Package: maatwebsite/excel
Discovered Package: nesbot/carbon
Discovered Package: nunomaduro/collision
Package manifest generated successfully.
➜ laravel6 git:(master) ✗
گام 2. کانفیگ پکیج
سرویس پرووایدر Maatwebsite\Excel\ExcelServiceProvider
دارای قابلیت auto-discovered است و به صورت پیش فرض رجیستر میشود.
اگر میخواهید خودتان آن را رجیستر کنید، باید این سرویس پرووایدر را در فایل اضافه کنید.
'providers' => [
/*
* Package Service Providers...
*/
Maatwebsite\Excel\ExcelServiceProvider::class,
]
فساد Excel اتودیسکاور شده است.
اگر میخواهید به صورت دستی اضافه کنید، باید آن را به فایل config/app.php
اضافه کنید.
اگر میخواهید فایل کانفیگ را پابلیش کنید، کامند vendor publish را اجرا کنید:
php artisan vendor:publish --provider="Maatwebsite\Excel\ExcelServiceProvider"
➜ laravel6 git:(master) ✗ php artisan vendor:publish --provider="Maatwebsite\Excel\ExcelServiceProvider"
Copied File [/vendor/maatwebsite/excel/config/excel.php] To [/config/excel.php]
Publishing complete.
➜ laravel6 git:(master) ✗
این کامند فایل کانفیگ excel.php را در config/excel.php
کپی می کند.
گام 3. فایلهای مدل و مایگریشن را بسازید
کامند زیر را اجرا کنید.
php artisan make:model Disneyplus -m
فایل مایگریشن [timestamp].create_disneypluses_table.php را باز کرده و ستونها را به آن اضافه کنید.
public function up()
{
Schema::create('disneypluses', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('show_name');
$table->string('series');
$table->string('lead_actor');
$table->timestamps();
});
}
حالا با استفاده از کامند زیر، دیتابیس را مایگریت کنید.
php artisan migrate
گام 4. یک کنترلر و روتها را بسازید
گام بعدی ساخت فایل DisneyplusController.php است.
php artisan make:controller DisneyplusController
حالا، دو روت زیر را به فایل routes >> web.php اضافه کنید.
// web.php
Route::get('disneyplus', 'DisneyController@create')->name('disneyplus.create');
Route::post('disneyplus', 'DisneyController@store')->name('disneyplus.store');
حالا، دو متد در فایل DisneyplusController.php بنویسید.
<?php
// DisneyplusController.php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Disneyplus;
class DisneyplusController extends Controller
{
public function create()
{
}
public function store()
{
}
}
گام 5. ساخت فرم در فایل بلید برای گرفتن دادهها
حالا، در پوشه views، فایلی با نام form.blade.php بنویسید. کد زیر را به آن اضافه کنید.
@extends('layout')
@section('content')
<style>
.uper {
margin-top: 40px;
}
</style>
<div class="card uper">
<div class="card-header">
Add Disneyplus Shows
</div>
<div class="card-body">
@if ($errors->any())
<div class="alert alert-danger">
<ul>
@foreach ($errors->all() as $error)
<li>{{ $error }}</li>
@endforeach
</ul>
</div><br />
@endif
<form method="post" action="{{ route('disneyplus.store') }}">
<div class="form-group">
@csrf
<label for="name">Show Name:</label>
<input type="text" class="form-control" name="show_name"/>
</div>
<div class="form-group">
<label for="price">Series :</label>
<input type="text" class="form-control" name="series"/>
</div>
<div class="form-group">
<label for="quantity">Show Lead Actor :</label>
<input type="text" class="form-control" name="lead_actor"/>
</div>
<button type="submit" class="btn btn-primary">Create Show</button>
</form>
</div>
</div>
@endsection
گام 6. ذخیره دادهها در دیتابیس
دو متد زیر را در DisneyplusController.php بنویسید.
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Disneyplus;
class DisneyplusController extends Controller
{
public function create()
{
return view('form');
}
public function store(Request $request)
{
$validatedData = $request->validate([
'show_name' => 'required|max:255',
'series' => 'required|max:255',
'lead_actor' => 'required|max:255',
]);
Disneyplus::create($validatedData);
return redirect('/disneyplus')->with('success', 'Disney Plus Show is successfully saved');
}
}
بنابراین، در فایل بالا، ابتدا، فایل فرم را نمایش میدهیم و سپس در متد store ولیدیشن را بررسی کرده و سپس دادهها را در دیتابیس ذخیره میکنیم.
همچنین، فیلدهای فیلیبل را در فایل مدل Disneyplus.php وارد میکنیم.
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Disneyplus extends Model
{
protected $fillable = ['show_name', 'series', 'lead_actor'];
}
گام 7. یک فایل ویو برای نمایش داده ها بسازید.
قبل از ساخت فایل ویو، روت زیر را به web.php اضافه کنید.
// web.php
Route::get('disneyplus/list', 'DisneyplusController@index')->name('disneyplus.index');
حالا، یک فایل ویو با نام list.blade.php بسازید. کد زیر را به آن اضافه کنید.
@extends('layout')
@section('content')
<table class="table table-striped">
<thead>
<th>ID</th>
<th>Show Name</th>
<th>Series</th>
<th>Lead Actor</th>
<th>Action</th>
</thead>
<tbody>
@foreach($shows as $show)
<tr>
<td>{{$show->id}}</td>
<td>{{$show->show_name}}</td>
<td>{{$show->series}}</td>
<td>{{$show->lead_actor}}</td>
</tr>
@endforeach
</tbody>
</table>
@endsection
حالا، متد index() را در فایل DisneyplusController.php بنویسید.
public function index()
{
$shows = Disneyplus::all();
return view('list', compact('shows'));
}
حالا، به آدرس http://localhost:8000/disneyplus/list بروید.
لیست شوها را خواهید دید.
گام 8. کلاس اکسپورت را بسازید
با استفاده از کامند make:export
میتوانید این کار را انجام دهید.
php artisan make:export DisneyplusExport --model=Disneyplus
فایل در دایرکتوری app/Exports
ایجاد خواهد شد.
فایل DisneyplusExport.php را در زیر میبینید.
<?php
namespace App\Exports;
use App\Disneyplus;
use Maatwebsite\Excel\Concerns\FromCollection;
class DisneyplusExport implements FromCollection
{
/**
* @return \Illuminate\Support\Collection
*/
public function collection()
{
return Disneyplus::all();
}
}
اگر مایلید فایل اکسپورت را به دستی ایجاد کنید، میتوانید فایل زیر را در app/Exports
بسازید.
گام 9. فانکشن اکسپورت را بنویسید
در فایل DisneyplusController.php، کد زیر را بنویسید.
// DisneyplusController.php
use App\Disneyplus;
use App\Exports\DisneyplusExport;
use Maatwebsite\Excel\Facades\Excel;
public function export()
{
return Excel::download(new DisneyplusExport, 'disney.xlsx');
}
بنابراین، فایل نهایی شبیه زیر میشود.
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Disneyplus;
use App\Exports\DisneyplusExport;
use Maatwebsite\Excel\Facades\Excel;
class DisneyplusController extends Controller
{
public function create()
{
return view('form');
}
public function store(Request $request)
{
$validatedData = $request->validate([
'show_name' => 'required|max:255',
'series' => 'required|max:255',
'lead_actor' => 'required|max:255',
]);
Disneyplus::create($validatedData);
return redirect('/disneyplus')->with('success', 'Disney Plus Show is successfully saved');
}
public function index()
{
$shows = Disneyplus::all();
return view('list', compact('shows'));
}
public function export()
{
return Excel::download(new DisneyplusExport, 'disney.xlsx');
}
}
در نهایت، روتی برای دسترسی به اکسل بسازید.
// web.php
Route::get('export', 'DisneyplusController@export');
و لینک آن را به لینک اکسل فایل list.blade.php اضافه کنید.
@foreach($shows as $show){{$show->id}}{{$show->show_name}}{{$show->series}}{{$show->lead_actor}}اکسل
@endforeach
لینک http://127.0.0.1/disneyplus/list را باز کرد و حالا میتوانید لینکی با عنوان اکسل را ببینید.
روی لینک اکسل کلیک کنید تا فایل disney.xlsx دانلود شود.
اکسپورت گرفتن از کالکشن ها در CSV در لاراول 6
به صورت پیش فرض، فرمت اکسپورت از طریق اکستنشن فایل مشخص میگردد.
public function export()
{
return Excel::download(new DisneyplusExport, 'disney.csv');
}
اجرای این متد منجر به دانلود یک فایل CSV خواهد شد.
اگر میخواهید فرمت فایل اکسپورت را صراحتا مشخص کنید، میتوانید آن را از طریق پارامتر دوم مشخص کنید.
return (new DisneyplusExport)->download('disney.xlsx', \Maatwebsite\Excel\Excel::XLSX);
مجتبی پاکزاد
حل مساله و چالش رو خیلی دوست دارم و رابطه خیلی خوبی با ریاضیات، برنامهنویسی و اقتصاد دارم. علاقه زیادی به هوشمصنوعی، یادگیری ماشین و موضوعات مرتبط دارم.
Mohammad Javad
سلام خدمت شما یک جایی به من تسکی دادند که یک رابطه many to many پیاده سازی کنم user,category و اینکه وقتی یک فایل اکسل ایمپورت میکنم sheet اول که مربوط به users هم در جدول users پیاده بشه و sheet دوم که مربوط به category هست در جدول catrgory و همچنین رابطه اینها هم یعنی article_category پیاده سازی بشه خیلی ممنون میشم اگه کمکم کنید
مجتبی پاکزاد
سلام تیبل مربوط به رابطه بین categories و users باید category_user باشه، احتمالا منظور شما رابطه بین تیبل categories و articles است. شیت اول مربوط به categories و شیت دوم مربوط به articles و از شیت سوم برای رابطهها استفاده کنید. بهترین راه برای اتصال استفاده از یک ستون یونیک برای ایمپورت است، مثلا اسلاگ یا تایتل یونیک و در تیبل رابطهها از این ستون یونیک برای پیدا کردن رابطهها استفاده کنید. کلیت کار به این صورته که ابتدای باید فایل اکسل آپلود شده، سپس شیتها به ترتیب ذخیره شوند. شیت categories و articles رابطه چند به چند دارند پس رابطه در شیت سوم بعد از این دو شیت ایجاد میگردد، معمولا دیتای این رابطه از طریق id ایجاد نمیشه چون در هنگام ساخت دو شیت id رکوردها مشخص نیست، یک ستون یونیک مثل slug یا code راه حل این مشکل است. اگه انتخاب پکیج به عهده شماست توصیه میکنم برای شروع از پکیج rap2hpoutre/fast-excel استفاده کنید، آموزش تصویری استفاده از این پکیج رو در <a href="https://baversion.com/series/laravel-fast-excel">آموزش ایمپورت و اکسپورت اکسل در لاراول</a> مشاهده کنید، اگه باید از پکیج Laravel Excel استفاده کنید، یا بخشی از مفاهیم توضیح کافی نداشتند بپرسید. موفق باشید.