I have a simple query that generates files using the maatwebsite
namespace App\Exports;
use Maatwebsite\Excel\Concerns\FromCollection;
use App\MyDB;
use Auth;
class ReportExport implements FromCollection
{
public function collection()
{
$email = Auth::user()->email;
return MyDB::MyFunction($email)
->select('Reference_Number')->get();
}
}
everything is working fine, but how can i add headers?
I tried looking at the documentation but it confused me more.
https://laravel-excel.maatwebsite.nl/docs/3.0/export/mapping
I must also admit. The documentation on Laravel Excel tries to mess with your head. You can add headings by adding a headings function to your export class:
use Maatwebsite\Excel\Concerns\WithHeadings;
class ReportExport implements FromCollection, WithHeadings
{
public function collection()
{
$email = Auth::user()->email;
return MyDB::MyFunction($email)
->select('Reference_Number')->get();
}
public function headings(): array
{
return [
'Heading 1',
'Heading 2',
'Heading 3',
];
}
}
Related
Laravel Excel: the date is not formatted in the export
When I try to export, the date in Excel is shown to me as: YYYY-MM-DD.
What I want to get is the date in the following format:
DD/MM/YYYY.
Going into detail, I have the columns shown in the following code; the date column is the one of interest.
This is the code:
<?php
namespace App\Exports;
use App\Models\Client;
use PhpOffice\PhpSpreadsheet\Shared\Date;
use Maatwebsite\Excel\Concerns\WithStyles;
use Maatwebsite\Excel\Concerns\WithHeadings;
use Maatwebsite\Excel\Concerns\FromCollection;
use Maatwebsite\Excel\Concerns\WithColumnFormatting;
use Maatwebsite\Excel\Concerns\WithMapping;
use PhpOffice\PhpSpreadsheet\Style\NumberFormat;
use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet;
class ClientsExport implements FromCollection, WithHeadings, WithStyles, WithMapping, WithColumnFormatting
{
/**
* #return \Illuminate\Support\Collection
*/
public function __construct(private ?\App\Models\Client $client = null)
{
$this->client = $client;
}
public function collection()
{
return is_null($this->client) ? Client::all() : collect([$this->client]);
}
public function headings(): array
{
return ["#", "Nome", "Cognome", "Email", "Città", "Data", "Diagnosi", "Soggiorno", 'Data creazione','Data modifica'];
}
public function styles(Worksheet $sheet)
{
return [
// prima riga con testo in grassetto
1 => ['font' => ['bold' => true]],
];
}
public function columnFormats(): array
{
return [
'F' => NumberFormat::FORMAT_DATE_DDMMYYYY,
];
}
/**
* #var Client $client
*/
public function map($client): array
{
//dd(Date::dateTimeToExcel($client->date));
return [
$client->id,
$client->name,
$client->surname,
$client->email,
$client->city,
Date::dateTimeToExcel($client->date),
$client->diagnosis,
$client->stay
];
}
}
With F I have indicated the date column.
Can anyone kindly help me?
You can make manipulate the attribute in model file:
public function getDateAttribute() {
return $this->attributes['fulldate'] = $this->date->format('Y-m-d');
}
i want to export only today's record from my table not whole data, i used Carbon also it didnt work and it just simply export empty excel file. here i am sharing my code snap please help me.
i am using laravel 7 and latest version of laravel-Excel package.
<?php
namespace App\Exports;
use App\CosQueue;
use Maatwebsite\Excel\Concerns\FromCollection;
use Maatwebsite\Excel\Concerns\ShouldAutoSize;
use Maatwebsite\Excel\Concerns\WithStyles;
use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet;
use Maatwebsite\Excel\Concerns\WithHeadings;
use Maatwebsite\Excel\Concerns\WithEvents;
use Maatwebsite\Excel\Events\AfterSheet;
use Carbon\Carbon;
class CosQueueExport implements FromCollection, WithHeadings, ShouldAutoSize, WithEvents
{
/**
* #return \Illuminate\Support\Collection
*/
public function collection()
{
$todaydate = date('Y-m-d');
return CosQueue::get(array('full_name', 'job_title','meeting_with','subject','date'))->where('created_at',$todaydate);
}
public function headings():array{
return[
"اسم",
'وظیفه',
'ملاقات با',
'موضوع',
'تاریخ'
];
}
public function registerEvents(): array
{
return [
AfterSheet::class => function(AfterSheet $event) {
$cellRange = 'A1:W1'; // All headers
$event->sheet->getDelegate()->getStyle($cellRange)->getFont()->setSize(14);
$event->sheet->getDelegate()->getStyle($cellRange)->getFont()->setName('calibri');
},
];
}
}
You can do one of these
public function collection()
{
// Carbon::today() === today()
return CosQueue::whereDate('created_at', Carbon::today())->get(array('full_name', 'job_title','meeting_with','subject','date'));
}
Also, you can do
public function collection()
{
return CosQueue::whereDate('created_at', date('Y-m-d'))->get(array('full_name', 'job_title','meeting_with','subject','date'));
}
I have upgraded the laravel excel library (Maatswebsite) from 2x to 3.1 (running Laravel 5.6/php 7.1) and trying to make my old data work (download exported file) and cannot work out how to pass my $data (which is an array from a foreach DB query (not eloquent) in controller) to the UsersExport.php class...
If I manually create a test collection (mirroring my $data array) in the class:
return collect([
[
'name' => 'F Name 1',
'surname' => 'Last Name 1',
'email' => 'Email 1'
'date_completed' => 'xx/xx/xx'
],
[
'name' => 'F Name 2',
'surname' => 'Last Name 2',
'email' => 'Email 2',
'date_completed' => 'xx/xx/xx'
]
]);
the above works perfect and the file is created and downloads when I run:
return Excel::download(new UsersExport, 'Test.xlsx');
But I want to pass my array ($data) from the controller to the class and not sure HOW I do this... I am trying to get something like this to work:
return Excel::download(new UsersExport($data), 'Test.xlsx');
From reading the specific posts I could find, I believe I need to create a constructor in the Class to accept my $data - but not sure how, and how to return that data if I succeed in my class accepting the data etc... Is the FromCollection the right option?
private $data;
public function __construct($data)
{
$this->data = $data;
}
Appreciate any assistance.... Thanks in advance.
Your approach is right. then use the collection() function to return that data.
private $data;
public function __construct($data)
{
$this->data = $data;
}
public function collection()
{
return $this->data;
}
if you want passing param data to class you use construct.
Example Controller:
<?php
namespace App\Http\Controllers\Reports;
use App\Http\Controllers\Controller;
use Maatwebsite\Excel\Facades\Excel;
use App\Exports\CustomerinvoiceExport;
use App\Model\OrderInvoiceList;
use Illuminate\Http\Request;
class CustomerInvoiceController extends Controller
{
public function index(Request $request)
{
if ($request->has('start_date')) {
$start_date = $request->start_date;
} else {
$date_now = Carbon::now();
$start_date = $date_now->toDateString();
}
if ($request->has('end_date')) {
$end_date = $request->end_date;
} else {
$date_now = Carbon::now();
$end_date = $date_now->toDateString();
}
$customer_invs = OrderInvoiceList::customer_invoice($start_date, $end_date);
return Excel::download(new CustomerinvoiceExport($customer_invs), 'Customer_Invoice_Report.xlsx');
}
}
}
Class Export
<?php
namespace App\Exports;
use Maatwebsite\Excel\Concerns\FromCollection;
class CustomerinvoiceExport implements FromCollection
{
protected $customer_invs;
/**
* Customer Invoice Report
*/
public function __construct($customer_invs)
{
$this->customer_invs = $customer_invs;
}
/**
* #return invoice_list
*/
public function collection(): array
{
$invoice_list = $this->invoice_list;
...........your logic here....
}
}
I need to export over 100K records to Excel from database using Maatwebsite Laravel excel 3.1 plugin, the problem is that I get data as an array.
$data = $this->client->getData("sc/asistencia-social/informe",$request->all());
return (new ExcelExport($data))->store('myFile.xlsx'); //using FromQuery
My ExcelExport Class :
<?php
namespace App\Exports;
use Maatwebsite\Excel\Concerns\FromQuery;
use Maatwebsite\Excel\Concerns\Exportable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Queue\SerializesModels;
class ExcelExport implements FromQuery
{
use Exportable, SerializesModels;
private $data;
public function __construct($data)
{
$this->data = $data; //Inject data
}
public function query()
{
return $this->data;
}
}
Actually, I get a "Call to a member function chunk() on array" error.
I even tried to convert it into a collection with no success. Is there any possible solution to this.
You have created your export class as FromQuery export class. instead create a FromArray export class.
Note the Implement interface and the function name
class ExcelExport implements FromArray // this was FromQuery before
{
use Exportable, SerializesModels;
private $data;
public function __construct($data)
{
$this->data = $data; //Inject data
}
public function array(): array // this was query() before
{
return $this->data;
}
}
You should use shouldQueue to export large data to an Excel file.
It Worked
In Query remove ->get() or replace with ->paginate(100)
with maatwebsite queue export.
Ill have a problem because my mutators never get called when ill use an constructor:
Like this:
function __construct() {
$this->attributes['guid'] = Uuid::generate(4)->string;
}
public function setDateAttribute($date) {
dd($date); // Never gets called
}
Ill already found out, that the mutators would ne be called when ill use an constructor, so i should use:
public function __construct(array $attributes = array()){
parent::__construct($attributes);
$this->attributes['guid'] = Uuid::generate(4)->string;
}
public function setDateAttribute($date) {
dd($date); // now its getting called
}
But so ill get the following error:
array_key_exists() expects parameter 2 to be array, null given
But i dont know where? Can anyone help me out how to create a default value (like a UUID) for a specific column, and use mutators in the same class?
Edit: Thanks Martin Bean for your help, but i am now getting the following error:
Cannot declare class App\Uuid because the name is already in use
I have tried:
Creating a File called "Uuid.php" in /app/ -> /app/Uuid.php
With this content:
<?php namespace App;
use Webpatser\Uuid\Uuid;
trait Uuid
{
public static function bootUuid()
{
static::creating(function ($model) {
$model->uuid = Uuid::generate(4)->string();
});
}
}
Changed my Model to:
<?php namespace App;
use Carbon\Carbon;
use Illuminate\Database\Eloquent\Model;
class Task extends Model {
use \App\Uuid;
Thank you very much!
Edit 2:
Ill tried it this way:
class Task extends Model {
protected $table = 'tasks';
protected $fillable = ['..... 'date', 'guid'];
public function setGuidAttribute($first=false){
if($first) $this->attributes['guid'] = Uuid::generate(4)->string;
}
TaskController:
public function store() {
$input = Request::all();
$input['guid'] = true;
Task::create($input);
return redirect('/');
}
Works fine, but when ill use:
public function setDateAttribute(){
$this->attributes['date'] = date('Y-m-d', $date);
}
In Task.php ill get:
Undefined variable: date
EDITED:
based on your comment:
i would like to set a field on first insert
use Uuid; //please reference the correct namespace to Uuid
class User extends Model{
protected $fillable = [
'first_name',
'email',
'guid' //add guid to list of your fillables
]
public function setGuidAttribute($first=false){
if($first) $this->attributes['guid'] = Uuid::generate(4)->string;
}
}
Later:
$user = User::create([
'guid' => true, //setAttribute will handle this
'first_name' => 'Digitlimit',
'email" => my#email.com
]);
dd($user->guid);
NB: Remove the __construct() method from your model
Mutators are called when you try and set a property on the model—they’re invoked via the __get magic method. If you manually assign a property in a method or constructor, then no mutators will ever be called.
Regardless, you should not be creating constructors on Eloquent model classes. This could interfere with how Eloquent models are “booted”.
If you need to set an UUID on a model then I’d suggest using a trait that has its own boot method:
namespace App;
trait Uuid
{
public static function bootUuid()
{
static::creating(function ($model) {
$model->uuid = \Vendor\Uuid::generate(4)->string();
});
}
}
You apply the trait to your model…
class SomeModel extends Model
{
use \App\Uuid;
}
…and now each time a model is created, a UUID will be generated and stored in the database with your model.