php - relacion - tabla pivote laravel
Uso de pivote personalizado de Laravel(Extiende el modelo o amplĂa el pivote) (1)
Estoy realmente atascado usando un modelo personalizado para mi pivote, y no entiendo por qué podemos crear un modelo personalizado si no podemos usarlo como modelo. He visto muchas respuestas y artículos, y todos decidieron ampliar Pivot o Model, pero el uso de la vida real nunca se toma en cuenta y nunca va más allá de darle una clase "named".
Aquí hay un ejemplo de lo que intento lograr: mis modelos principales: modelo de jugador , con mesa de jugadores . Modelo de juego , con mesa de juegos .
El jugador y el juego tienen una relación de muchos a muchos, a la que podemos llamar " Fiesta " con una mesa de " jugador_jugador ".
Menos importante por ahora, también tengo un modelo de puntaje que contiene los puntajes / turnos, una parte puede tener muchos puntajes, por lo que la tabla de puntajes tiene una entrada party_id.
Entonces, aquí están básicamente mis clases (Laravel 5.2):
Jugador
class Player extends Model
{
// The Games this Player is participating to.
public function games() {
return $this->belongsToMany(Game::class)->withPivot(''id'')->withTimestamps();
}
// The Scores belonging to this Player.
public function parties() {
return $this->hasManyThrough(Score::class, Party::class);
}
// The Custom Pivot (Party) creation for this Player.
public function newPivot(Model $parent, array $attributes, $table, $exists) {
if ($parent instanceof Game) {
return new Party($parent, $attributes, $table, $exists);
}
return parent::newPivot($parent, $attributes, $table, $exists);
}
}
Juego
class Game extends Model
{
// The Players participating into this Game.
public function players() {
return $this->belongsToMany(Player::class)->withPivot(''id'')->withTimestamps();
}
// The Scores belonging to this Party.
public function parties() {
return $this->hasManyThrough(Score::class, Party::class);
}
// The Custom Pivot (Party) creation for this Game.
public function newPivot(Model $parent, array $attributes, $table, $exists) {
if ($parent instanceof Player) {
return new Party($parent, $attributes, $table, $exists);
}
return parent::newPivot($parent, $attributes, $table, $exists);
}
}
Fiesta
class Party extends Pivot
{
protected $table = ''game_player'';
// The Player this Party belongs to.
public function player() {
return $this->belongsTo(Player::class);
}
// The Game this Party belongs to.
public function event() {
return $this->belongsTo(Game::class);
}
// The Scores belonging to this Party.
public function scores()
{
return $this->hasMany(Score::class);
}
}
Puntuación
class Score extends Model
{
// The Party this Score belongs to (has "party_id" column).
public function party() {
return $this->belongsTo(Party::class);
}
}
Ahora, tengo dos conjuntos diferentes de problemas que aparecen dependiendo de si extiendo Model o Pivot on Party:
1) Cuando Party extiende Pivot:
- No se puede hacer algo como Party :: count () , cualquier cosa que funcione con modelos.
- No se puede hacer algo como Party :: where ("player_id", $ player-> id) y así sucesivamente ... Básicamente quiero que la fiesta tenga una tabla de puntajes / turnos adjunta y, para ello, debo seleccionar el modelo de pivote.
- No se puede hacer algo como $ events-> player-> first () -> scores () ni event $ events-> player-> first () -> pivot-> scores (), rompe con lo siguiente:
Error de PHP: el argumento 1 pasado a Illuminate / Database / Eloquent / Relations / Pivot :: __ construct () debe ser una instancia de Illuminate / Database / Eloquent / Model
2) Cuando Party extiende el Modelo:
- Puede hacer cosas triviales como Party :: count (), Party :: where ("Game_id", $ game-> id)
- Pierde todas las funciones de pivote, así que no puede hacer $ juegos-> jugadores, ni siquiera $ games-> players () funcionan: $ game-> players () -> count () es correcto, pero $ game-> players () -> first () o $ game-> players-> first () se romperá con lo siguiente:
Error de PHP: el argumento 1 pasado a Illuminate / Database / Eloquent / Model :: __ construct () debe ser del tipo array, objeto dado
Pregunta:
¿Cómo usar correctamente el modelo de pivote personalizado cuando crear instancias de ellos es diferente?
Espero lograr lo siguiente:
- Haz lo normal $ eventos-> jugadores-> adjuntar ($ jugador)
- Ser capaz de adjuntar un puntaje como $ score-> party_id = $ events-> players-> find ($ x) -> pivot-> id (o de cualquier otra manera a través de un alcance, por ejemplo)
- Ser capaz de contar todas las partes que se juegan, o las que están en un juego específico o por un jugador específico (algo así como Party :: count (), $ player-> parties-> count () etc)
Gracias.
Por mi - poca - experiencia con laravel, he encontrado que las pivot tables
se usan cuando tienes una relación de many-to-many
que solo mantiene un enlace entre un objeto específico de la tabla A y la tabla B. Por ejemplo, Usuario con Rol .
Como puede obtener una imagen, un usuario A solo necesita un enlace / relación con el rol B. Pero, ¿qué sucede si queremos usar una tabla dinámica (por ejemplo, Ventas) que necesita mantener diferentes registros entre usuarioA y productoB? No he encontrado una manera directa de hacer esto.
Mi solución es tratar la tabla intermareal como un modelo real, luego establecer una relación uno a muchos con ambas tablas (ventas de usuarios y ventas de productos) y luego, si es necesario, relacionar este modelo intermedio con otros.
Entonces en tu caso, tendría 4 modelos claros:
- Jugador |
one-to-many
con la fiesta - Juego |
one-to-many
con la fiesta - Fiesta |
one-to-one
con Score |many-to-one
con Party |many-to-one
con el jugador - Puntuación |
one-to-one
con la fiesta
Con este enfoque, también tiene más control de las propiedades de cada modelo.