3

I am trying to write some code, that displays data from a database in Laravel. But I have two table values linked to eachother with a foreign key, and when I try to show that on my page, it just shows the id and not the actual name. I saw in another stackoverflow question that you should define the table data values in ur Model, but that doesn't work or I did it wrong. Can someone be so kind to help me fix this please? :)

Model Planet.php:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Planet extends Model
{
    public function solar()
    {
    return $this->belongsTo(SolarSystems::class, 'id');
    }
}

Model SolarSystems.php:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class SolarSystems extends Model
{
    public function planet()
    {
        return $this->belongsTo(Planet::class, 'solar_systems_id');
    }
}

PlanetController.php:

<?php

namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\Planet;
use App\Models\SolarSystems;

class PlanetController extends Controller
{
    public function index()
    {
        $planets = Planet::all();
        $solar = SolarSystems::all();

        return view('welcome', ['planets'=>$planets]);
    }
    public function show($planeet)
    {
        $planets = Planet::all();
        $solar = SolarSystems::all();
    
        $planets = collect($planets)->where('name', $planeet);
        return view('welcome', ['planets' => $planets]);
    }
}

welcome.blade.php:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <title>Laravel</title>
        <link href="https://fonts.googleapis.com/css2?family=Nunito:wght@400;600;700&display=swap" rel="stylesheet">
        <style>
            body {
                font-family: 'Nunito', sans-serif;
            }
        </style>
    </head>
    <body>

@foreach ($planets as $planeten)
    <ul>
        <li>{{ ucfirst($planeten->name) }}</li>
        <p>{{ ucfirst($planeten->description) }}</p>
        <p>{{ ucfirst($planeten->solar_systems_id) }}
    </ul>
@endforeach
    </body>
</html>

import.sql:

CREATE DATABASE laravel;
USE laravel;
CREATE TABLE planets (
    id int(11) AUTO_INCREMENT,
    name text,
    description text,
    size_in_km int(11),
    solar_systems_id int(11),
    PRIMARY KEY (id)
);

CREATE TABLE solar_systems (
    id int(11) AUTO_INCREMENT,
    name text,
    age_in_years int(11),
    PRIMARY KEY (id)
);

INSERT INTO planets (name, description, size_in_km, solar_systems_id)
VALUES ('mars', 'Mars is the fourth planet from the Sun and the second-smallest planet in the Solar System, being larger than only Mercury.', 3389, 1);

INSERT INTO planets (name, description, size_in_km, solar_systems_id)
VALUES ('venus', 'Venus is the second planet from the Sun. It is named after the Roman goddess of love and beauty.', 6051, 1);

INSERT INTO planets (name, description, size_in_km, solar_systems_id)
VALUES ('earth', 'Our home planet is the third planet from the Sun, and the only place we know of so far thats inhabited by living things.', 6371, 1);

INSERT INTO solar_systems (name, age_in_years)
VALUES ('The Milky Way', 1360000000);

This is what I get right now, but instead of the '1' it needs to say: 'The Milky Way' enter image description here

1
  • Where is the relational table of the two tables ? Have you defined one that connects the two tables "planets" and "solar_systems"? Bear in mind that you need a specific key that is on both tables like the id of the solar_system for example. If you haven't set that, I think that you should first check how to set up a relational table and then set up your Model. Commented Jan 26, 2022 at 11:40

3 Answers 3

1

There few issues with your code;

Relationship

You have 1-N relationship, a Planet belongsTo a Solar System and a Solar System hasMany Planet.

Planet.php

public function solar()
{
    return $this->belongsTo(SolarSystems::class, 'solar_systems_id');
}

SolarSystems.php

public function planets()
{
    return $this->hasMany(Planet::class, 'solar_systems_id');
}

Controller

PlanetController.php

public function show($planeet)
{
    $planets = Planet
              ::with('solar')
              ->where('name', $planeet)
              ->get();
       
    return view('welcome', ['planets' => $planets]);
}

Has you can see, I'm using with and where to optimize the query.

View

Since you have loaded the relationship with the eager loading, you can directly have access to the model from the planet.

 <p>{{ ucfirst($planeten->solar->name) }}
Sign up to request clarification or add additional context in comments.

1 Comment

Now it finally works, thank you so much man! :D
0

replace this line

<p>{{ ucfirst($planeten->solar_systems_id) }} 

with this line

<p>{{ ucfirst($planeten->solar()->name) }}</p> 

3 Comments

This cause a N+1 issue that could easily be solved with eager loading
All I'm getting now is this error: 'Undefined property: Illuminate\Database\Eloquent\Relations\BelongsTo::$name (View: C:\Users\mauro\OneDrive\Bureaublad\School\Bit Academy\18 Laravel\project\resources\views\welcome.blade.php)'
So use Planet::with('solar')->get() instead of Planet::all() , and there is no need for the brackets just <p>{{ ucfirst($planeten->solar->name) }}</p>
0

Just replace this line

{{ ucfirst($planeten->solar_systems_id) }} 

with this line 

{{ ucfirst($planeten->solar->name) }}

Because you need to get the name from the relationship

1 Comment

Like the other answer, this cause a N+1 issue that could easily be solved with eager loading $planets = Planet::with('solar')->get();

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.