Cannot using where in eloquent - laravel

I'm using Eloquent ORM in Laravel. There is 2 model, User and Trans. User hasMany Trans, and Trans belongsTo User. The problem is when I'm using query where, it doesn't work.
I tried using ->get() in the last code, it still doesn't work. I tried using ->all() in the last code it still doesn't work. I tried whereIn, it still doesn't work.
User Model
public function trans()
{
return $this->hasMany('App\Trans', 'user_id');
}
Trans Model
public function user ()
{
return $this->belongsTo('App\User','user_id');
}
Controller
$trans = Auth::user()->trans->where('date', $date);
I want the output is based on query where the date is based on user input, when I delete ->where , it works and the output like this.
Collection {#797 ▼
#items: array:13 [▼
0 => Trans {#783 ▶}
1 => Trans {#784 ▶}
2 => Trans {#785 ▶}
3 => Trans {#786 ▶}
]
}

try to change like that
Auth::user()->trans->where('date', $date);
to
Auth::user()->trans()->where('date', $date)->get();
note : if you want to get only property then u get property without
pointer but if you want to used another method then must used(add)
pointer(->).

Related

Sort an Eloquent model

Table for MyModel is like below
id name parent_id
--------------------------
1 parent1 null
2 p1-c1 1
3 parent2 null
4 p1-c1-g1 2
5 p2-c1 3
6 p1-c1-g1-f1 4
7 parent3 null
8 p1-c2 1
9 p3-c1 7
10 p1-c2-c1 8
How order with eloquent or raw DB query without getting all rows like below
Collection {#499 ▼
#items: array:22 [▼
0 => MyModel {#524 ▶} // parent1
1 => MyModel {#525 ▶} // p1-c1
2 => MyModel {#526 ▶} // p1-c1-g1
3 => MyModel {#527 ▶} // p1-c1-g1-f1
4 => MyModel {#528 ▶} // p1-c2
5 => MyModel {#529 ▶} // p1-c2-c1
6 => MyModel {#530 ▶} // parent2
7 => MyModel {#531 ▶} // p2-c1
8 => MyModel {#532 ▶} // parent3
9 => MyModel {#533 ▶} // p3-c1
]
}
for a better view and understanding
parent1
p1-c1
p1-c1-g1
p1-c1-g1-f1
p1-c2
p1-c2-c1
parent2
p2-c1
parent3
p3-c1
use Recursive relationship to same table
For example if model name is MyModel then the relationship will be
public function child(){
return $this->hasMany(MyModel::class,'parent_id','id');
}
public function recursiveChild(){
return $this->child()->with('recursiveChild');
}
So in your controller
MyModel::with(['recursiveChild'])->get();
What is your actual code, what are you trying to accomplish with this?
Collections are your friend in Laravel.
You can do a groupBy or using a With if you have a table that's related... your question is really too ambiguous.
You can get fairly complex with many chained Where orWhere with limits and groupBy
What I do see is that you need to have is not only the parent in the db but you also need a sort order on the children. Another thought is do you need a Grandparent, Parent, child? In that case you're going to have to have columns for all of those to know who they belong to when building your collection or doing just a straight eloquent pull.
My guess is this is for a menu or something you have here. Again ambiguity, so totally guessing.
EDIT
I've done this kind of thing in several apps...
You're table is going to look something like this:
id, name, menu_type, url, page_id, parent_id, sidebar, order, depth, role, created_at, updated_at, deleted_at
So in your model your going to want to do a relationship:
public function parent()
{
return $this->belongsTo('App\Models\Menus', 'parent_id');
}
public function children()
{
return $this->hasMany('App\Models\Menus', 'parent_id')->orderBy('order', 'asc');
}
Then what I've done is use this as a trait so it's available wherever I need to use it.
The trait is a little more complex than you are asking but it points you in the direction.
public function PrimaryMenu($pageid , $namespace, $user) {
// Get all primary menu items.
$appspace = "\App\Models\\".$namespace."\\Menus";
$roles = $user->roles->pluck('name');
$pmenus = $appspace::with('children')->where([['menu_type', '=', 'primary'],['parent_id','=', NULL]])->
where(function ($q) use($pageid) {
$q->where('page_id', '=', $pageid)->orWhere('page_id', NULL);
})->
where(function ($q2) use($roles) {
$q2->whereIn('role', $roles)->orWhere('role', '=', NULL);
})->
get();
return $pmenus;
}
You can see I'm checking a type of menu (this can be anything as long as you have something to group them by category) in this case primary, then I check for the page and see if we should include a row or not on the page then I check for any roles the user might have that we should include items.
Then in your controller it's just a matter of using the trait at the top:
use App\Traits\CommonTrait;
Now all of those traits are available to use in your controller. So you just call the function you need:
$pmenus = $this->PrimaryMenu($pageid, $namespace, $user);
You can see I'm sending along 3 variables to this as I have this set up for having many menus. Really the code translates to anything though that you want children associated with a parent.
The important bits are the model actions on relationships.
Thanks everyone, i used this package to achieve a sort like that.
https://github.com/lazychaser/laravel-nestedset#building-flat-tree

Laravel - Select relation columns

I am trying to write a query which selects columns from a model then selects one column from a relationship table.
Team Model
public function members(){
return $this->hasManyThrough('App\User', 'App\Membership', 'team_id', 'id', 'id', 'user_id');
}
Member(user) model
public function skills()
{
return $this->belongsToMany('App\Skill');
}
Function
Query i have attempted but had no luck:
$members = $this->team->members()
->select('id', 'name')
->with(['skills' => function ($query) {
$query->select('name');
}])
->get();
dump of query
When i dump the query it returns just the data for the id and name columns from the team table but the skills relation returns back empty when i want it to return the name from that table.
#relations: array:1 [▼
"skills" => Illuminate\Database\Eloquent\Collection {#1657 ▼
#items: []
}
]
How would do i grab the name column from the skills relation table within this query?
To select column in relation you can use this :
->with('members.skills:id,name')
If you're not passing id attribute inside the with, the relation can't work
You need to add the id to the fields returned from the skills table. Otherwise Eloquent has no way to link the skill to the correct team.
->with(['skills' => function ($query) {
$query->select('id', 'name');
}])

Laravel remove index element from get collection

I pull in data from the database via ->get(); and want to remove a certain element based on a condition in a foreach loop so i would need something like
foreach($datas as $data) {
$data->forget(this);
}
or i count the index or whatever, but I need to find a way to remove it because the ->forget() does only work on collection instances (not on eloquent collections as it seems) , any idea?
here is the format of my log:
[{"id":14,...},{"id":15,...}...]
so i get objects in an array.
and here is the dd();
Collection {#274 ▼
#items: array:4 [▼
0 => Data {#275 ▶}
1 => Data {#276 ▶}
2 => Data {#277 ▶}
3 => Data {#278 ▶}
]
}
edit: i know its better to select only needed elements in the first place but thats not possible or rather not wished for because I am putting the results through a long carbon related check and wish to do something depending on different scenarios.
edit 2:
I can remove with forget(1..2 and 3) but not with 0, it tells me undefined offset?
Maybe map is what your are looking for if you want to remove a specific property in the item:
$datas = $datas->map(function ($data) {
// modify $data here, unset unset($data->property);
return $data;
});
See documentation here
Or filter to remove the whole item:
$datas = $datas->filter(function ($data) {
return ($data->property == 'bar') ? true : false;
});
See documentation here

How to pluck data for a form

I'd like to show names on my select dropdown
I have 3 tables: 'users','users_pro' and 'practice'
users : id ,name ,dob ,.. etc
users_pro : id ,user_id,..etc
practice : id , user_pro_id ,...etc
I want to input data to table 'practice' and I want to make a select dropdown using pluck on users_pro with users like this :
public function input_practice()
{
$data= Users_pro::with('users')->get()->pluck('id','user_id');
dd($data);
// return view('admin.input.input_riwayat_kgb',
// [
// 'data'=>$data,
// ]);
}
If I dd($data), I get :
Collection {#327 ▼
#items: array:4 [▼
6 => 3 // 6 is user_id ,and 3 is 'id' on users_pro , i need to show 'name' like 3 => 'jhon'
13 => 4
12 => 5
14 => 6
]
}
But I want to show the name of the user on my select dropdown. Can someone help me?
You are trying to pull a collection and then get the name and id from the relationship models within. Thus, you will get an error that the property does not exist on the collection because it is many User_pro objects and then tries to get user data from each one of the relations would require a loop.
Assuming you have a users relationship set up on the User_pro model, you can get your dropdown list like this:
$data= User::whereHas('user_pro')->pluck('name','id');
This gives you a collection of users (who happen to be pros) and then plucks the name and id of your users for you to use in your dropdown.
This is solved with this line :
$data = Users_pro::with('users')->get()->pluck('users.nama', 'id');

Laravel: Check if Models have same relation

I have models: Partido and Coalicion related in a many to many relationship.
I need to know when two or more Coalicion has the same Partido related.
Hope I have explained myself.
Edit 1:
Model:
class Coalicion extends Model
{
public function partidos()
{
return $this->belongsToMany(Partido::class);
}
}
Let's say users selected some elements from a select input and I grabbed them in an array and send them to the controller.
...
public function example(Request $request)
{
$coaliciones = $request->coaliciones;
foreach ($coaliciones as $c) {
$coalicion = Coalicion::find($c);
# Here we have a list of Coalicion model in a loop
# Let's say the first iteration I can see the relationship
dump($c->partidos);
}
}
This for example give me the following answer at the browser:
Collection {#1 ▼
#items: array:2 [▼
0 => Partido {#271 ▶} #This is Partido with id 1
1 => Partido {#268 ▶}
]
}
Collection {#2 ▼
#items: array:3 [▼
0 => Partido {#279 ▶}
1 => Partido {#280 ▶}
2 => Partido {#283 ▶} #This is Partido with id 1
]
}
I need to know when the item 0 of the first Collection and the item 2 of the second Collection are the same.
I kinda found a way but I don't know if it's the correct or best approach.
In Coalicion model I add the following function:
public function partidosId()
{
return $this->partidos->pluck('id');
}
With this I can get only the id's from the relations, then in the controller I created an empty array() and fill it with all my ids with a foreach loop, then, finishing up I evaluated if the id's in the now filled array are unique, if the unique values are less than the length of the array then some models have the same relation (I don't know which but It's a start), e.g.:
public function example(Request $request)
{
$coaliciones = $request->coaliciones;
$allItems = [];
foreach ($coaliciones as $c) {
$coalicion = Coalicion::find($c);
$allItems = array_merge($allItems, $coalicion->partidosId()->toArray());
}
if (count(array_unique($allItems))<count($allItems)) {
dd("Duplicates");
}else{
dd("Uniques");
}
}
If anyone find a better way or a way to know which are the ones with the duplicate relation please let me know

Resources