Laravel - big collection and page load slow - php

I have a project for food ordering. On my object(restaurant) show page I'm calling all product categories with relationship for foreach products that belongs to that category.
I'm also using laravel livewire and this is my Component:
<?php
namespace App\Http\Livewire\Stores;
use Livewire\Component;
use Illuminate\Http\Request;
use App\Models\Store;
use App\Models\CategoryProduct;
use App\Models\Product;
use App\Http\Livewire\Cart;
use App\Models\Favourite;
use Session;
use Auth;
class Show extends Component
{
public $store;
public $categories;
public $ratings;
public $message = '';
public $supplements = [];
public $supplementsArray = [];
public $features = [];
public $featuresArray = '';
public $quantity = 1;
public $deliveryPrice = 0;
public function render(Request $request)
{
if(!Session::has('cart')){
return view('livewire.stores.show');
}
$items = explode('|', $this->featuresArray);
$oldCart = Session::get('cart');
$store_id = $this->store->id;
$oldCart->deliveryPrice = $this->store->delivery_price;
if($oldCart->storeId != $store_id){
$request->session()->forget('cart');
}
$cart = new Cart($oldCart);
//dd(session()->get('cart'));
return view('livewire.stores.show',[
'products' => $cart->items,
'totalPrice' => $cart->totalPrice + $cart->deliveryPrice,
'totalQty' => $cart->totalQty,
'ordersPrice' => $cart->ordersPrice,
'storeId' => $cart->storeId,
]);
}
}
This public $categories; variable is from my Controller:
/**
* Display the specified resource.
*
* #param int $id
* #return \Illuminate\Http\Response
*/
public function show($id)
{
$store = Store::find($id);
$categories = CategoryProduct::where('store_id', $store->id)->get();
$ratings = $store->getAllRatings($store->id);
if($store->checkWorktime() == 'Zatvoreno'){
return view('website.stores.closed', compact('store', 'categories', 'ratings'));
}
return view('website.stores.show', compact('store', 'categories', 'ratings'));
}
And in my blade view this is how I'm viewing it:
#foreach($categories as $category)
<div class="row m-0" id="{{$category->id}}">
<h6 class="p-3 m-0 bg-light font-weight-bold w-100">{{$category->title}} <span class="float-right">
<small class="text-black-50">{{count($category->categoryProducts)}} proizvoda</small></span>
</h6>
<div class="col-md-12 px-0 border-top">
<div class="">
<ul class="list-group list-group-flush">
#foreach($category->categoryProducts as $product)
<a href="#0" class="list-group-item list-group-item-action" data-toggle="modal" data-target="#modal{{$product->id}}">
<div class="row">
<div class="col-9">
<b class="text-dark">{{$product->title}}</b><br>
<small class="text-muted">{{$product->description}}</small><br><br>
#if($product->features->isNotEmpty())
<small class="text-dark" style="font-size:14px !important;">od {{$product->price}}€</small>
#else
<small class="text-dark" style="font-size:14px !important;">{{$product->price}}€</small>
#endif
</div>
#if($product->thumbnail)
<div class="col-3">
<span class="float-right">
<img src="{{$product->thumbnail->getUrl('showPreview')}}" style="width:80px;height:80px;border-radius:50%;object-fit:cover;" alt="">
</span>
</div>
#endif
</div>
</a>
#include('website.stores.product-modal')
#endforeach
</ul>
</div>
</div>
</div>
#endforeach
And my page is loading crazy slow. I know I'm something doing wrong and I know that there is a way to speed this up. How can I do that?

Related

post request not working in laravel livewire

hello guys I'm new to laravel and livewire please kindly assist, post request not going through , if i click on the submit nothing is happening, I'm not getting error either, I have added the livewire script in my app.blade.php and it's rendering properly
Post Create form
<div>
<div class="p-4 mx-auto mt-3 bg-gray-100 md:p-8 md:w-4/5 md:mt-0">
<h1 class="mb-3 text-xl font-semibold text-gray-600">New post</h1>
<form wire:submit.prevent="createPost" action="#" class="px-4 py-6 space-y-4">
<div class="overflow-hidden bg-white rounded-md shadow">
<div class="px-4 py-3 space-y-8 sm:p-6">
<div class="grid grid-cols-6 gap-6">
<div class="col-span-6 sm:col-span-3">
<input class="w-full" type="text"
wire:model="post.title" placeholder="Post title" />
</div>
</div>
<div class="flex flex-col">
<textarea id="body" rows="4" wire:model="post.body"
class="border-gray-300 rounded-sm form-textarea">
</textarea>
</div>
</div>
<div class="px-4 py-3 text-right bg-gray-50 sm:px-6">
<button type="submit" class="inline-flex justify-center">
post
</button>
</div>
</div>
</form>
</div>
</div>
this is my post create livewire method
<?php
namespace App\Http\Livewire;
use App\Models\Post;
use Livewire\Component;
use Illuminate\Http\Response;
class PostCreate extends Component
{
public $post;
public $points = 10;
public $energy = 1;
public function increment()
{
$this->points++;
}
protected $rules = [
// 'category' => 'required|integer|exists:categories,id',
'title' => 'required|min:4',
'body' => 'required|min:4',
];
public function createPost()
{
if (auth()->check()) {
$this->validate();
$post = Post::create([
'user_id' => auth()->user()->id,
// 'category_id' => $this->category,
'body' => $this->body,
'title' => $this->title,
]);
$users = auth()->user();
$users->increment('points', 10);
session()->flash('success_message', 'Post was added successfully!');
$this->reset();
return redirect()->route('posts.index');
}
// abort(Response::HTTP_FORBIDDEN);
}
public function render()
{
return view('livewire.post-create');
}
}
There are two thing here to note - you don't initialize $this->post and you don't have the proper validation. You need to check for post.title and post.body, and you also need to display the actual errors.
<?php
namespace App\Http\Livewire;
use App\Models\Post;
use Livewire\Component;
class PostCreate extends Component
{
public $post;
public $points = 10;
public $energy = 1;
public function mount()
{
$this->post = new Post;
$this->post->user_id = auth()->id();
}
public function increment()
{
$this->points++;
}
protected $rules = [
// 'category' => 'required|integer|exists:categories,id',
'post.title' => 'required|min:4',
'post.body' => 'required|min:4',
];
public function createPost()
{
if (auth()->check()) {
$this->validate();
$post = $this->post->save();
auth()
->user()
->increment('points', 10);
session()->flash('success_message', 'Post was added successfully!');
$this->reset();
return redirect()->route('posts.index');
}
// abort(Response::HTTP_FORBIDDEN);
}
public function render()
{
return view('livewire.post-create');
}
}
To display the errors from validation, you can add the following snippet in your blade-file,
#if ($errors->any())
<ul>
#foreach ($errors->all() as $error)
<li>{{ $error }}</li>
#endforeach
</ul>
#endif
Add lazy to the wire.model:
<input class="w-full" type="text" wire:model.lazy="post.title" placeholder="Post title" />
<textarea id="body" rows="4" wire:model.lazy="post.body" class="border-gray-300 rounded-sm form-textarea"></textarea>

Missing required parameters for [Route: voluntier.submit.get] [URI: voluntier/submit/{id}]

I am currently working on my final project, but I got this error and I have tried to change the route action on my html to {{ route('voluntier.submit.get') }} but it still shows the error. Could anyone help me to find the solution.
Thank you so much
VoluntierController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Event;
use App\City;
use App\User;
use App\VoluntierProfile;
use App\Submission;
class VoluntierController extends Controller
{
public function index()
{
$data = Event::select('events.job_desk', 'events.location', 'events.city', 'events.job_description', 'events.fee', 'cities.name as city', 'job_desks.job_desk')
->leftJoin('job_desks', 'events.job_desk', 'job_desks.id')
->leftJoin('cities', 'events.city', 'cities.id')
->get();
$data_category_liaison = Event::select('events.job_desk')
->where('id' , '=', 2)
->count();
// dd($data_category);
return view('voluntier.index', compact('data', 'data_category_liaison'));
}
public function profile()
{
return view('voluntier.profile');
}
public function createProfile()
{
$city = City::all()->where('id', '!=', '0');
return view('voluntier.profile-edit', compact('city'));
}
public function storeProfile(Request $request)
{
$profile = new VoluntierProfile();
$profile->voluntier_id = $request->input('voluntier_id');
$profile->about = $request->input('tentang');
$profile->city_id = $request->input('kota');
$profile->address = $request->input('alamat');
$profile->latest_education = $request->input('pendidikan_terakhir');
$profile->save();
}
public function submitCreate($id)
{
$event = Event::find($id)->first();
$voluntier = Voluntier::find(Auth::user()->id)->get();
// dd($voluntier);
return view('voluntier.submit', compact('data'));
}
public function submitStore($id, Request $request)
{
$event = Event::find($id);
$voluntier = Auth::user();
$submission = new Submission();
$submission->event_id = $event->id;
$submission->voluntier_id = $voluntier->id;
$submission->status_id = $request->input('status');
$submission->save();
return redirect('voluntier/dashboard');
}
}
index.blade.php
#foreach($data as $row)
<td><a href="{{ route('voluntier.submit.get', $row->id) }}" class="job-item d-block d-md-flex align-items-center border-bottom fulltime">
<div class="company-logo blank-logo text-center text-md-left pl-3">
<img src="images/company_logo_blank.png" alt="Image" class="img-fluid mx-auto">
</div>
<div class="job-details h-100">
<div class="p-3 align-self-center">
<h3>{{ $row->job_desk }}</h3>
<div class="d-block d-lg-flex">
<div class="mr-3"><span class="icon-suitcase mr-1"></span>{{ $row->location }}</div>
<div class="mr-3"><span class="icon-room mr-1"></span>{{ $row->city }}</div>
<div><span class="icon-money mr-1"></span>Rp. {{ $row->fee }}</div>
</div>
</div>
</div>
<!-- <div class="job-category align-self-center">
<div class="p-3">
<span class="text-info p-2 rounded border border-info">Full Time</span>
</div>
</div> -->
</a></td>
#endforeach
submit.blade.php
<form action="{{ route('voluntier.submit.post', $event->id) }}" method="post" class="p-5 bg-white">
My route
web.php
Route::prefix('voluntier')->group(function() {
Route::get('/login', 'Auth\LoginController#showVoluntierLoginForm')->name('voluntier.login.get');
Route::post('/login/post', 'Auth\LoginController#voluntierLogin')->name('voluntier.login.post');
Route::get('/register', 'Auth\RegisterController#showVoluntierRegisterForm')->name('voluntier.register.get');
Route::post('/register/post', 'Auth\RegisterController#createVoluntier')->name('voluntier.register.post');
Route::get('/dashboard', 'VoluntierController#index')->middleware('auth:voluntier')->name('voluntier.dashboard');
Route::get('/profile', 'VoluntierController#profile')->middleware('auth:voluntier')->name('voluntier.get');
Route::get('/profile/get', 'VoluntierController#createProfile')->middleware('auth:voluntier')->name('voluntier.profile.get');
Route::post('/profile/post', 'VoluntierController#storeProfile')->name('voluntier.profile.post');
Route::get('/submit/{id}', 'VoluntierController#submitCreate')->middleware('auth:voluntier')->name('voluntier.submit.get');
Route::post('submit/post/{id}', 'VoluntierController#submitStore')->name('voluntier.submit.post');
});

How I use relationship in blade template (hasOne) || Laravel

Okay i'm trying get "likes" and "users" in Posts by relationship hasOne.
here is my Post.php Model
class Posts extends Model
{
protected $table = 'posts';
public function User()
{
return $this->hasOne(User::class, 'id', 'user_id');
}
public function Like()
{
return $this->hasOne(Like::class, 'post_id', 'id');
}}
My Blade template
#foreach ($showdeals as $deal)
<div class="tab-pane active" id="home" role="tabpanel">
<div class="card-body">
<div class="profiletimeline">
{{$deal->like->status}}
<br>
{{$deal->user->email}}
<div class="sl-item">
<div class="sl-left"> <img src=" {{asset( '/assets/images/users/2.jpg')}}" alt="user" class="img-circle"> </div>
<div class="sl-right">
<div> {{$deal->user->username}} || {{$deal->subject}} <Br> <span class="sl-date">{{$deal->created_at}}</span>
<div class="m-t-20 row">
<div class="col-md-3 col-xs-12"><img src="{{$deal->image}}" alt="user" class="img-responsive radius"></div>
<div class="col-md-9 col-xs-12">
<p> {{$deal->body}} </p> עבור למוצר </div>
</div>
<div class="like-comm m-t-20"> 2 תגובות <i class="fa fa-heart text-danger"></i> 5 לייקים </div>
</div>
</div>
</div>
</div>
<hr></div>
</div>
#endforeach
And there is my Controller
class PostsController extends Controller
{
public function showdeals()
{
$showdeals = Posts::with( 'User', 'Like')->get();
return view('posts.show', compact('showdeals'));
}
public function helpnewview(){
return view('posts.anew');
}
public function helpnew(Request $request){
//User pick link
$userlink = $request['userlink'];
return \Redirect::route('newdeal', compact('userlink'));
}
public function new(Request $request)
{
//Emdeb user link
$link = Embed::create($request['userlink']);
$linke = $request['userlink'];
return view('posts.new', compact('link', 'userlink', 'linke'));
}
public function create(Request $request)
{
$posts = New Posts;
$posts->user_id = Auth::User()->id;
$posts->subject = $request['subject'];
$posts->body = $request['body'];
$posts->link = $request['link'];
$posts->price = $request['price'];
$posts->image = $request['image'];
$posts->tag = $request['tag'];
$posts->save();
return back();
}
}
Now if I do something like {{$deal->user->email}} its will work,
if I go to something like this {{$deal->like->status}} its does not work,
am I missing something ?
If you want multiple relationships to be eagerly loaded you need to use an array of relationships: Model::with(['rl1', 'rl2'])->get();
public function showdeals()
{
...
$showdeals = Posts::with(['User', 'Like'])->get();
...
}
EDIT:
From that json in the comments that I see, there is no attribute named status in your Like model so thats probably the root of the problem
Controller edit this code
public function showdeals()
{
$showdeals = Posts::all();
return view('posts.show', compact('showdeals'));
}
And blade file code
#foreach ($showdeals as $deal)
<div class="tab-pane active" id="home" role="tabpanel">
<div class="card-body">
<div class="profiletimeline">
{{ $deal->Like->status }}
<br>
{{ $deal->User->email }}
#endforeach
I think everything is good except
{{$deal->like->status}} {{$deal->user->email}}
Please try as
{{$deal->Like()->status}}
<br>
{{$deal->User()->email}}

pagination in laravel in frontend using relationship

>
I want to use pagination in category view. I only want to display 5 posts of that specific category which is selected using a slug.
I want pagination link in below.
This is my view:
#extends('layouts.frontend')
#section('content')
<!-- Stunning Header -->
<div class="stunning-header stunning-header-bg-lightviolet">
<div class="stunning-header-content">
<h1 class="stunning-header-title">Category:{{$category->name}}</h1>
</div>
</div>
<!-- End Stunning Header -->
<div class="container">
<div class="row medium-padding120">
<main class="main">
<div class="row">
#php
$i = 0;
#endphp
#foreach($category->posts as $post)
<div class="case-item-wrap">
<div class="col-lg-4 col-md-4 col-sm-6 col-xs-12">
<div class="case-item" style="margin-top: 20px;">
<div class="case-item__thumb">
<img src="{{$post->featured}}" alt="our case">
</div>
<h6 class="case-item__title">{{$post->title}}</h6>
</div>
</div>
</div>
#php $i++; #endphp
#if($i % 3 == 0)
<div class="row"></div>
#endif
#endforeach
</div>
</div>
</main>
</div>
</div>
#endsection
And this is my frontendcontroller. Where I want to select Post with specific category Then display 5 number post in my view. Having problem in how to use pagination with realtionship.
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Setting;
use App\Category;
use App\Post;
use App\User;
use App\Tag;
class FrontEndController extends Controller
{
public function index()
{
$title = Setting::first()->site_name;
$categories = Category::all();
$first_post = Post::latest()->first();
$second_post = Post::latest()->skip(1)->take(1)->get()->first();
$third_post = Post::latest()->skip(2)->take(1)->get()->first();
$english_11 = Category::find(1);
$blog = Category::find(3);
$settings = Setting::first();
$tags = Tag::all();
return view('index',compact('title','categories','first_post','second_post','third_post','english_11','blog','settings','tags'));
}
public function singlePost($slug)
{
$categories = Category::all();
$settings = Setting::first();
$post = Post::where('slug',$slug)->first();
$next_id = Post::where('id','>',$post->id)->min('id');
$prev_id = Post::where('id','<',$post->id)->max('id');
$next = Post::find($next_id);
$prev = Post::find($prev_id);
$tags = Tag::all();
$title = $post->title;
return view('single',compact('post','title','categories','settings','next','prev','tags'));
}
public function categories($slug)
{
$category = Category::where('slug',$slug)->first();
$categories = Category::all();
$title = $category->name;
$settings = Setting::first();
return view('category',compact('category','categories','title','settings'));
}
public function tags($slug)
{
$tag = Tag::where('slug',$slug)->first();
$categories = Category::all();
$title = $tag->tag;
$settings = Setting::first();
return view('tag',compact('tag','categories','title','settings'));
}
}

Invalid argument supplied for foreach() in laravel 5.3

I do not know exactly how this works, so that's why I'm asking. I'm still working on a Bulletin Board System and now I want under each category, a subcategory.
For example:
I have done this using the following thread on LaraCasts:
https://laracasts.com/discuss/channels/eloquent/eloquent-getting-subcategories-from-the-categories
Now my IndexController looks like this:
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Thread;
use App\Chat;
use App\Category;
class IndexController extends Controller
{
/**
* Show the application dashboard.
*
* #return \Illuminate\Http\Response
*/
public function index()
{
$threads = Thread::all()->toArray();
$chats = Chat::orderBy('id', 'DESC')->take(50)->with('author')->get();
$categories = Category::with('sub_category')->get();
return view('index', compact('threads','chats','categories'));
}
}
This is my Category Model:
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Category extends Model
{
public function sub_category()
{
return $this->belongsTo(self::class, 'parent_id', 'id');
}
public function parent_category()
{
return $this->hasMany(self::class, 'id', 'parent_id');
}
}
My view (index.blade.php):
#foreach($categories as $category)
<div class="col-md-8">
<div class="panel panel-primary">
<div class="panel-heading"><i class="fa fa-angle-right" aria-hidden="true"></i> {{ $category->caption }}</div>
<div class="panel-body">
#foreach($category->sub_category as $sub_category)
<div class="row forum-row">
<div class="col-xs-12 col-md-8 col-sm-8">
<div class="hidden-xs visible-sm visible-lg visible-md pull-left forum-icon-read">
<i class="fa fa-comment"></i>
</div>
{{ $sub_category->caption }}<br>
<small>{{ $sub_category->desc }}</small>
</div>
<div class="col-xs-12 col-md-4 col-sm-4 forum-latest-container">
<p class="forum-data cutoff">Test</p>
<small>
door <a class="Donateur" href="/user-Sygun">Sygun</a>
<p class="forum-data">
2 minuten geleden </p>
</small>
</div>
</div>
#endforeach
</div>
</div>
</div>
#endforeach
I also have two database tables:
Sub_categories (id, caption, parent_id, min_rank, desc)
Categories (id, caption, min_rank, desc)
The error message I get:
Invalid argument supplied for foreach()
Can you tell me what is the right way to achieve this?
Create two model named Category and SubCategory.
In Category model
public function subcategories()
{
return $this->hasMany('App\SubCategory', 'parent_id');
}
In SubCategory model
public function parent_category()
{
return $this->belongsTo('App\Category', 'parent_id');
}
Then in your controller query it like:
$categories = Category::with('subcategories')->get();
And hopefully your foreach will work.
Category model
public function subcategories(){
return $this->hasMany('SubCategory', 'parent_id');
}
On view
#foreach($categories as $category)
#foreach($category->subcategories as $subcategory)
{{$subcategory->caption}}
#endforeach
#endforeach
And make sure you create SubCategory model.

Categories