Laravel:hasMany 关系为空/空

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/35306974/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 13:12:48  来源:igfitidea点击:

Laravel: hasMany Relationship is null / empty

phplaraveleloquentrelationshiplaravel-5.2

提问by festie

my problem is, that my hasMany relationship returns just an "empty" collection:

我的问题是,我的 hasMany 关系只返回一个“空”集合:

Collection {#172 ▼
  #items: array:1 [▼
    0 => 0
  ]
}

My belongsTo relationship just returns "null".

我的belongsTo 关系只返回“null”。

Here are the eloquents: Game.php

以下是口才:Game.php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

/**
 * App\Models\Game
 *
 * @property integer $id
 * @property integer $steamid
 * @property string $name
 * @property \Carbon\Carbon $created_at
 * @property \Carbon\Carbon $updated_at
 */
class Game extends Model
{
    protected $fillable = [
        'appid', 'name'
    ];

    public function keys()
    {
        $this->hasMany('App\Models\Game\Key', 'id', 'game_id');
    }
}

Key.php
<?php

namespace App\Models\Game;

use Illuminate\Database\Eloquent\Model;

/**
 * App\Models\Game\Key
 *
 */
class Key extends Model
{
    protected $fillable = [
        'key', 'game_id', 'author_id',
    ];

    public static function getRandom()
    {
        if (!self::available()) return false;
        $keys = Key::where('redeemer_id', 0)->get();
        $key = $keys[ rand(0, count($keys) - 1) ];
        return $key;
    }

    public static function available()
    {
        $keys = Key::where('redeemer_id', 0)->get();
        $count = count($keys);
        if ($count > 0) return $count;
        return false;
    }

    public function author()
    {
        $this->hasOne('App\Models\User', 'author_id');
    }

    public function redeemer()
    {
        $this->hasOne('App\Models\User', 'redeemer_id');
    }

    public function game()
    {
        $this->belongsTo('App\Models\Game', 'game_id');
    }
}

User.php
<?php

namespace App\Models;

use Carbon\Carbon;
use Illuminate\Foundation\Auth\User as Authenticatable;

/**
 * App\Models\User
 *
 * @property integer $id
 * @property string $name
 * @property string $email
 * @property string $password
 * @property string $remember_token
 * @property \Carbon\Carbon $created_at
 * @property \Carbon\Carbon $updated_at
 */
class User extends Authenticatable
{
    protected $fillable = [
        'username', 'email', 'password'
    ];

    protected $hidden = [
        'password', 'remember_token',
    ];

    public function keys()
    {
        $this->hasMany('App\Models\Game\Key');
    }

    public function canRedeem()
    {
        // TODO: not tested yet
        if(count(self::keys()) == 0) return true;
        if(Carbon::now(-24) > self::keys()->first()->created_at) return true;
            return false;
    }
}

these are my migrations:

这些是我的迁移:

user-table
<?php

use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;

class CreateUsersTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('users', function (Blueprint $table) {
            $table->increments('id');
            $table->string('username')->unique();
            $table->string('email')->unique();
            $table->string('password', 60);
            $table->rememberToken();
            $table->timestamps();
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::drop('users');
    }
}

game-table
<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;

class CreateGamesTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        if (!Schema::hasTable('games')) {
            Schema::create('games', function (Blueprint $table) {
                $table->increments('id');

                $table->integer('appid')->unsigned();
                $table->string('name');

                $table->timestamps();
            });
        }
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        //Schema::drop('games');
    }
}

keys-table
<?php

use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;

class CreateKeysTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('keys', function(Blueprint $table) {
            $table->increments('id');

            $table->string('key');

            $table->integer('game_id')->unsigned()->index();
            $table->foreign('game_id')->references('id')->on('games')->onDelete('cascade');

            $table->integer('author_id')->unsigned()->index();
            $table->integer('redeemer_id')->unsigned()->index();

            $table->timestamps();


        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::drop('keys');
    }
}

I googled alot and I found some "solutions" on Laracast, but they only tell me what I already have.

我在 google 上搜索了很多,我在 Laracast 上找到了一些“解决方案”,但他们只告诉我我已经拥有的东西。

Can anyone help? Deazl

任何人都可以帮忙吗?迪兹尔

回答by James Okpe George

The method that creates the relationship has to return a value, this is what I am saying:

创建关系的方法必须返回一个值,这就是我要说的:

Rather than:

而不是:

public function keys()
{
    $this->hasMany('App\Models\Game\Key', 'id', 'game_id');
}

You should have:

你应该有:

public function keys()
{
    return $this->hasMany('App\Models\Game\Key', 'id', 'game_id');
}

The difference is the return statement, your methods that create the relationship do not return any, they should return the results of the hasOneand hasManyfor all method that uses them for query building.

所不同的是return语句,你的方法是创建关系不返回任何,他们应该返回的结果hasOne,并hasMany为所有的方法使用它们查询的建筑。

PS: You should add the return statement for the other methods that create a relationship.

PS:您应该为其他创建关系的方法添加 return 语句。

回答by Can Celik

If you have extra columns in your intermediate table you need to include them when defining your relation.

如果中间表中有额外的列,则需要在定义关系时包含它们。

public function keys()
{
    $this->hasMany('App\Models\Game\Key')->withPivot('author_id','redeemer_id')->withTimestamps();

}