php - La relación de muchos a muchos de Laravel 8 no funciona (no se generan errores)

CorePress2024-01-24  9

Soy nuevo en Laravel pero tengo un problema muy extraño.

Creé exitosamente modelos y migraciones para 6 tablas para trabajar con relaciones de muchos a muchos. Una de las relaciones funciona bien y puedo recuperar datos a través de una ruta. El otro, sin embargo, sólo devuelve una pantalla en blanco (sin error, sin nada). La respuesta de la pestaña de redes dice: "Esta solicitud no tiene datos de respuesta disponibles". - pero verifiqué tres veces la base de datos y busqué diferentes registros y nunca arrojó ningún resultado.

Mantuve la información lo más simple posible y seguí todas las convenciones de nomenclatura.

¿Alguna idea de lo que está pasando aquí? ¿Hay algo mal configurado? Por favor, ayúdenme a no volverme loco. He probado un montón de iteraciones de código y nada parece funcionar para establecer la solución.Relación cliente/red de cualquiera a muchos.

Relación no laboral

Tabla de clientes:

+----------------+-----------------+------+-----+---------+----------------+
| Field          | Type            | Null | Key | Default | Extra          |
+----------------+-----------------+------+-----+---------+----------------+
| id             | bigint unsigned | NO   | PRI | NULL    | auto_increment |
| client_name    | varchar(255)    | NO   |     | NULL    |                |
| client_type_id | bigint unsigned | YES  |     | NULL    |                |
| address        | varchar(255)    | YES  |     | NULL    |                |
| address_2      | varchar(255)    | YES  |     | NULL    |                |
| city           | varchar(255)    | YES  |     | NULL    |                |
| state          | varchar(255)    | YES  |     | NULL    |                |
| zip_code       | varchar(255)    | YES  |     | NULL    |                |
| country        | varchar(255)    | YES  |     | NULL    |                |
| created_at     | timestamp       | YES  |     | NULL    |                |
| updated_at     | timestamp       | YES  |     | NULL    |                |
+----------------+-----------------+------+-----+---------+----------------+

Tabla de redes:

+--------------+-----------------+------+-----+---------+----------------+
| Field        | Type            | Null | Key | Default | Extra          |
+--------------+-----------------+------+-----+---------+----------------+
| id           | bigint unsigned | NO   | PRI | NULL    | auto_increment |
| network_name | varchar(255)    | NO   |     | NULL    |                |
| created_at   | timestamp       | YES  |     | NULL    |                |
| updated_at   | timestamp       | YES  |     | NULL    |                |
+--------------+-----------------+------+-----+---------+----------------+

tabla client_network:

+------------+-----------------+------+-----+---------+----------------+
| Field      | Type            | Null | Key | Default | Extra          |
+------------+-----------------+------+-----+---------+----------------+
| id         | bigint unsigned | NO   | PRI | NULL    | auto_increment |
| client_id  | bigint unsigned | NO   |     | NULL    |                |
| network_id | bigint unsigned | NO   |     | NULL    |                |
| created_at | timestamp       | YES  |     | NULL    |                |
| updated_at | timestamp       | YES  |     | NULL    |                |
+------------+-----------------+------+-----+---------+----------------+

Modelo de cliente:

namespace App\Models;

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

class Client extends Model
{
    use HasFactory;

    public function networks()
    {
        return $this->belongsToMany(Network::class);
    }
}

Modelo de red:

namespace App\Models;

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

class Network extends Model
{
    use HasFactory;

    public function clients()
    {
        return $this->belongsToMany(Client::class);
    }
}

Ruta:

Route::get('/testclient', function() {
    $network = Client::find(1)->network_name;
    return $network;
});

¡Hola! Solo para asegurarnos, ¿una publicación pertenece a muchos comentarios? Haría lo que dice la wiki, una relación de uno a muchos (e inversa) para que una publicación tenga muchos comentarios y muchos comentarios puedan pertenecer a una publicación. laravel.com/docs/8.x/eloquent-relationships#one-to-many

- Pimiento Verde

27/03/2021 a las 18:47

Si intenta algo como: $network = Client::find(1); devolver $red->cliente();

Próspero

27/03/2021 a las 19:11

@Prospero que arroja un 'mal método' error. Además, los otros modelos/métodos para la relación Publicaciones/Comentarios funcionan bien tal como están.

- Shaiden

27 de marzo de 2021 a las 23:56

1

Una recomendación personal, no nombrar en singular, lo que es un recurso de muchos. Si sus clientes pueden tener múltiples redes y viceversa, no nombre las relaciones como cliente() y red() porque devolverán una colección, pero si las lee como singulares esperará obtener un modelo... también puede hacer dd(Client::find(1)->network); y comparte los resultados.

Matiaslauriti

28 de marzo de 2021 a las 8:44

1

@matiaslauriti Dispara... Me faltan 2 puntos de reputación para poder votar a favor de tu comentario. Una vez que llegue allí, lo haré. Mientras tanto, agregaré la respuesta. ¡Gracias de nuevo!

- Shaiden

29/03/2021 a las 14:17



------------------------------------

Para cualquiera que esté enfrentando un problema similar, el problema en esta situación no era la relación, sino la ruta para extraer los datos de la relación.

Ruta que no funciona

Route::get('/testclient', function() {
    $network = Client::find(1)->network_name;
    return $network;
});

Ruta de trabajo

Route::get('/testing', function(){

    $networks = Client::find(1)->networks;

    foreach($networks as $network){

        $network_arr[] = $network->network_name;

    }

    return $network_arr;

Para resolver el problema, el código sugerido en los comentarios ayudó a mostrar que efectivamente se estaban extrayendo datos.de la relación pero no se muestra correctamente.

Código de ayuda:

dd(Network::find(1)->clients);

1

Puedes tener una forma más "laravel" código si cambia foreach a map, debe terminar con una función que haga esto: return $network->network_name; y automáticamente terminará con otra colección. Si necesita tener una matriz, entonces haga ->toArray() pero si va a iterar esa colección, no es necesario convertirla en una matriz.

Matiaslauriti

29/03/2021 a las 17:31



------------------------------------

Cometes un error tipográfico, cambia

Route::get('/testclient', function() {
    $network = Client::find(1)->network;
    return $network;
});

Para

Route::get('/testclient', function() {
    $network = Client::find(1)->networks; //Add s
    return $network;
});

1

Gracias por la sugerencia, pero todavía no devuelve ningún dato. Cambié la ruta anterior para reflejar la iteración actual.

- Shaiden

28/03/2021 a las 17:31

Su guía para un futuro mejor - libreflare
Su guía para un futuro mejor - libreflare