Insert relational models laravel eloquent - php

I am new to eloquent for laravel 4 and i can't quite figure out on how to make and save related models.
Table Messages: id | user | message | parent
For example:
class Message extends Eloquent {
public function user(){
return $this->belongs_to('User', 'id');
}
public function child(){
return $this->hasMany('Message', 'parent');
}
public function parent(){
return $this->belongs_to('Message', 'id')
}
}
So if you have a conversation you have a message, this message may or may not have a child or a parent and always has a user which made the message. So if i want to save a conversation this way, how would i do this?
For example, i have to following conversation:
John (1) says: Hi all!
Mark (3) responds: Hey there!
Hans (4) responds: Hi john
Peter(2) responds: Goodmorning.
Now i am john and i would like to save this conversation as below:
id | user | message | parent
========================================
1 | 1 | Hi, All! | NULL
2 | 3 | Hey there! | 1
3 | 4 | Hi john | 1
4 | 2 | Goodmorning. | 1
I can save them all separately but i figure there has to be a better way than below:
$parent = NULL;
foreach($messages as $message){
$model = new Message;
$model->user = $message['user'];
$model->message = $message['value'];
if(!is_null($parent)){
$model->parent = $parent;
}
$model->save();
if(is_null($parent)){
$parent = $model->id;
}
}

The initial problem I saw was that you are saying that the message's parent is always itself, you need to specify an additional unsigned integer to relate on. Here's one example:
public function parent(){
return $this->belongs_to('Message', 'parent_id')
}
You need to use that same 'parent_id' for the children as well:
public function children(){
return $this->hasMany('Message', 'parent_id');
}

Related

Laravel relationship HasMany

I keep multiple address records belonging to a user. but when i write with dd i can't access other table's data.
Following my code:
user Table
id | name | country |
--- -------------- ----------
7 | Mr. Lenny Bins| Belgium
2 | Dalton Miller | Swaziland
address Table
user_id | address
-------- ---------
7 | 740 Brown Greens Suite
7 | 9906 Cleora Wall Apt.
2 | 53977 Kip Center Apt
UserModel
public function getAddress()
{
return $this->hasMany(Address::class);
}
UserController
$users = User::where('id' ,7)->with('getAddress')->get();
dd($users->toArray());
// The output of this is below
dd($users->getAddress->toArray());
I get an error when I try like this.
Property [getAddress] does not exist on this collection instance.
Firstly you are using get that will return collection, In Following you will get all users with their addresses.
$users = User::where('id' ,7)->with('getAddress')->get();
You can use first() instead of get() as you are finding only one user
$user = User::where('id' ,7)->with('getAddress')->first();
If You want only address of that user use
dd($user->getAddress)
Or If you want only in form of array use
dd($user->getAddress->toArray())
User Model
public function getAddress()
{
return $this->hasMany('App\Address');
}
Get User(s)
$users = \App\User::with('getAddress')->where('id' ,7)->get();
Iterate and read data
foreach ($users as $user) {
echo '<pre>' , var_dump($user->getAddress()->first()['address']) , '</pre>';
}
$users = User::with('getAddress')->where('id' ,7)->first();
dd($users);

Laravel get all from with belongTo value

In my Laravel 8 project I have two tables A and B:
| A |
---------
| ID |
| B_ID |
| VALUE |
| B |
-----------
| ID |
| VALUE |
| Private |
In my models I have:
A{
public function b()
{
return $this->belongsTo(B::class);
}
}
B{
public function as()
{
return $this->hasMany(A::class);
}
}
In my controller I have:
public function index()
{
$a = A::join('bs', 'as.b_id', '=', 'b.id')->get(['as.value', 'bs.value']);
return $a;
}
Is'nt there a more elegant Laravel way to do this?
I would like to get all records from table A with the value from table B but without the private value from B. (There could be a lot of entries in Table A, Table B only has some values (<20) ).
When building a query, you may specify which relationships should be eager loaded using the with method. In your case you could write:
A::with('b:value')->('value')
In the with you can precise a specific relationship by its name or a list of column you want : https://laravel.com/docs/8.x/eloquent-relationships
The code I have provided as an example as not been tested and may need some changes but you have the general idea

Laravel Lumen Many to One return []

I'm quite new in Lumen but I have to do this because i have final task about Laravel.
So, i do have these two tables, the users and userTypes table.
usertypes table
+-----------------------+
| userTypeId | typeName |
+-----------------------+
| 1 | admin |
| 2 | buyer |
| 3 | store |
+-----------------------+
users table
+----------------------------------+
| id | name | email | userTypeId |
+----------------------------------+
| 1 | john | e#e.com | 2 |
+----------------------------------+
Now, what i was hoping the output for is something like this:
{
"data" : {
"id" : 1,
"nama" : "john",
"email" : "e#e.com",
"usertypes" : {
"typesName" : "buyer"
}
}
}
I've tried hasMany() and hasOne() and more but the "userTypes" field still return []. Here's the model for both of that.
User.php
....
public function usertype() {
return $this->hasMany(UserTypes::class, 'userTypeId');
}
....
UserTypes.php
.....
public function User() {
return $this->belongsTo(User::class);
}
.....
And here's the UserController.php
...
public function user($id) {
$user = User::with(['usertype'])->findOrFail($id);
return response()->json(['data' => $user]);
}
...
Any way to fix this? I appreciated for anyone who willing to help me. Thank you 🙏🙏
Its better to use find method you use route model binding. when you pass id
to method User $user auto find user from databse. now we have $user so we
call relation $user->usertype.
public function user(User $user) {
return response()->json(['data' => $user->usertype]);
}
So it appears that i'm not fully understand the meaning of the "third parameters" and thanks to someone in telegram group that helping me out, in the User model it should be:
return $this->hasOne(UserTypes::class, 'userTypeId', 'userTypeId');
and it works. Second parameter is the foreign key on the users table, third parameter is the primary column name in that userTypes table. Hope it clears the dumb newbie like me.

Laravel Eloquent returns an empty collection on belongsToMany relationship

UPDATE: The issue mentioned here has caused by the use of MariaDB instead of MySQL by XAMPP. I have followed the answer here to switch it to MySQL and it works like a charm.
This is regarding an e-commerce platform.
I have 2 data tables with 1 joining table for a many-to-many join. The idea is for Products to have many Special Offers running at any given time.
Tables
products
+-------+-------------------------------+
| id | name |
+-------+-------------------------------+
| 10001 | Apple iPhone 11 |
| 10002 | Samsung Galaxy S11 |
+-------+-------------------------------+
special_offers
+----+-------------------------------+
| id | name |
+----+-------------------------------+
| 1 | Awesome Offer |
| 2 | Year End Offer |
+----+-------------------------------+
product_special_offer
+------------+------------------+----------+
| product_id | special_offer_id | discount |
+------------+------------------+----------+
| 10001 | 1 | 10.0 |
| 10002 | 2 | 12.5 |
+------------+------------------+----------+
Models
Since the requirement is for a many-to-many relationship, I am using belongToMany method in my models.
Product
class Product extends Model
{
public function specialOffers()
{
return $this->belongsToMany(SpecialOffer::class)->withPivot('discount');
}
}
SpecialOffer
class SpecialOffer extends Model
{
public function products()
{
return $this->belongsToMany(Product::class)->withPivot('discount');
}
}
Controller
The following is the controller snippet.
ProductController
class ProductController extends Controller
{
public function index()
{
$product = Product::find(10001);
dd($product->specialOffers);
}
}
Results
The following is what Laravel returns.
Collection {#610 ▼
#items: []
}
The query it runs is mentioned below.
select `special_offers`.*, `product_special_offer`.`product_id` as `pivot_product_id`, `product_special_offer`.`special_offer_id` as `pivot_special_offer_id`, `product_special_offer`.`discount` as `pivot_discount` from `special_offers` inner join `product_special_offer` on `special_offers`.`id` = `product_special_offer`.`special_offer_id` where `product_special_offer`.`product_id` = 10001
This could work
class SpecialOffer extends Model
{
public function products()
{
return $this->belongsToMany(Product::class, 'product_special_offer','special_offer_id','product_id');
}
}
Make a third model to the connection table, and add the two relation. And it's will work.
class ProductSpecialOffer extends Model
{
public function products() {
return $this->belongsTo(Product::class);
}
public function specialOffers() {
return $this->belongsTo(SpecialOffer::class);
}
}

Laravel hasManyThrough but must return only one array

I have these tables:
Entries table
---------------------------------
| id | blog_id | title |
---------------------------------
| 1 | 1 | 1st Entry |
---------------------------------
Blogs Table
-----------------
| id | name |
-----------------
| 1 | 1stBlog |
-----------------
Field Groups Table
-------------------------
| id | blog_id | name |
-------------------------
| 1 | 1 | Group1 |
-------------------------
Fields Table
---------------------------------
| id | field_group_id | name |
---------------------------------
| 1 | 1 | field_1 |
---------------------------------
Values Table
------------------------------------------
| id | field_id | entry_id | value |
------------------------------------------
| 1 | 1 | 1 | Hello World |
------------------------------------------
Now on my Models I've set up these relationships:
class Entry extends Model
{
public function blog()
{
return $this->belongsTo(Blog::class);
}
}
class Blog extends Model
{
public function entries()
{
return $this->hasMany(Entry::class);
}
public field_group()
{
return $this->hasOne(FieldGroup::class);
}
}
class FieldGroup extends Model
{
public function fields()
{
return $this->hasMany(Entry::class);
}
public function blog()
{
return $this->belongsTo(Blog::class);
}
}
class Field extends Model
{
public function group()
{
return $this->belongsTo(FieldGroup::class, 'field_group_id');
}
public function values()
{
// this method should get the values from the Values table per entry id
return $this->hasManyThrough(Value::class, Entry::class, 'id', 'entry_id');
}
}
class Value extends Model
{
public function field()
{
return $this->belongsTo(Field::class, 'field_id');
}
}
Using this query I can
$entry = Entry::with('blog.field_group.fields')->find(1)
I can get the entry, along with its blog, field groups and fields. I want to get the values associated with the entry too,
$entry = Entry::with('blog.field_group.fields.values')->find(1)
I am having trouble on which relationship to use. Any help is much appreciated. I just started using laravel.
Try it...
Replace ID by field_id:
return $this->hasManyThrough(Value::class, Entry::class, 'id', 'entry_id');
Like this:
return $this->hasManyThrough(Value::class, Entry::class, 'field_id', 'entry_id');
Because you are using the standard laravel column names you can simplify even more:
return $this->hasManyThrough(Value::class, Entry::class);
See in: https://laravel.com/docs/5.1/eloquent-relationships#has-many-through
I think you should use 'foreign_key' with 'hasMany' and 'hasOne'.
return $this->hasMany('Comment', 'foreign_key');
class Blog extends Model
{
public function entries()
{
return $this->hasMany(Entry::class, 'blog_id');
}
public field_group()
{
return $this->hasOne(FieldGroup::class, 'blog_id');
}
}
refer
http://laravel.com/docs/4.2/eloquent#one-to-many

Categories