Я большой поклонник функциональности Laravel Cache::remember
, и я использую ее в своих классах обслуживания следующим образом:
/**
* SummaryService
*/
public function getSummaryData(string $userId)
{
$summaryCacheKey = $userId . '_summary_cache';
$summaryCacheLifespanMinutes = config('summary_cache_lifespan_minutes');
return Cache::remember($summaryCacheKey, $summaryCacheLifespanMinutes, function () use ($userId) {
$summaryResult = [
'userExists' => false,
'data' => [],
];
$user = $this->userRepository->findById($userId);
if ($user) {
$summaryResult = [
'userExists' => true,
'data' => $this->summaryRepository->getSummaryByUserId($user->id),
];
}
return $summaryResult;
});
}
Это работает как ожидалось. Если данные присутствуют в кэше, они возвращаются, а если нет, загружаются, кэшируются и возвращаются.
Теперь я пытаюсь выполнить модульное тестирование моего SummaryService
(оба пути выполнения).
Первая часть, где данные возвращаются через кеш, легко тестируется и выглядит следующим образом:
public function i_can_load_summary_data_via_cache()
{
// given
$userId = 'aaaa45-bbbb-cccc-ddddssswwwdw';
$expectedResult = [
'userExists' => true,
'data' => [ ... ],
];
$summaryCacheKey = $userId . '_summary_cache';
$summaryCacheLifespanMinutes = config('summary_cache_lifespan_minutes');
Cache::shouldReceive('remember')
->once()
->with($summaryCacheKey, $summaryCacheLifespanMinutes, Closure::class)
->andReturn($expectedResult);
// when
$result = $this->summaryService->getSummaryData($userId);
// then
$this->assertSame($expectedResult, $result);
}
Однако, когда я пытаюсь протестировать сценарий, в котором данные отсутствуют в кеше, и я должен загрузить их (через смоделированные репозитории) примерно так:
public function i_can_load_summary_data_via_database()
{
// given
$userId = 'aaaa45-bbbb-cccc-ddddssswwwdw';
$expectedResult = [
'userExists' => true,
'data' => [ ... ],
];
$user = new User();
$user->id = $userId;
$summaryCacheKey = $userId . '_summary_cache';
$summaryCacheLifespanMinutes = 0;
Cache::shouldReceive('remember')
->once()
->with($summaryCacheKey, $summaryCacheLifespanMinutes, \Mockery::on(function() use($user) {
$this->mockedUserRepository
->shouldReceive('findById')
->once()
->andReturn($user);
$this->mockedSummaryRepository
->shouldReceive('getSummaryByUserId')
->once()
->with($user->id)
->andReturn([ ... ]);
}))
->andReturn($expectedResult);
// when
$result = $this->summaryService->getSummaryData($userId);
// then
$this->assertSame($expectedResult, $result);
}
Тест не пройден:
Не найдено подходящего обработчика для
Mockery_3_Illuminate_Cache_CacheManager :: запомнить ('aaaa45-bbbb-cccc-ddddssswwwdw_summary_cache', '10', объект (закрытие)). Либо метод был неожиданным, либо его
для этого метода не найдено ни одного ожидаемого списка аргументов
Объекты: (массив ('Закрытие' => массив (
'class' => 'Закрытие',
'свойства' =>
массив (
),),))
Есть идеи, как правильно это проверить?