How to get data from intermediate table Laravel? - laravel

How to get data from third table through model?
I have model Prototype and PrototypeField model.
Where Prototype is:
id | name
Where PrototypeField is:
prototype_id | field_id
Also there is table Field that contains name of fields:
id | name
How to get names from table Field throught model 'Prototype' where Prototype relative with PrototypeField by:
Prototype.id = PrototypeField.prototype_id
So, Prototype can has one or many PrototypeField.

Your prototype model should have a relationship inside it which specifies the fields it should be related to for example:
public function fields()
{
return $this->belongsToMany('App\Fields'); // Change to location of fields model
}
Your fields model should also contain a relationship to specify which prototypes it relates to, for example:
public function prototypes()
{
return $this->belongsToMany('App\Prototypes'); // Change to location of prototype model
}
Once you have set these up, you will then be able to select the fields which the prototype belongs to using the following:
Prototype::first()->fields; //This selects the first prototype and gets the associated fields.
The inverse of which would be:
Fields::first()->prototypes //This selects the first field and get associated prototypes.
You can find out lots of information by reading the documentation on Laravel models - https://laravel.com/docs/5.4/eloquent-relationships

Related

Laravel Eloquent relation for getting user name for a specific id

I have a table named project. In this table I have a column named student_id. Model for this table is Project. And I have another table named user. And model name is User. Now I am retrieving all project table details in a page including student_id. Now I want to show user name instead of student_id. I mean I want to show this student name instead of student id. For example if student_id is 10 then I want to print name for that user from user table whose id is 10.
Any one please help.I have read document from laravel. But i don't know why I am not getting the eloquent concept properly.
Define belongsTo() relationship in Project model class:
public function student()
{
return $this->belongsTo(User::class, 'student_id');
}
And use it:
$project->student->name;

Eloquent join with where clause

I have problems to build a relationship with eloquent.
I have two models created, Spielplan and Verein. In model Spielplan I have the fields Team_ID and Spiel_ID. In model Verein I have the field V_ID and Name. Now I need to join this two tables about Team_ID = V_ID.
This is my model
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class Spielplan extends Model
{
protected $table = 'Spielplan';
public function vereinFunction(){
return $this->hasOne('App\Verein', 'V_ID');
}
}
And this is a function in my web route where I want to get Spiel_ID and Name.
Route::get('test', function(){
$spieleT = App\Spielplan::where('Spiel_ID', '=', 30)->get();
foreach($spieleT as $da){
echo $da->Spiel_ID;
echo $da->vereinFunction->Name;
}
});
The first echo works and I get back Spiel_ID but the second echo gives back ErrorException Trying to get property of non-object.
What is wrong with my code?
Try editing this line:
$spieleT = App\Spielplan::with('vereInFunction')->where('Spiel_ID', '=', 30)->get();.
The with() allows you to fetch the association at the time you use get(). After using get(), you're working with a collection, and can't query the database again.
Try specifying the model primary key as a third argument, because if not, Laravel will assume it is named id, which is not the case.
Allow me to suggest you something: I used to name the tables and fields like you do (in the days I use Codeigniter) but since I started using Laravel around three years ago, I follow Laravel convention (which is recommended, but not imposed). I now name the tables in lowercase, (snakecase) plural, table fields also snakecasm lowercase. Models singular, camelcase similar corresponding table, relation function names as related model, being singular if relation is to one, plural if to many, etc. The advantage of this is among other reflected in model relationship declaration, which is a lot simpler and easier to define.
For instance (only as demonstration of stated above),
tables (with relation one to many:
managers (primarykey: id, name, ......)
technicians (primary key: id, foreingkey: manager_id (related table name in singular plus underscore plus id), name, .....)
models:
Manager:
/* relationships */
public function technicians () // see name as related table, plural due to as many relationship)
{
return $this->hasMany(Technician::class); // as naming convention has followed, you don't need to specify any extra parameters;
}
Techician:
/* relationship */
public function manager() // named as related table, singular due to to one relationship
{
$this->belongsToOne(Manager::class); // again, as naming convention has followed, you don't need to specify any extra parameters;
}
Therefore you can do this:
$manager::find(1);
echo $manager->technicians->first()->name,
or
foreach ($manager->technicians as $technician) {
echo $technician->name;
}
as well as:
$technician->manager->name;
Remember, a proper model relationship definition will save a lot of headache along the way, like the one you have
Hope this help in anyway

what to do with an inverted polymorphic relation?

I have been trying to get my head around these polymorphic relationships all day. I might be over complicating/thinking it but. Can Laravel handle inverse polymorphic relationships? I have a registration flow that can have two types of field Models- normal field and customField.
When I loop through all the fields available it could pull the attributes from either NormalField or CustomField.
<?php
foreach($registrationFlow->fields->get() as $field)
{
echo $field->name; // could be custom field or could be normal field
}
?>
My difficulty is that, the example given in the docs works if you want to assign a photo to either staff or orders, but i want to assign either a customField or a normalField to a registrationFlow
*Edit
If you follow the example for the polymorphic many to many relationship, The tag class contains posts and videos- while i would want just a simple fields() method that relates to customField or normalField dependent on the type
First of all, you should take a look at the updated docs for Laravel 5.1: https://laravel.com/docs/5.1/eloquent-relationships#polymorphic-relations.
I think the difficulty with the example they provide is that the relationship between Photo and Staff/Product are "has-a" relationships, whereas you are trying to model an "is-a" relationship. However, you can model "is-a" essentially the same way. Take a look at this article: http://richardbagshaw.co.uk/laravel-user-types-and-polymorphic-relationships/.
Basically, the strategy is to define a generic model (and a generic table), perhaps in your case Field, that relates to your RegistrationFlow. You then have two subtype models, NormalField and CustomField, that have one-to-one relationships with Field. (there's your "is-a"). Thus, RegistrationFlow is indirectly related to your field subtypes.
Polymorphism comes in when you want to access the specific subtypes:
class Field extends Model {
public function fieldable()
{
return $this->morphTo();
}
}
Your base field table should have fieldable_id and fieldable_type columns defined (see the Eloquent docs).
You can then add methods to NormalField and CustomField that let you access the base model (your "inverse relationship"):
class NormalField {
public function field()
{
return $this->morphOne('Field', 'fieldable');
}
}
class CustomField {
public function field()
{
return $this->morphOne('Field', 'fieldable');
}
}
Usage:
$field = Field::find(1);
// Gets the specific subtype
$fieldable = $field->fieldable;

getting all attributes for nested relationships in laravel in one JSON

I am trying to get all attributes in one JSON.
Eg:
Consider I have a table "place" with "id","name","description" as attributes.
Now,
I have another table "region" with "id","name","place_id","description" as attributes(or) schema.
There is one to many relationship between place and region.
And now,I define another table "street" with "id","name","region_id" as its schema.
There is again One to Many relationship between "region" and "street".
I want to get all details which comes in one place.If there is some place "1,banglore,garden city" and there are two regions with that place_id as
"{"1,r.t.nagar,1,region in banglore"},{"2,ashok nagar,1,region in banglore"}".Here "1" is foreign key referring id of "banglore's id(1)".
Now,similarly if each region has 3 streets in street table.I want to get all the values in one JSON. I know that we can get this with foreach .But,i want an efficient solution to get all nested relationship to my Place model from Region,Street in JSON.
Thanks.
You first need to define one to many relations like:
class Places extends Eloquent{
....
public function regions()
{
return $this->hasMany('App\Region');
}
...
}
And the same to streets:
class Regions extends Eloquent{
....
public function streets()
{
return $this->hasMany('App\Street');
}
....
}
Note that I have assumed that your models stay within App folder and have corresponding namespaces.
After that you can get you model like:
Place::with('regions.streets')->get();
Which will automatically nest all relations and cast to JSON if you send a json response.

Many to one on one table, relationship in laravel

I have model, named Magazine. This model represents of magazines table.
magazines
--id
--name
I also have model, named Transfer. This model is represents of transfers table.
In this table I would like store information about product transfers.
transfers
--id
--source
--target
There are two important columns, source is id of magazine from I getting product, target is id of magazine where I put the product.
How should I create relationship in Eloquent model? I did something like this
public function source()
{
return $this->belongsTo('Magazine', 'source');
}
public function target()
{
return $this->belongsTo('Magazine', 'target');
}
But, doesn't work. If I call $transfer->source I only get id, which is stored in this column(integer value). But I would like get Magazine object. If I change method name from source() to magazine(), Eloquent returns Magazine object, and this is correct.
How should I create relationship if source and target indicate on the same table
Your fields and methods overlap. So now you can do this:
$transfer->source()->getResult()->name;
but obviously this is not the way to handle relationships.
That said, to make it work as expected, rename either methods or table fields. I suggest this:
table transfers: id, source_id, target_id
// Transfer model
public function source()
{
return $this->belongsTo('Magazine', 'source_id');
}
public function target()
{
return $this->belongsTo('Magazine', 'target_id');
}
If you call $transfer->source you will only get the id.
You need to load your source too
$transfer = Transfer::with('source')->find(123);
and then access the name of the source
$nameOfSource = $transfer->source->name

Resources