Laravel weekly group by eloquent collection error - laravel

I have orders table, and for each user weekly payments table.
I want to show user that he wil take total payment count on depending week.
I have created the query but on blade side, when i try to access other tables via eloquent it gives does not exits in this collection.
If i dont use group by function it works. But with group by function it doent
$earnings = user()->orders()->where('payment_status',0)-
>where('status',1)->get()->groupBy(function($date) {
return Carbon::parse($date->created_at)->format('W');
});
In blade side my codes like following;
#foreach($earnings as $earning)
<tr>
<td>{{$earning->user->name}}</td>
<td>{{$earning->order->commission}}</td>
<td>{{$earning->user->bank}}</td>
<td>{{$earning->user->iban}}</td>
<td>{{$earning->user->phone}}</td>
#endforeach

get() should be last:
$earnings = user()->orders()
->where('payment_status',0)
->where('status',1)
->groupBy('created_at')
->get();
How about using DATE_FORMAT function:
$earnings = user()->orders()
->where('payment_status',0)
->where('status',1)
->groupBy(DB::raw("DATE_FORMAT(created_at, '%W')"))
->get();

Assuming your table is orders, you can do like this:
$earnings = user()->orders()->select('orders.*', DB::raw("DATE_FORMAT(created_at, '%W') as week"))
->where('payment_status',0)
->where('status',1)
->get()->groupBy('week');

Laravel Collection groupBy() function returns a collection of grouped collections.
$earningGroups = user()->orders()
->where('payment_status',0)
->where('status',1)
->get()
->groupBy(function($earning) {
return Carbon::parse($earning->created_at)->format('W');
});
Now this is a collection of earning groups, not earnings.
#foreach($earningGroups as $earcningGroupName => $earcningGroup)
// So here you have a group or earnings
// I don't know why did you want to group.
// For an example I will print the group name as a table row here.
// But do whatever you want.
<tr>
<td>{{ $earningGroupName }}</td>
</tr>
// So if you want to loop through earnings, you have to loop again.
#foreach($earningGroup as $earning)
<tr>
<td>{{$earning->user->name}}</td>
<td>{{$earning->order->commission}}</td>
<td>{{$earning->user->bank}}</td>
<td>{{$earning->user->iban}}</td>
<td>{{$earning->user->phone}}</td>
</tr>
#endforeach
#endforeach

Related

Laravel Eloquent get data where comparison is true

I am creating a mini inventory stock for a fashion store. I am using Laravel/Voyager with BREAD and everything fine. I have 2 tables Sizes and Products with a column in common product_code.
I would like to get the results from Sizes where column product_code = Product 'product_code'.
I have this query in the controller:
$product_code = Product::all();
$allSizes = Size::where('product_code', ($product_code->product_code));
and in browse.blade.php I have:
#foreach ($allSizes as $size)
<tr>
<td align="right">{{$size->size_name}}</td>
<td align="right">{{$size->stock}}</td>
</tr>
#endforeach
I guess the where statement is not working as supposed to.
I want to get the corresponding stock based on product_code for each size from table Sizes
Try This
$product_code = Product::pluck('product_code')->toArray();
$allSizes = Size::whereIn('product_code', $product_code)->get();
and in browse.blade.php:
#foreach ($allSizes as $size)
<tr>
<td align="right">{{$size->size_name}}</td>
<td align="right">{{$size->stock}}</td>
</tr>
#endforeach
I think you're going about this the wrong way. Your tables are related in some way and you need to define a relationship to access the data Eloquently.
If I were building such a database, I think that the relationship between Product and Size is a many to many. I.e. a Product can have many Sizes, and you can also shop for many Products in a certain Size. Thus, your models should have a belongsToMany() relationship to each other.
// Product.php
protected $with = ['sizes']; // eager load product sizes
public function sizes() {
return $this->belongsToMany(Size::class);
}
// Size.php
public function products() {
return $this->belongsToMany(Product::class);
}
Then you can do
// ProductsController.php
public function show(Product $product) {
return $product;
}
You missed to run the query
$product_code = Product::all();
# ::all() will return collection, and you can't access a property of it directly
$allSizes = Size::where('product_code', ($product_code->first()->product_code))->get();
Notice the ->get();

Only return one row in foreach

I'm starting with Laravel and I'm having trouble getting the results of a query on the laravel blade.
From a list obtained through a query to MySQL 'mysql', I want to check the name it has in another table of another 'tienda' database.
Everything is fine, but it only returns the last value of the second query, it does not return all the values ​​of the $ products query with its corresponding name obtained in $ products_name.
Controller
$productos = [
'id' => $id
];
$products = DB::connection('mysql')
->SELECT("SELECT * FROM promociones_product WHERE id_promo = $id", $productos);
foreach ($products as $product)
{
$products_name = collect(DB::connection('tienda')
->table('ps_product_lang')
->where('id_product', $product->id_product)
->get(['name', 'id_product']));
}
return view('promociones-products')->with('promo', $products_name);
Blade
#foreach($promo as $product)
<tr>
<td>{{ $product->id_product }}</td>
<td>{{ $product->name }}</td>
</tr>
#endforeach
I need to make a query against the 'mysql' database and, with those results, consult its name in another database, and all the values ​​are printed on the screen.
So there are a couple of issues with the code you provided.
To start with, in your loop you are creating a new collection called 'products_name' on each loop which keeps overwriting itself.
There are lots of ways of approaching this however how I would do it is below:
$promo = []; // Initialise a new array called promo
foreach ($products as $product)
{
// Append the collection to the new array
$promo[] = collect(DB::connection('tienda')
->table('ps_product_lang')
->where('id_product', $product->id_product)
->get(['name', 'id_product']));
}
Now you have an array with all of the products in collections.
Now the loop to get that data should work.
You can then return the data to the view using a couple of methods, my preferred method is indeed compact() seen below:
return view('promociones-products', compact('promo'));
What compact() will do is grab any variable names mentioned in the view and pass it through to the view. This compact will pass the $promo variable to the view.

Laravel - Populating view with info from single row (with pivot data)

I currently have a form/view that allows a User to save an Order. This also updates a pivot table with the respective Products and qtys. What I am trying to do, is after this information is inputted and saved into the database, I want to send the user to a checkout page that shows all the information they inputted for that Order.
Relationships
User hasMany Order
Order belongsToMany Product
Product belongsToMany Order
checkout.blade.php
#foreach ($orders as $order)
#foreach ($order->products as $product)
<tr>
<td>{{ $product->name }}</td>
<td>{{ $product->pivot->qty }}</td>
</tr>
#endforeach
#endforeach
OrderController.php
public function checkout($id)
{
$user = Auth::user();
$user->load("orders.products"); //eager load pivot table
$orders = $user->orders->where('order_id', $id);
return view('orders.checkout', compact('orders', 'user'));
}
I know I am calling the order incorrectly, because if I change
$orders = $user->orders->where('order_id', $id);
to
$orders = $user->orders;
It displays correctly, except of course, it populates with every Order's detail.
Or is there some elegant way for me to pass the data from the checkout function without this additional query? (I understand about moving data in Sessions, but I am working with a pivot table, and that complicates things.
If on the checkout page, you want to use just the latest order that the user has made, then you can just load that order using route model binding
Route::get('checkout/{order}', 'OrdersController#checkout');
Then in your controller:
public function checkout(Order $order)
so from here, you can pass this order to the view, and list all the products from this order, and also in your Order model you should have a reference to the user that this order belongs to:
public function user()
{
return $this->belongsTo(User::class);
}
Accessing columns from the pivot table will be:
#foreach($order->products as $product)
<div> {{ $product->pivot->column }} </div>
#endforeach

Make a sum() of column accessors Laravel

im improving my skills in laravel making a simple challenges web but i stuck on the next problem.
I have the users table with the id, name, mail, etc. The challenges table where i list all the challenges (with columns id, name, body, answer, score) and a third table called "Answers" where i post each try of the users solving a challenge with the columns id, user_id, challenge_id, success (boolean) and score.
Now i'am trying to make a ranking of users with their scores. The problem is to show a sum() of the column 'score' in the table answers where user_id.answers = users.id. So i can get easy the total score for each user.
For now i solved the problem doing this in blade:
#foreach($users as $user)
<tr>
<th>{{ $user->id }}</th>
<td>{{ $user->name }}</td>
<td>Team pindonga</td>
<td>{{ score = DB::table('answers')->where('user_id', $user->id)->sum('score') }} </td> </tr>
#endforeach
works perfectly, but i want to get them by desc score (for now i solved the desc with js but want to get desc order from the eloquent query) and have something like this in the blade:
#foreach($users as $user)
<tr>
<th>{{ $user->id }}</th>
<td>{{ $user->name }}</td>
<td>Team pindonga</td>
<td>{{ $team->score }} </td> </tr>
#endforeach
I was thinking about solve it with accessors doing something like this:
public function getScoreAttribute($value)
{
return $this->groupBy('user_id')->where('user_id', '=', $value)->sum('score');
}
also i have a relationship belongsTo in the answers modle to users and a hasMany in the users to answers. But i'm not sure of how pass the results to blade. Tried in tinker:
>>> \App\Answer::find(1)->score;
=> "3400"
>>> \App\Answer::find(2)->score;
=> "3400"
>>> \App\Answer::find(5)->score;
=> "3400"
allways getting the sum of the id = 1. And with $user->score; in the blade foreach i got a '0'.
Using the relationship with Blade would be {{ $user->answers->sum('score') }}. No accessor needed.
For sorting I would use the sortByDesc collection method.
$users = User::get();
$users = $users->sortByDesc(function ($user) {
return $user->answers->sum('score');
});
I think this is what you're looking for. It takes a while to get used to Eloquent ORM :-)
foreach($users as $user){
print $user->answers->sum('score');
}
https://laravel.com/docs/5.6/queries#aggregates

Laravel join query confusion

Very new to laravel and trying to do something simple but keep getting stuck. I have 3 tables
countries:
id
country
regions:
id
region
country_id
wineries:
id
winery
country_id
region_id
joined together as follows:
public function index()
{
$wineries = Country::join('wineries', 'countries.id', '=', 'wineries.country_id')
->join('regions', 'regions.id', '=', 'wineries.region_id')
->select('countries.*')
->orderBy('countries.country', 'asc')
->get()
->unique();
return view('winery.index', compact('wineries'));
}
I'm trying to return a table organized by country with each winery listed along with it's region. Countries without wineries are not to be displayed. My Index page, looks like this:
<tbody>
#foreach ($wineries as $country)
<tr>
<td colspan="2">{{ $country->country }}</td>
</tr>
#foreach ($country->wineries as $winery)
<tr>
<td>{{ $winery->winery }}</td>
<td>{{ $winery->region }}</td>
</tr>
#endforeach
#endforeach
</tbody>
All works well except I can't get the associated region for each winery since the region is not a part of the $winery array. Any advice on how to make it a part of array or how to accomplish this using a different query?
In laravel you can define relationships for Models. Models represent a Model of data (normally related to a DB table, but not always)
Laravel uses Eloquent for database defining relational tables within PHP.
http://laravel.com/docs/4.2/eloquent#relationships
For your case it sounds like you have three Models
Countries
Region
Wineries
Your counties will have many regions, but a region will only have one country.
Your regions will have many wineries, but a winery will only have one region.
To spec your relationships within Eloquent you want to write the following functions within each
(Country)
public function regions()
{
return $this->hasMany('Region');
}
(Region)
public function country()
{
return $this->hasOne('Country');
}
public function winery()
{
return $this->hasMany('Region');
}
etc..
From there you can then relate the data via the models. So if you have a Country object and wanted to get the regions you would do
$country->regions
You might want to wrap this in a loop to print all of the regions
foreach($country->regions as $region) {
echo $region->name;
}
Hope this helps
Define relationships using model. Laravel has Eloquent model in built. It's very easy to query database using that. Learning curve is well worth it.

Resources