Implemented a sidebar based on user with most posts and comments - laravel

i want to implement a sidebar based on user with most posts and comments in laravel 5.2 app,
i want to show the top 5 users with most posts and comment.
Exemple Like this:
User Name: "Mohcin", Post:30, answer:20
Thanks in advance

User model:
use Authenticatable, CanResetPassword;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = ['name', 'email', 'password'];
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = ['password', 'remember_token'];
public function questions(){
return $this->hasMany('\App\Question');
}
public function answers(){
return $this->hasMany('\App\Answer');
}
Question model: (posts model)
public function User(){
return $this->belongsTo('\App\User');
}
public function answers(){
return $this->hasMany('\App\Answer');
}
public static function your_questions(){
return static::where ('user_id','=',Auth::user()->id)->paginate(50);
}
public static function unsolved(){
return static::where ('solved','=',0)->orderby('id','DESC')->latest()->paginate(50);
}
public static function unsolvedbar(){
return static::where ('solved','=',0)->orderby('id','DESC')->latest()->take(3)->get();;
}
public function category()
{
return $this->belongsTo('App\Category');
}
public function tags()
{
return $this->belongsToMany('App\Tag');
}

Steps:
Open app/Providers/AppServiceProvider.php
In this file you have an empty (probably) boot method.
Inside this method, you can create a view composer to pass data for a specific view.
Like this:
//Assuming you want to pass the var to the view: sidebar.blade.php inside resources/views/layout
view()->composer('layout.sidebar', function($view){
$topUsers = User::topUsers(); //Create a query or scope to do this...
//After populate topUsers, you have to pass it to the view using:
$view->with('topUsers', $topUsers);
});
In your view: `resources/views/layout/sidebar.blade.php, you can access the users with a simple $topUsers like this:
foreach($topUsers as $user) {
var_dump($user);
}

Related

Laravel 6 - Accessor appends not called in relationships

I use Laravel 6 and I want access to avatar attribute from user when I use posts() relation.
User model:
/**
* #var array
*/
protected $appends = [
'avatar',
];
/**
* #return HasMany
*/
public function posts(): HasMany
{
return $this->hasMany(Post::class);
}
/**
* #return string
*/
public function getAvatarAttribute(): string
{
return sprintf('https://secure.gravatar.com/avatar/%s?s=500', md5($this->email));
}
The code of my controller:
$topic = Topic::where('slug', $slug)->firstOrFail();
foreach ($topic->posts()->get() as $post) {
dd($post->user->avatar); // return null
}
Post model:
/**
* #return BelongsTo
*/
public function user(): BelongsTo
{
return $this->belongsTo(User::class);
}
I get the name of user with $post->user->name but avatar attribute is not called.

Laravel Relationship Find UUID

I have make a Trait for UUID. I use a lot of relationschip inside my code. On a relationship you can do find() and findOrFail() but i have write a code for findU() and findUOrFail() but i can't use it inside a relationship. How can i fix it?
Trait:
<?php
namespace App\Modules\Base\Traits;
use Ramsey\Uuid\Uuid;
/**
* Trait Uuids
*
* #package Modules\Core\Traits
*/
trait Uuids
{
/**
* Boot function from laravel.
*/
public static function bootUuids ()
{
static::creating(function ($model) {
$model->uuid = Uuid::uuid4()->toString();
});
}
/**
* #param $uuid
*
* #return mixed
*/
public static function findU ($uuid)
{
return static::where('uuid', '=', $uuid)->first();
}
/**
* #param $uuid
*
* #return mixed
*/
public static function findUOrFail($uuid)
{
$post = static::where('uuid', '=', $uuid)->first();
if( is_null($post) ) {
return abort(404);
} else {
return $post;
}
}
}
Controller:
/**
* Show
*/
public function show(Request $request, $uuid)
{
return responder()->success($request->user()->projects()->findUOrFail($uuid))->respond();
}
Error:
Call to undefined method Illuminate\\Database\\Eloquent\\Relations\\BelongsToMany::findUOrFail()
Assuming you don't need id since you're using uuid
In your migration file you need:
$table->uuid('uuid');
$table->primary('uuid');
In your model:
use Uuids;
protected $primaryKey = 'uuid';
public $incrementing = false;
Or much easier
In your migration file:
$table->uuid('id');
$table->primary('id');
In your model:
use Uuids;
public $incrementing = false;
You don't need to override findOrFail or find
It should help to have the function referenced directly in the model rather than trying to access it directly in a trait. I am assuming that you are including the Uuids trait above in your projects model. If so, try creating a method on the projects model like this:
public function tryFindUOrFail($uuid)
{
return $this->findUOrFail($uuid);
}
Then you would write your show method as:
return responder()->success($request->user()->projects()->tryFindUOrFail($uuid))->respond();
If this doesn't work, you may need to include your method with the $appends array so that it is directly accessible through the relationship.

Laravel getting information from other table

I have the following tables user table, post table and profile table. the post belongs to a user and the profile belongs to a user. I also have a forum were people can post I want the users username to show instead of their name. But The username is in the profiles table and I don't know how to get it.
here is my code
class Post extends Model
{
//
public function users(){
return $this->belongsToMany('App\User','posted_by');
}
class Profile extends Model
{
//
public function users(){
return $this->belongsTo('App\User','whos_profile');
}
class User extends Authenticatable
{
use Notifiable;
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'firstname','lastname', 'email', 'password',
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'password', 'remember_token',
];
public function profile(){
return $this->hasOne('App\Profile');
}
public function post(){
return $this->hasMany('App\Post');
}
}`enter code here`
You can get it as follows
$user = User::find($id);
if($user->profile){
echo $user->profile->username;
}
You should try this:
$rsltUsers = User::with(['profile','post'])->where('id',$id)->get();
foreach($rsltUsers as $rsltUsers){
dd($user->profile->username);
}

Laravel Relationship Issues : Laravel 5.4

I have 2 tables in my application... Users Conventioners
I have users id in the conventioners table and i want to access their genders from the Users table....
I have like 10 user ids in the conventioners table and 20 users in the users table...
Please how do I access all their genders in the users table...
$conventioners->users()->gender
Conventioners is an instance of the Conventioner Model which contains a relationship **belongsToMany
Thanks alot guys
Here is my Conventioner Model
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Conventioner extends Model
{
/**
* #var string
*/
protected $table = 'conventioners';
/**
* #var array
*/
protected $fillable = [
'user_id','year','church_id','convention_id'
];
/**
* #return \Illuminate\Database\Eloquent\Relations\BelongsTo
*/
public function user()
{
return $this->belongsTo('App\User');
}
/**
* #return \Illuminate\Database\Eloquent\Relations\HasMany
*/
public function users()
{
return $this->hasMany('App\User');
}
/**
* #return \Illuminate\Database\Eloquent\Relations\BelongsTo
*/
public function convention()
{
return $this->belongsTo('App\Convention');
}
}
Here is my ConventionController method called Convention...
It retrieves the details for the current convention
public function convention($slug)
{
if(!$this->admin()) return redirect()->back();
$convention = Convention::where('slug', $slug)->first();
$participants = Conventioner::where('convention_id', $convention->id)->get();
$conventioner = [];
foreach($participants as $participant)
{
$thisUser = [];
$thisUser['data'] = User::withTrashed()->where('id', $participant->user_id)->first();
$thisUser['convention'] = $participant;
array_push($conventioner, $thisUser);
}
var_dump($participants->users()->pluck('gender')->all());
return view('dashboard/conventions/convention', [
'convention' => $convention,
'user' => Auth::user(),
'conventioners' => $convention->conventioners(),
'participants' => $conventioner
]);
}
The problem is that users is a collection not an individual that you can call gender on. If you want a list of all the genders you can use the following:
Conventioner::where('convention_id', $convention->id)->with('users')->get()
$conventioners->pluck('users')->pluck('gender')->all();
This will return an array of the genders. You can read more about pluck here.
The pluck method retrieves all of the values for a given key

How to relate two tables in Laravel 5.0

In a little example, I have 3 tables (2 of them are important).
My tables are PRODUCT, TRANSFER, WAREHOUSE
I want to transfer the PRODUCT from 1 WAREHOUSE to another and obviously this transfer has to be in the TRANSFER TABLE, My example model could be the next.
HERE THE ENTITY - RELATION - MODEL
Now I'm Using Laravel 5.0
And when I create the models im doing this, with TRANSFER model:
<?php namespace Sicem;
use Illuminate\Database\Eloquent\Model;
class TRANSFER extends Model{
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'TRANSFER';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = ['id','ware_ori_id','ware_end_id','product_id'];
public function product(){
return $this->belongsTo('Sicem\Product');
}//THIS IS OK!
public function sourceware(){
return $this->belongsTo('Sicem\Warehouse\ware_ori_id');
}//I THINK THIS IS OK!
public function endware(){
return $this->belongsTo('Sicem\Warehouse\ware_end_id');
}//I THINK THIS IS OK!
}
Now, My question is here in my WAREHOUSE model, I don't what can I put:
<?php namespace Sicem;
use Illuminate\Database\Eloquent\Model;
class WAREHOUSE extends Model{
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'WAREHOUSE';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = ['id','name'];
public function transfer(){
return $this->hasMany('Sicem\TRANSFER');
}//I supose this.
//But is or not necesary to have 2(two) functions for the relation in my TRANSFER model???????????
}
SICEM: is my project name
Please Help me.
class Product {
protected $table = 'PRODUCT';
protected $fillable = ['name'];
public function transfers()
{
return $this->hasMany(Transfer::class);
}
public function transfer($warehouse_from_id, $warehouse_to_id)
{
return Transfer::create([
'product_id' => $this->id,
]);
}
}
class Transfer {
protected $table = 'TRANSFER';
protected $filalble = ['ware_ori_id', 'ware_end_id', 'product_id'];
public function warehouse_from()
{
retrun $this->belongsTo(Warehouse::class);
}
public function warehouse_to()
{
return $this->belongsTo(Warehouse::class);
}
public function product()
{
return $this->belongsTo(Product::class);
}
}
class Warehouse {
protected $table = 'WAREHOUSE';
protected $fillable = ['name'];
}
So you need to do something like this:
$warehouseFrom = Warehouse::find(1);
$warehouseTo = Warehouse::find(2);
$product = Product::find(23);
$product->transfer($warehouseFrom->id, $warehouseTo->id);

Resources