fix: correct edit reload dirty-state
This commit is contained in:
@@ -5,6 +5,7 @@ declare(strict_types=1);
|
||||
namespace App\Tests\Controller\Booking\Edit;
|
||||
|
||||
use App\BusProNet\Model\Booking;
|
||||
use App\BusProNet\Model\Service;
|
||||
use App\BusProNet\Model\Travel;
|
||||
use App\BusProNet\XmlLoader\AgencyLoader;
|
||||
use App\Controller\Booking\Edit\IndexController;
|
||||
@@ -68,6 +69,8 @@ class IndexControllerTest extends TestCase
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(true);
|
||||
$fingerprintService->expects($this->never())
|
||||
->method('generateFingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
@@ -151,6 +154,10 @@ class IndexControllerTest extends TestCase
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(false);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('generateFingerprint')
|
||||
->with($bookingDto)
|
||||
->willReturn('normalized-fingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
@@ -225,8 +232,12 @@ class IndexControllerTest extends TestCase
|
||||
->willReturn(false);
|
||||
|
||||
$fingerprintService = $this->createMock(BookingChangeTracker::class);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(true);
|
||||
$fingerprintService->expects($this->never())
|
||||
->method('isDirty');
|
||||
->method('generateFingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
@@ -310,10 +321,14 @@ class IndexControllerTest extends TestCase
|
||||
->willReturn(false);
|
||||
|
||||
$fingerprintService = $this->createMock(BookingChangeTracker::class);
|
||||
$fingerprintService->expects($this->once())
|
||||
$fingerprintService->expects($this->exactly(2))
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(false);
|
||||
->willReturnOnConsecutiveCalls(false, false);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('generateFingerprint')
|
||||
->with($bookingDto)
|
||||
->willReturn('normalized-fingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
@@ -365,6 +380,184 @@ class IndexControllerTest extends TestCase
|
||||
$this->assertSame([0 => ['E-Mail']], $controller->renderParameters['bookingEditContext']->missingValueLabelsByParticipantIndex);
|
||||
}
|
||||
|
||||
public function testIndexTreatsDefaultPreselectionOnCleanDtoAsBaselineState(): void
|
||||
{
|
||||
$request = Request::create('/bookings/42/edit', 'GET');
|
||||
$user = $this->createUser();
|
||||
$bookingDto = $this->createBookingDto();
|
||||
$bookingDto->originalFingerprint = 'api-fingerprint';
|
||||
$bookingDto->participants = [$this->createParticipant()];
|
||||
$bookingData = $this->createBooking();
|
||||
|
||||
$form = $this->createMock(FormInterface::class);
|
||||
$form->method('isSubmitted')->willReturn(false);
|
||||
|
||||
$fingerprintService = $this->createMock(BookingChangeTracker::class);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(false);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('generateFingerprint')
|
||||
->with($bookingDto)
|
||||
->willReturn('normalized-fingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('loadFormData')
|
||||
->with($request, 42, $user)
|
||||
->willReturn($bookingDto);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('fetchBookingData')
|
||||
->with(42, $user)
|
||||
->willReturn($bookingData);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('isDraftRestored')
|
||||
->willReturn(false);
|
||||
|
||||
$preselectedService = $this->createService(1001);
|
||||
$bookingConfigurator = $this->createMock(BookingConfigurator::class);
|
||||
$bookingConfigurator->expects($this->once())
|
||||
->method('preselectDefaultServices')
|
||||
->with($bookingDto)
|
||||
->willReturnCallback(static function (BookingDto $dto) use ($preselectedService): void {
|
||||
$dto->participants[0]->additionalServices[] = $preselectedService;
|
||||
});
|
||||
|
||||
$contextFactory = $this->createMock(BookingEditContextFactory::class);
|
||||
$contextFactory->expects($this->once())
|
||||
->method('createOverviewContext')
|
||||
->with($bookingDto, $bookingData, false, false, false, [])
|
||||
->willReturn($this->createOverviewContext($bookingDto, $bookingData, false, false, false));
|
||||
|
||||
$controller = new TestableIndexController(
|
||||
$dataLoader,
|
||||
$this->createMock(BookingEditDraftManager::class),
|
||||
$this->createMock(BookingSessionManager::class),
|
||||
$fingerprintService,
|
||||
$bookingConfigurator,
|
||||
$contextFactory,
|
||||
$this->createPreflightChecker($bookingDto),
|
||||
$this->createMock(BookingEditSubmitter::class),
|
||||
$user,
|
||||
$form,
|
||||
);
|
||||
|
||||
$response = $controller->index(42, $request);
|
||||
|
||||
$this->assertInstanceOf(Response::class, $response);
|
||||
$this->assertSame('normalized-fingerprint', $bookingDto->originalFingerprint);
|
||||
$this->assertFalse($controller->renderParameters['bookingEditContext']->isDirty);
|
||||
}
|
||||
|
||||
public function testIndexKeepsDirtyStateWhenDtoWasDirtyBeforeDefaultPreselection(): void
|
||||
{
|
||||
$request = Request::create('/bookings/42/edit', 'GET');
|
||||
$user = $this->createUser();
|
||||
$bookingDto = $this->createBookingDto();
|
||||
$bookingDto->originalFingerprint = 'api-fingerprint';
|
||||
$bookingDto->participants = [$this->createParticipant()];
|
||||
$bookingData = $this->createBooking();
|
||||
|
||||
$form = $this->createMock(FormInterface::class);
|
||||
$form->method('isSubmitted')->willReturn(false);
|
||||
|
||||
$fingerprintService = $this->createMock(BookingChangeTracker::class);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(true);
|
||||
$fingerprintService->expects($this->never())
|
||||
->method('generateFingerprint');
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('loadFormData')
|
||||
->with($request, 42, $user)
|
||||
->willReturn($bookingDto);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('fetchBookingData')
|
||||
->with(42, $user)
|
||||
->willReturn($bookingData);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('isDraftRestored')
|
||||
->willReturn(false);
|
||||
|
||||
$preselectedService = $this->createService(1001);
|
||||
$bookingConfigurator = $this->createMock(BookingConfigurator::class);
|
||||
$bookingConfigurator->expects($this->once())
|
||||
->method('preselectDefaultServices')
|
||||
->with($bookingDto)
|
||||
->willReturnCallback(static function (BookingDto $dto) use ($preselectedService): void {
|
||||
$dto->participants[0]->additionalServices[] = $preselectedService;
|
||||
});
|
||||
|
||||
$contextFactory = $this->createMock(BookingEditContextFactory::class);
|
||||
$contextFactory->expects($this->once())
|
||||
->method('createOverviewContext')
|
||||
->with($bookingDto, $bookingData, true, false, false, [])
|
||||
->willReturn($this->createOverviewContext($bookingDto, $bookingData, true, false, false));
|
||||
|
||||
$controller = new TestableIndexController(
|
||||
$dataLoader,
|
||||
$this->createMock(BookingEditDraftManager::class),
|
||||
$this->createMock(BookingSessionManager::class),
|
||||
$fingerprintService,
|
||||
$bookingConfigurator,
|
||||
$contextFactory,
|
||||
$this->createPreflightChecker($bookingDto),
|
||||
$this->createMock(BookingEditSubmitter::class),
|
||||
$user,
|
||||
$form,
|
||||
);
|
||||
|
||||
$response = $controller->index(42, $request);
|
||||
|
||||
$this->assertInstanceOf(Response::class, $response);
|
||||
$this->assertSame('api-fingerprint', $bookingDto->originalFingerprint);
|
||||
$this->assertTrue($controller->renderParameters['bookingEditContext']->isDirty);
|
||||
}
|
||||
|
||||
public function testReloadFromApiClearsSessionDeletesDraftInvalidatesCacheAndRedirectsToEdit(): void
|
||||
{
|
||||
$request = Request::create('/bookings/42/edit/reload', 'POST');
|
||||
$user = $this->createUser();
|
||||
|
||||
$bookingSessionService = $this->createMock(BookingSessionManager::class);
|
||||
$bookingSessionService->expects($this->once())
|
||||
->method('clearBookingDto')
|
||||
->with($request, BookingDto::MODE_EDIT);
|
||||
|
||||
$draftService = $this->createMock(BookingEditDraftManager::class);
|
||||
$draftService->expects($this->once())
|
||||
->method('deleteDraft')
|
||||
->with($user, 42);
|
||||
|
||||
$dataLoader = $this->createMock(BookingEditDataLoader::class);
|
||||
$dataLoader->expects($this->once())
|
||||
->method('invalidateBookingCache')
|
||||
->with(42, $user);
|
||||
|
||||
$controller = new TestableIndexController(
|
||||
$dataLoader,
|
||||
$draftService,
|
||||
$bookingSessionService,
|
||||
$this->createMock(BookingChangeTracker::class),
|
||||
$this->createMock(BookingConfigurator::class),
|
||||
$this->createMock(BookingEditContextFactory::class),
|
||||
$this->createMock(BookingEditPreFlightChecker::class),
|
||||
$this->createMock(BookingEditSubmitter::class),
|
||||
$user,
|
||||
$this->createMock(FormInterface::class),
|
||||
);
|
||||
|
||||
$response = $controller->reloadFromApi(42, $request);
|
||||
|
||||
$this->assertInstanceOf(RedirectResponse::class, $response);
|
||||
$this->assertSame('/bookings/42/edit', $response->headers->get('Location'));
|
||||
$this->assertSame([['success', 'Änderungen verworfen, Daten neu geladen']], $controller->flashes);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dataProvider submissionResultProvider
|
||||
*
|
||||
@@ -448,6 +641,25 @@ class IndexControllerTest extends TestCase
|
||||
return new \App\Form\Model\ParticipantDto();
|
||||
}
|
||||
|
||||
private function createService(int $id): Service
|
||||
{
|
||||
$service = new Service();
|
||||
$service->id = $id;
|
||||
|
||||
return $service;
|
||||
}
|
||||
|
||||
private function createPreflightChecker(BookingDto $bookingDto): BookingEditPreFlightChecker
|
||||
{
|
||||
$preflightChecker = $this->createMock(BookingEditPreFlightChecker::class);
|
||||
$preflightChecker->expects($this->once())
|
||||
->method('findMissingValueLabelsByParticipantIndex')
|
||||
->with($bookingDto)
|
||||
->willReturn([]);
|
||||
|
||||
return $preflightChecker;
|
||||
}
|
||||
|
||||
private function createOverviewContext(
|
||||
BookingDto $bookingDto,
|
||||
Booking $bookingData,
|
||||
@@ -499,8 +711,12 @@ class IndexControllerTest extends TestCase
|
||||
$bookingData = $this->createBooking();
|
||||
$form = $this->createMock(FormInterface::class);
|
||||
$fingerprintService = $this->createMock(BookingChangeTracker::class);
|
||||
$fingerprintService->expects($this->once())
|
||||
->method('isDirty')
|
||||
->with($bookingDto)
|
||||
->willReturn(true);
|
||||
$fingerprintService->expects($this->never())
|
||||
->method('isDirty');
|
||||
->method('generateFingerprint');
|
||||
|
||||
$form->expects($this->once())
|
||||
->method('handleRequest')
|
||||
|
||||
Reference in New Issue
Block a user