LoginSignup
0
1

More than 5 years have passed since last update.

PHP Mockey 特定のオブジェクトが引数として渡されたときの戻り値を切り替える方法

Posted at

動作環境

PHP 7.2
PHPUnit 6.5.14
Mockery 1.2.2

やりたいこと

Mockeryでモック化したUserRepositoryクラスのメソッドisExistの動作を引数によって切り替えたい

isExistメソッドの役割:指定されたユーザIDが存在している場合 true 存在していない場合 false を返す

コード


interface UserRepository
{
    /**
     * @param UserId $userId
     * @return bool true:ユーザが存在する false:ユーザが存在しない
     */
    public function isExist(UserId $userId): bool;
}

class UserId
{
    /**
     * @var int
     */
    protected $id;
    /**
     * UserId constructor.
     * @param int $id
     */
    public function __construct(int $id)
    {
        $this->id = $id;
    }

    /**
     * @return int
     */
    public function getId(): int
    {
        return $this->id;
    }
}

//~~~~~~~~~ 以下テストケース内

$mockUserRepository = \Mockery::mock(UserRepository::class);

$mockUserRepository->shouldReceive('isExist')
            ->byDefault()
            ->andReturn(true);

$mockUserRepository->shouldReceive('isExist')
            ->with(\Mockery::on(function (UserId $userId) {
                if ($userId->getId() === 999) { //ユーザIDが 999 の場合に andReturn に指定された値を返却する
                    return true;
                }
                return false;
            }))
            ->andReturn(false);


$this->assertTrue($this->mockUserRepository->isExist(new UserId(1))); // OK
$this->assertFalse($this->mockUserRepository->isExist(new UserId(999))); // OK

ポイント

Mockeryのwithメソッドは通常値を設定するだけで、動作を切り替えたりできますが、
今回のように「オブジェクトが引数」となる場合はだたwithを使うだけだと想定どおりに動作してくれません。

誤りのケース
$mockUserRepository->shouldReceive('isExist')
            ->byDefault()
            ->andReturn(true);
$mockUserRepository->shouldReceive('isExist')
            ->with(new UserId(999)) // new UserId(999) === new UserId(999) → false
            ->andReturn(false);

$this->assertTrue($this->mockUserRepository->isExist(new UserId(1))); // OK
$this->assertFalse($this->mockUserRepository->isExist(new UserId(999))); // NG defaultのほうが呼ばれてしまっている
0
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1