How can I display other data in foreach? - php

In my show function in which you can watch every single group, I load all articles with the same tags. And the article with the most votes will be displayed separately at the top. In addition, I indicate the average rating of the items in this group. This is how my function looks like:
public function show($id)
{
$group = group::find($id);
$tagIdArray = $group->tags->pluck('id')->all();
$mostvotedarticle = Article::where('type', 4)->whereIn('privacy', [1, 3])
->whereHas('tags', function($query) use ($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))
->orderByVotes()->first();
$articledown = Article::where('status', 1)->whereHas('tags', function($query) use ($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))->downVotesAll()->count();
$articleup = Article::where('status', 1)->whereHas('tags', function($query) use ($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))->upVotesAll()->count();
$ratio = null;
if($articleup + $articledown == 0) {
$ratio = 0;
} else {
$ratio = ($articleup*100)/($articleup + $articledown);
}
return view('singlegroup',compact('groups','mostvotedarticle', 'ratio'));
}
On a overview page, the individual groups are displayed with a foreach loop:
function:
public function index()
{
$user = Auth::user();
$groups = $user->groups()->latest()->with('tags')->paginate(20);
return view('groups', compact('groups'));
}
view:
#foreach ($groups as $group)
{{$group->name}}
<img src="-----load mostvotedarticle that is in this group------" alt="" />
<div class="progress-bar-primary" style="width:{{$ratio}}%;">
#endforeach
How can I have the mostvotedarticle and group ratings displayed in the foreach loop?
Article Model
public function scopeOrderByVotes($query)
{
$query->leftJoin('Article_activities', 'Article_activities.article_id', '=', 'articles.id')
->selectRaw('articles.*, count(Article_activities.id) as aggregate')
->groupBy('articles.id')
->orderBy('aggregate', 'desc');
}
public function scopeDownVotesAll($query)
{
$query->leftJoin('Article_activities', 'Article_activities.article_id', '=', 'articles.id')
->selectRaw('articles.*, count(Article_activities.id) as aggregate')
->where('Article_activities.activity', '=', '0');
}
public function scopeUpVotesAll($query)
{
$query->leftJoin('Article_activities', 'Article_activities.article_id', '=', 'articles.id')
->selectRaw('articles.*, count(Article_activities.id) as aggregate')
->where('Article_activities.activity', '=', '1');
}

you need put all inside your foreach groups
public function index()
{
$user = Auth::user();
$groups = $user->groups()->latest()->with('tags')->paginate(20);
$ratio = null;
foreach($groups as $key => $group)
{
$tagIdArray = $group->tags->pluck('id')->all();
$mostvotedarticle = Article::where('type', 4)->whereIn('privacy', [1, 3])
->whereHas('tags', function($query) use ($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))
->orderByVotes()->first();
$articledown = Article::where('status', 1)->whereHas('tags', function($query) use
($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))->downVotesAll()->count();
$articleup = Article::where('status', 1)->whereHas('tags', function($query) use
($tagIdArray) {
$query->whereIn('tags.id', $tagIdArray);
}, '>=', count($tagIdArray))->upVotesAll()->count();
if($articleup + $articledown == 0) {
$ratio = 0;
} else {
$ratio = ($articleup*100)/($articleup + $articledown);
}
$group->mostVote = $mostvotedarticle;
$group->ratio = $ratio;
}
return view('groups', compact('groups'));
}

Related

Filter data via ajax request in Laravel

This is my function in controller
public function ajaxResponse (Request $request) {
if ($request->ajax()) {
$mat_id = $request->input('mat');
$cat_id = $request->input('cat');
$met_id = $request->input('met');
if ($cat_id != null) {
$products = Product::whereHas("categories", function ($query) use ($cat_id) {
$query->whereIn('category_id', explode(',', $cat_id));
})->get();
}
if ($mat_id != null) {
$products = Product::whereHas("productMaterial", function ($query) use ($mat_id) {
$query->whereIn('product_material_id', explode(',', $mat_id));
})->get();
}
if ($met_id != null) {
$products = Product::whereHas("productionMethod", function ($query) use ($met_id) {
$query->whereIn('production_method_id', explode(',', $met_id));
})->get();
}
if ($cat_id == null && $mat_id == null && $met_id == null) {
$products = Product::all();
}
$prod = view('partials.ajaxProducts', ['products' => $products])->render();
}
return response()->json(['prod' => $prod]);
}
all the record filtered according to $cat_id, $mat_id,$met_id
here categories and productMaterial have Many to many relations with product and productionMethod have one to many relations with the product
i want to filter data via ajax request in combination with all these three relationships
You can use:
public function ajaxResponse(Request $request) {
if ($request->ajax()) {
$mat_id = $request->input('mat');
$cat_id = $request->input('cat');
$met_id = $request->input('met');
$products = Products::query();
if ($cat_id != null) {
$products = $products->whereHas("categories", function ($query) use ($cat_id) {
$query->whereIn('category_id', explode(',', $cat_id));
});
}
if ($mat_id != null) {
$products = $products->whereHas("productMaterial", function ($query) use ($mat_id) {
$query->whereIn('product_material_id', explode(',', $mat_id));
});
}
if ($met_id != null) {
$products = $products->whereHas("productionMethod", function ($query) use ($met_id) {
$query->whereIn('production_method_id', explode(',', $met_id));
});
}
$products = $products->get();
$prod = view('partials.ajaxProducts', ['products' => $products])->render();
}
return response()->json(['prod' => $prod]);
}
public function ajaxResponse(Request $request){
if ($request->ajax()) {
$mat_id = $request->input('mat');
$cat_id = $request->input('cat');
$met_id = $request->input('met');
$products = Product::query();
if ($cat_id != null) {
$products->whereHas("categories", function ($query) use ($cat_id) {
$query->whereIn('category_id', explode(',', $cat_id));
})->get();
}
if ($mat_id != null) {
$products->whereHas("productMaterial", function ($query) use ($mat_id) {
$query->whereIn('product_material_id', explode(',', $mat_id));
})->get();
}
if ($met_id != null) {
$products->whereHas("productionMethod", function ($query) use ($met_id) {
$query->whereIn('production_method_id', explode(',', $met_id));
})->get();
}
$products = $products->get();
$prod = view('partials.ajaxProducts', ['products' => $products])->render();
}
return response()->json(['prod' => $prod]);
}

Print the name of function has highest value

My 3 different function given me value as below: in JSON.
I want to PRINT name of function which has highest value. The Functions are;
public function firstHourTrades()
{
$user_id = Auth::user()->id;
$data = DB::table('finaltrade')
->select(DB::raw('count(*) as first_hour'))
->join('exchanges', 'finaltrade.exchange_id', '=', 'exchanges.id')
->where('finaltrade.user_id', $user_id)
->whereTime(DB::raw('IF(finaltrade.buy_datetime<finaltrade.sell_datetime, finaltrade.buy_datetime, finaltrade.sell_datetime) '), '>=', DB::raw('exchanges.start_time'))
->whereTime(DB::raw('IF(finaltrade.buy_datetime<finaltrade.sell_datetime, finaltrade.buy_datetime, finaltrade.sell_datetime) '), '<=', DB::raw("ADDTIME(exchanges.start_time, '1:00:00')"))
->get();
return response()->json($data);
}
public function lastHourTrades()
{
$user_id = Auth::user()->id;
$data = DB::table('finaltrade')
->select(DB::raw('count(*) as last_hour'))
->join('exchanges', 'finaltrade.exchange_id', '=', 'exchanges.id')
->where('finaltrade.user_id', $user_id)
->whereTime(DB::raw('IF(finaltrade.buy_datetime<finaltrade.sell_datetime, finaltrade.buy_datetime, finaltrade.sell_datetime) '), '<=', DB::raw('exchanges.close_time'))
->whereTime(DB::raw('IF(finaltrade.buy_datetime<finaltrade.sell_datetime, finaltrade.buy_datetime, finaltrade.sell_datetime) '), '>=', DB::raw("SUBTIME(exchanges.close_time, '01:00:00')"))
->get();
return response()->json($data);
}
public function otherHoursTrades()
{
$user_id = Auth::user()->id;
$data = DB::table('finaltrade')
->select(DB::raw('count(*) as other_hours'))
->join('exchanges', 'finaltrade.exchange_id', '=', 'exchanges.id')
->where('finaltrade.user_id', $user_id)
->whereRaw('finaltrade.created_at NOT BETWEEN exchanges.start_time AND DATE_ADD(exchanges.start_time, INTERVAL 1 HOUR)')
->whereRaw('finaltrade.created_at NOT BETWEEN exchanges.close_time AND DATE_SUB(exchanges.close_time, INTERVAL 1 HOUR)')
->get();
return response()->json($data);
}
FROM THE ANSWER I HAVE CREATED:
public function allCmp()
{
$func_names = ['firstHourTrades()','lastHourTrades()','otherHoursTrades()'];
foreach($func_names as $name)
$results[$name] = $name();
$max = max($results);
DD($max);
}
<?php
function one()
{
return 1;
}
function two()
{
return 2;
}
function three()
{
return 3;
}
$func_names = ['three','one','two'];
// Call each function and store result.
foreach($func_names as $name)
$results[$name] = $name();
$max = max($results);
$max_funcs = array_keys($results, $max);
var_dump($max_funcs);
Output:
array(1) {
[0]=>
string(5) "three"
}
You may need to decode your JSON at some point, something like:
function get_val_from_my_json($json) {
return array_values(json_decode($json, true))[0];
}
print get_val_from_my_json('{"some_key":5}');
Output:
5
And run all the results through that function (assuming valid json).
$results = array_map('get_val_from_my_json', $results);

Loop over Laravel Collection

public function showJobCategoryContent($id){
$jobsInfoById = DB::table('jobs')->where('category_id', '=', $id)->where('published', '=', 1)->paginate(3);
// Imagine here i got 5 data
foreach ($jobsInfoById as $jobInfoById) {
return $current=$jobInfoById->created_at;
//$trialExpires []= $current->addDays(30);
}
}
If i loop it it only show 1 data. How is it possible If use array sign then it will show 1 data.
If you want to get an array of all created_at dates, you don't need a loop.
public function showJobCategoryContent($id)
{
$jobsInfoById = DB::table('jobs')->where('category_id', '=', $id)->where('published', '=', 1)->paginate(3);
return $jobsInfoById->pluck('created_at');
}
Using the loop:
public function showJobCategoryContent($id)
{
$jobsInfoById = DB::table('jobs')->where('category_id', '=', $id)->where('published', '=', 1)->paginate(3);
$dates = [];
foreach ($jobsInfoById as $jobInfoById) {
$dates[] = $current = $jobInfoById->created_at;
}
return $dates;
}
If want to add 30 days to each date:
public function showJobCategoryContent($id)
{
$jobsInfoById = DB::table('jobs')->where('category_id', '=', $id)->where('published', '=', 1)->paginate(3);
$jobsInfoById = $jobsInfoById->map(function ($job) {
return $job->created_at->addDays(30);
});
return $jobsInfoById->pluck('created_at');
}
Have a look at Laravel collections and how they can be useful: link

laravel filter if else statement is not working

i trying to filter my product for price gender colors
here is my working code when i use like that url localhost/category/tag?price=100
if (request()->has('gender')) {
$products = Product::withAllTags($tags)->where('gender', request('gender'))->get();
}
if (request()->has('price')) {
$products = Product::withAllTags($tags)->where('price', '<=', request('price'))->get();
}
if (request()->has('color')) {
$products = Product::withAllTags($tags)->whereHas('colors', function ($query) {
$query->where('name', request('color'));
})->paginate(20);
}
if (request()->has('brand')) {
$products = Product::withAllTags($tags)->whereHas('brands', function ($query) {
$query->where('name', request('brand'));
})->orderBy('created_at', 'desc')->paginate(20);
}
but getting error when url is localhost/category/tag
Undefined variable: products
i try to add else condition like that
if (request()->has('gender')) {
$products = Product::withAllTags($tags)->where('gender', request('gender'))->get();
}
if (request()->has('price')) {
$products = Product::withAllTags($tags)->where('price', '<=', request('price'))->get();
}
if (request()->has('color')) {
$products = Product::withAllTags($tags)->whereHas('colors', function ($query) {
$query->where('name', request('color'));
})->paginate(20);
}
if (request()->has('brand')) {
$products = Product::withAllTags($tags)->whereHas('brands', function ($query) {
$query->where('name', request('brand'));
})->orderBy('created_at', 'desc')->paginate(20);
}
else {
$products = Product::withAllTags($tags)->orderBy('created_at', 'desc')->paginate(20);
}
its working on localhost/category/tag
but now filter not working on localhost/category/tag?price=100
all data is showing sorry for my grammar
You are basically doing
if (request()->has('brand')) {
$products = Product::withAllTags($tags)->whereHas('brands', function ($query) {
$query->where('name', request('brand'));
})->orderBy('created_at', 'desc')->paginate(20);
}
else {
$products = Product::withAllTags($tags)->orderBy('created_at', 'desc')->paginate(20);
}
which makes the else statement work for request()->has('brand')
wrap all your conditions in an if statement and the rest in an else statement
if(request()->has('gender')||request()->has('price')||request()->has('color')||request()->has('brand')){
if (request()->has('gender')) {
$products = Product::withAllTags($tags)->where('gender', request('gender'))->get();
}
if (request()->has('price')) {
$products = Product::withAllTags($tags)->where('price', '<=', request('price'))->get();
}
if (request()->has('color')) {
$products = Product::withAllTags($tags)->whereHas('colors', function ($query) {
$query->where('name', request('color'));
})->paginate(20);
}
if (request()->has('brand')) {
$products = Product::withAllTags($tags)->whereHas('brands', function ($query) {
$query->where('name', request('brand'));
})->orderBy('created_at', 'desc')->paginate(20);
}
}
else {
$products = Product::withAllTags($tags)->orderBy('created_at', 'desc')->paginate(20);
}

Laravel multiple withCount on the same relationship

I need to count the results from two different conditions, from the same relationship, but it's being returned as the same name.
Model::where('types_id', $specialism_id)
->withCount(['requests' => function ($query) {
$query->where('type', 1);
}])
->withCount(['requests' => function ($query) {
$query->where('type', 2);
}])
I can access the withCount using $model->requests_count, but because it's querying the same relationship, it appears to overwrite it:
select count(*)
from `requests` where `requests`.`id` = `model`.`id`
and `type` = '1') as `requests_count`,
(select count(*) from `requests` where `requests`.`id` = `model`.`id`
and `type` = '2') as `requests_count`
How can I specify the name for multiple withCount?
You can now do it like this
Model::where('types_id', $specialism_id)
->withCount(['requests as requests_1' => function ($query) {
$query->where('type', 1);
}, 'requests as requests_2' => function ($query) {
$query->where('type', 2);
}])
Option 1
Create two different relationships:
public function relationship1()
{
return $this->hasMany('App\Model')->where('type', 1);
}
public function relationship2()
{
return $this->hasMany('App\Model')->where('type', 2);
}
And use them:
Model::where('types_id', $specialism_id)->withCount(['relationship1', 'relationship2'])
Option 2
Create withCount() like method which will build property with custom names:
public function withCountCustom($relations, $customName)
{
if (is_null($this->query->columns)) {
$this->query->select([$this->query->from.'.*']);
}
$relations = is_array($relations) ? $relations : func_get_args();
foreach ($this->parseWithRelations($relations) as $name => $constraints) {
$segments = explode(' ', $name);
unset($alias);
if (count($segments) == 3 && Str::lower($segments[1]) == 'as') {
list($name, $alias) = [$segments[0], $segments[2]];
}
$relation = $this->getHasRelationQuery($name);
$query = $relation->getRelationCountQuery(
$relation->getRelated()->newQuery(), $this
);
$query->callScope($constraints);
$query->mergeModelDefinedRelationConstraints($relation->getQuery());
$column = $customName; <---- Here you're overriding the property name.
$this->selectSub($query->toBase(), $column);
}
return $this;
}
And use it:
Model::where('types_id', $specialism_id)
->withCountCustom(['requests' => function ($query) {
$query->where('type', 1);
}], 'typeOne')
->withCountCustom(['requests' => function ($query) {
$query->where('type', 2);
}], 'typeTwo')

Categories