repository = new InMemoryPeriodConfigurationRepository(); } #[Test] public function itReturnsNullWhenNoPeriodsConfigured(): void { $handler = $this->createHandler('2025-10-15'); $result = $handler(new GetPeriodsQuery(self::TENANT_ID, self::ACADEMIC_YEAR_ID)); self::assertNull($result); } #[Test] public function itReturnsPeriodsWithCurrentPeriodInfo(): void { $this->seedTrimesterConfig(); $handler = $this->createHandler('2025-10-15'); $result = $handler(new GetPeriodsQuery(self::TENANT_ID, self::ACADEMIC_YEAR_ID)); self::assertNotNull($result); self::assertSame('trimester', $result->type); self::assertCount(3, $result->periods); // T1 is current self::assertNotNull($result->currentPeriod); self::assertSame('T1', $result->currentPeriod->label); self::assertTrue($result->currentPeriod->isCurrent); self::assertSame(46, $result->currentPeriod->daysRemaining); } #[Test] public function itReturnsNullCurrentPeriodWhenOutOfRange(): void { $this->seedTrimesterConfig(); $handler = $this->createHandler('2025-08-15'); $result = $handler(new GetPeriodsQuery(self::TENANT_ID, self::ACADEMIC_YEAR_ID)); self::assertNotNull($result); self::assertNull($result->currentPeriod); } #[Test] public function itMarksPastPeriods(): void { $this->seedTrimesterConfig(); $handler = $this->createHandler('2026-04-15'); $result = $handler(new GetPeriodsQuery(self::TENANT_ID, self::ACADEMIC_YEAR_ID)); self::assertNotNull($result); self::assertTrue($result->periods[0]->isPast); self::assertTrue($result->periods[1]->isPast); self::assertFalse($result->periods[2]->isPast); } private function seedTrimesterConfig(): void { $config = DefaultPeriods::forType(PeriodType::TRIMESTER, 2025); $this->repository->save( TenantId::fromString(self::TENANT_ID), AcademicYearId::fromString(self::ACADEMIC_YEAR_ID), $config, ); } private function createHandler(string $dateString): GetPeriodsHandler { $clock = new class($dateString) implements Clock { public function __construct(private readonly string $dateString) { } public function now(): DateTimeImmutable { return new DateTimeImmutable($this->dateString); } }; return new GetPeriodsHandler($this->repository, $clock); } }