Метод travelTo
Метод travelTo предоставляется Laravel для управления временем в тестовой среде. Он позволяет установить конкретную дату и время, которые будут использоваться как текущие в рамках теста. Метод принимает экземпляр DateTimeInterface, строку с датой или целое число, представляющее временную метку. После вызова метода все операции, связанные со временем (например, now, today, фабрики с временными метками), будут использовать указанное время. Метод полезен для тестирования отложенных задач, скидок, сроков действия и других временных зависимостей.
Важно отметить, что travelTo автоматически сбрасывает время после выполнения теста, если используется с трейтом InteractsWithTime. Однако, если трейт не используется, рекомендуется вызывать метод travelBack для возврата к реальному времени. Метод доступен только в контексте тестов.
Синтаксис
<?php
// Установка даты с помощью строки
$this->travelTo('2025-01-01');
// Установка даты с помощью объекта Carbon
use Carbon\Carbon;
$date = Carbon::create(2025, 1, 1, 12, 0, 0);
$this->travelTo($date);
// Установка даты с помощью временной метки
$this->travelTo(1735689600);
?>
Пример
Рассмотрим простой пример использования метода travelTo для проверки функциональности, возвращающей текущую дату в зависимости от времени:
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Article extends Model
{
public function isPublishedToday()
{
// Проверяем, опубликована ли статья сегодня
return $this->published_at && $this->published_at->isToday();
}
}
?>
<?php
namespace Tests\Unit;
use Tests\TestCase;
use App\Models\Article;
use Carbon\Carbon;
class ArticleTest extends TestCase
{
public function testIsPublishedToday()
{
// Устанавливаем время на 2025-01-01 10:00:00
$this->travelTo('2025-01-01 10:00:00');
// Создаем статью с датой публикации 2025-01-01
$article = new Article();
$article->published_at = Carbon::create(2025, 1, 1, 12, 0, 0);
// Проверяем, что статья опубликована сегодня
$res = $article->isPublishedToday();
$this->assertTrue($res);
// Возвращаем реальное время
$this->travelBack();
}
}
?>
Результат выполнения кода:
"Test passed"
Пример
Теперь рассмотрим более сложный пример тестирования кэширования данных с учетом времени. Предположим, есть метод, который возвращает данные с кэшированием на один час:
<?php
namespace App\Http\Controllers;
use Illuminate\Support\Facades\Cache;
class ReportController extends Controller
{
public function getReport()
{
// Кэшируем отчет на 1 час
return Cache::remember('report', 3600, function () {
return ['data' => 'report data', 'generated_at' => now()->toDateTimeString()];
});
}
}
?>
<?php
namespace Tests\Feature;
use Tests\TestCase;
use Illuminate\Support\Facades\Cache;
class ReportTest extends TestCase
{
public function testReportCacheExpiration()
{
// Устанавливаем начальное время
$this->travelTo('2025-01-01 10:00:00');
// Получаем отчет
$response = $this->get('/report');
$res1 = $response->json();
// Перемещаемся на 30 минут вперед (время еще не истекло)
$this->travelTo('2025-01-01 10:30:00');
// Получаем отчет снова (должен быть из кэша)
$response = $this->get('/report');
$res2 = $response->json();
// Проверяем, что данные совпадают (кэш работает)
$this->assertEquals($res1, $res2);
// Перемещаемся еще на 31 минуту (время истекло)
$this->travelTo('2025-01-01 11:01:00');
// Получаем отчет снова (должен быть новый)
$response = $this->get('/report');
$res3 = $response->json();
// Проверяем, что данные изменились (кэш обновился)
$this->assertNotEquals($res1, $res3);
// Возвращаем реальное время
$this->travelBack();
}
}
?>
Результат выполнения кода:
"Test passed"
Смотрите также
-
метод
travel,
который перемещает время на указанное количество часов/минут -
метод
freezeTime,
который фиксирует текущее время и останавливает его -
класс
TestCase,
базовый класс для всех тестов Laravel -
метод
setUp,
который выполняется перед каждым тестом