setStatus($status); $booking->setAccommodation(new Accommodation()); $bookingRepository = $this->createStub(AccommodationBookingRepository::class); $bookingRepository->method('findOneBy')->willReturn($booking); $linkSigner = $this->createStub(AccommodationBookingLinkSigner::class); $linkSigner->method('isSessionAuthorized')->willReturn(true); $bookingService = $this->createMock(AccommodationBookingService::class); $bookingService->expects(self::never())->method('createOfferContext'); $controller = new TestableOfferViewController($bookingRepository, $linkSigner, $bookingService); $request = Request::create('/groups/booking/offer/'.$booking->getUuid().'/view'); $request->setSession(new Session(new MockArraySessionStorage())); $response = $controller->index($booking->getUuid(), $request); self::assertSame(Response::HTTP_OK, $response->getStatusCode()); self::assertSame('groups/offer/unavailable.html.twig', $controller->renderedView); } /** * @return iterable */ public static function statusesTheCustomerMustNotSee(): iterable { yield 'draft' => [AccommodationBookingStatus::Draft]; yield 'requested' => [AccommodationBookingStatus::Requested]; yield 'discarded' => [AccommodationBookingStatus::Discarded]; } public function testRendersOfferWhenSessionAuthorized(): void { $booking = new AccommodationBooking(); $booking->setStatus(AccommodationBookingStatus::Open); $booking->setAccommodation(new Accommodation()); $bookingRepository = $this->createMock(AccommodationBookingRepository::class); $bookingRepository->method('findOneBy')->with(['uuid' => $booking->getUuid()])->willReturn($booking); $linkSigner = $this->createStub(AccommodationBookingLinkSigner::class); $linkSigner->method('isSessionAuthorized')->willReturn(true); $ctx = new AccommodationBookingContext(accommodation: $booking->getAccommodation(), priceBreakdown: ['total' => 1000]); $bookingService = $this->createMock(AccommodationBookingService::class); $bookingService->method('createOfferContext')->with($booking, $booking->getAccommodation())->willReturn($ctx); $bookingService->expects(self::never())->method('acceptBooking'); $controller = new TestableOfferViewController($bookingRepository, $linkSigner, $bookingService); $request = Request::create('/groups/booking/offer/'.$booking->getUuid().'/view'); $request->setSession(new Session(new MockArraySessionStorage())); $response = $controller->index($booking->getUuid(), $request); self::assertSame(Response::HTTP_OK, $response->getStatusCode()); self::assertSame('groups/offer/view.html.twig', $controller->renderedView); self::assertSame($booking, $controller->renderedParameters['booking']); self::assertSame(['total' => 1000], $controller->renderedParameters['priceBreakdown']); self::assertSame($ctx, $controller->renderedParameters['ctx']); } public function testRendersUnavailableWhenSessionNotAuthorized(): void { $booking = new AccommodationBooking(); $bookingRepository = $this->createStub(AccommodationBookingRepository::class); $bookingRepository->method('findOneBy')->willReturn($booking); $linkSigner = $this->createStub(AccommodationBookingLinkSigner::class); $linkSigner->method('isSessionAuthorized')->willReturn(false); $controller = new TestableOfferViewController( $bookingRepository, $linkSigner, $this->createStub(AccommodationBookingService::class), ); $response = $controller->index($booking->getUuid(), Request::create('/groups/booking/offer/'.$booking->getUuid().'/view')); self::assertSame(Response::HTTP_OK, $response->getStatusCode()); self::assertSame('groups/offer/unavailable.html.twig', $controller->renderedView); } } final class TestableOfferViewController extends ViewController { public ?string $renderedView = null; /** @var array */ public array $renderedParameters = []; protected function render(string $view, array $parameters = [], ?Response $response = null): Response { $this->renderedView = $view; $this->renderedParameters = $parameters; return $response ?? new Response(''); } }