How to print some part of blade file in Laravel with domPDF - php

I have to create a pdf file with Laravel. So I install in my composer domPDF. But I have to generate the pdf with only some parts of my blade file. I've already tried to create a new blade file and include it in the old blade file, but this return to me errors as the new blade file can't get the data I passed with the controller, so what can I do?
This is the function I wrote
public function printPDF(){
$pdf = PDF::loadView('pages.newblade');
return $pdf->download('document.pdf');
}
Thanks

I am suggesting an option to refactor your code like this
public function printPDF(){
$printthis = true;
$pdf = PDF::loadView('pages.newblade', compact('printthis'));
return $pdf->download('document.pdf');
}
on pages.newblade check printthis variable if present means show the printable content else show all like this
#if(isset($printthis))
//printable code goes here
#else
//General code goes here
#endif

Related

Laravel: DOMPDF error when trying to get PDF

I've been trying to get the PDF of a view using DOMPDF with a table full of ingredients populated from a database table.
I created a function in my Controller:
public function createPDF() {
// retreive all records from db
$data = Ingredients::all();
// share data to view
view()->share('ingredients', $data);
$pdf = PDF::loadView('printableingredientslist', $data);
// download PDF file with download method
return $pdf->download('printableingredientslist.pdf');
}
And the route in web.php is defined as:
Route::get('/printpreviewingredients/pdf', [MealPlanDisplayController::class, 'createPDF']);
However, I keep getting this error:
fopen(D:\mealplan\storage\fonts//nunito_normal_46b9b3b48cc3ddbae60da82f1c1c5d29.ufm):
failed to open stream: No such file or directory
It must be something to do with the 'printableingredientslist' as when I replaced it with a plain view page with simple text that worked. I am struggling to see how there's a path issue however, as printableingredientslist.blade.php is simply under the views folder. What can the issue be? I am using tailwind.css, could that be a problem?
setOptions method to use default font.For example like below
public function pdf()
{
$pdf = \PDF::loadView('contact')->setOptions(['defaultFont' => 'sans-serif']);
return $pdf->download('invoice.pdf');
}
or
Create the directory fonts in storage directory
Ref: https://github.com/barryvdh/laravel-dompdf/issues/724
Ref:https://github.com/barryvdh/laravel-dompdf/issues/176
Ref:https://github.com/barryvdh/laravel-dompdf/issues/269

Laravel: Generate PDF of Blade View and Store it in specified folder

I have a Laravel Blade View, which is fetching data from Database. It is working perfectly.
Here is my Controller:
$model = new outbound_detail;
$data = $model->where('reference', $reference)->get();
$sku_count = $data->count();
$model2 = new outbounds;
$data_model2 = $model2->where('reference',$reference)->first();
$date = $data_model2->created_at;
return view('ims.release.release_invoice',compact('data'))->with('sku_count',$sku_count)->with('reference',$reference)->with('date',$date)->with('warehouse',$warehouse);
Now instead of returning this view I want to save this view as PDF in my folder: public/uploads
I have already installed the composer for DOMPDF.
How can I convert this page to pdf with passing all variables to view file without returning the view.
i use this libraries, it's depends on your needs:
https://github.com/dompdf/dompdf
https://github.com/barryvdh/laravel-dompdf
https://github.com/niklasravnsborg/laravel-pdf
https://packagist.org/packages/carlos-meneses/laravel-mpdf

Laravel does not return view

Currently I'm working on a Laravel project and I try to return a view in my controller. So far, so good.
But, when I really want to show the data from the view, nothing gots returned. It only shows a white screen.
So, what can be the problem? I don't know yet.
This is my current code
public function show(Domain $inputDomain)
{
$domainId = Domain::where('domain', $inputDomain->domain)->firstOrFail()->id;
$scanId = Scan::where('domain_id', $domainId)->firstOrFail()->id;
$result = Result::where('scan_id', $scanId)->firstOrFail();
return view('detail');
}
The last return does not work, it does not show the view.
Good to know:
1. When I just dump (dd) true, it works and I see the true-message
2. The view really exists and it contains data (I also tried to replace the blade template with some 'lorem ipsum' data, but also that did'nt show up)
When I just do a dd on the View::render (made an $view variable and did dd($view->render()) it shows me the HTML (in the DD screen), but when I return it, it is empty.
Comments
According to a comment I want to show the Route that I'm using
Route::get('{domain}', 'DomainController#scan');
According to a comment, I also want to show that I point to a file in the root of views/
How can I show the view to the visitor?
Also good to know, (forgot to mention)
This is my #scan function
public function scan(Domain $domain)
{
Dispatch(new ProcessScan($domain));
$this->show($domain);
}
Found the problem
I forgot to return the data in #scan
Changed the code to
public function scan(Domain $domain)
{
Dispatch(new ProcessScan($domain));
return $this->show($domain); //Added return
}
And it is working

Laravel 5 - Where should I write this function, and how?

Goodevening,
I have an overview page where I display all my project items.
I have a model (Project.php) a controller (ProjectController) where I send the variable $project (this includes all the information for each project) to the specific view.
Note: Each project has a own row in the database. (Quit obvious I guess)
Now I also have a table 'tasks' related to a specific project. In my view I wanna display how much of the total tasks are 'done'. (This is doing with the column 'done' (true/false, boolean)).
Now because I have a foreach function in my view (to display each individuele project) I can make the function in the view. But the Laravel framework is there for reasons. And writing out a lot of php in a view isn't the right way.
But, where should I make this function? And how can I use it in my foreach (in the view). Ofcourse I can make a new foreach in my model or controller and send that variable to my view. But then I can't use that one in my view-foreach as things will get mixed up.
I don't know how/where I can set up a function like this on a clean way.
Kinds regards,
Dylan
You can create a function in app directory(forexample app/Helpers/), or wherever you want and name it yourHelperFunction.php.
After creating that file, Laravel won’t recognize the file until it is registered inside composer.json file. Add files array inside autoload section.
.
.
.
"autoload": {
"files":[
"app/Helpers/yourHelperFunction.php"
]
}
.
.
.
then do composer dump autoload and you are ready to use the function inside the blade
Use Blade engine, not Core PHP loops.
It is wise to use blade engine then core php codes.
You can see the documentation
Laravel 5 Blade Template
Thanks for the help. I've figured it out (I guess?).
I have this function in my Project Model.
public function getTaskDonePercentage($id) {
$tasks = Task::where('project_id', $id)->count();
$tasks_done = Task::where([
['project_id', $id],
['status', 'done']
])->count();
if ($tasks_done > 0) {
$calc = ($tasks_done / $tasks) * 100;
}
else {
$calc = '100';
}
return round($calc) . '%';
}
Then in my view I just call the function in the foreach like:
#foreach
{{ $project_item->getTaskDonePercentage($project_item->id) }}
#endforeach
Tbh I still wanna know if this approach is a good one. (Or, if not, why it isnt?).
Thanks!

Save blade templates to database rather than file

I want to save my blade templates to database, because the header and footer of each page is customizable for the user. I want to let my users create the layout themselves and then for each request from a given user, I want to serve the page, using the layout specified by that user.
The necessary variables that are passed by the controller are provided to them in the documentation.
Note: I trust my users. They are all stake-holders of the project and are programmers, so server side code execution is acceptable.
Although this is an old post but just in case someone stumbles across it like I did. I achieved similar while using the Laravel Framework, by saving the view in database such that, whenever I need to display the view, I retrieve it from DB, and load it into a file using the file_put_contents() php function and render it with the view() method. For example;
$blade = DB::table('pages')->where('name', 'index')->first();
file_put_contents('template.blade.php', $blade->view);
//Note if I also need to pass data to the view I can also pass it like so
//$data = ['page_title' => 'Testing Blade Compilation using views Saved in DB'];
// return view(template, $data);
return view('template');
While again in my own case for added security, I created base templates with the blade templating scheme & injected user created inputs into the template after sanitizing the generated input using HTMLPurifier and rendering the view. For example
$view = view('base.template')->render();
//similarly like the above I can load any data into the view like so
//$data = ['page_title' => 'Testing Blade Compilation using views Saved in DB'];
//$view = view('base.template', $data)->render();
$purifier = new HTMLPurifier(HTMLPurifier_Config::createDefault());
$with_purified_input = $purifier->purify($user_generated_input);
str_replace('view_variable', $with_purified_input, $view);
return $view;
I realised that I can improve security and caching if I just let them insert the static content only. The only thing I need to change is the main content, so I can just let them set a token where the content is to be placed. As is in the above answer by #huzaib-shafi , I did the following...
//In controller
$content = View::make('final',compact('data'));
$token = "<meta name='_token' content='" . csrf_token() ."'";
$scripts = View::make('final_scripts',compact('data'));
$view = str_replace_first("<%content%>", $content, $templateInDatabase);
$view = str_replace_first("<%token%>", $token, $view);
$view = str_replace_first("<%scripts%>", $scripts, $view);
return $view;
This enforces them to use bootstrap in their template, because I use bootstrap styles in my blade templates, but it is acceptable in my case.
I asked and answered a similar question some days ago. So far as I know, Blade doesn't process view content from database columns. Although you can use compileString() method of View. But you should have a look at the following questions.
Extend Blade Template from Database stored string
Let users create custom blade layouts / store in database
In Laravel 9 you can use blade Facades to render from DB:
use Illuminate\Support\Facades\Blade;
return Blade::render('Your Blade Content {{ $parameter1}}', ['parameter1' => 'Name']);

Categories