feat: make email optional for under-16 participants except applicant

This commit is contained in:
fromme committed 2026-10-19 09:18:22 +02:00
1 parent b958d1a371
commit 1d9c852113
18 files changed
+435 -336

No files matched your search

+91
View File
@@ -429,6 +429,97 @@ class BookingDtoTest extends TestCase
$this->assertSame(['participants[0].address'], $this->collectFirstParticipantAddressPaths($dto));
}
public function testChildApplicantWithoutEmailIsReportedOnce(): void
{
$dto = $this->createCreateModeDto();
$dto->participants[0] = $this->createParticipantWithoutEmail(10);
$this->assertSame(
['participants[0].email'],
$this->collectFirstParticipantEmailPaths($dto),
'The applicant is the booking contact and needs an email at any age'
);
}
public function testChildAtIndexZeroOfASplitBookingMayLeaveTheEmailBlank(): void
{
$dto = $this->createCreateModeDto();
$dto->applicantTravels = false;
$dto->participants[0] = $this->createParticipantWithoutEmail(10);
$this->assertSame([], $this->collectFirstParticipantEmailPaths($dto));
}
public function testAdultAtIndexZeroOfASplitBookingStillNeedsAnEmail(): void
{
$dto = $this->createCreateModeDto();
$dto->applicantTravels = false;
$dto->participants[0] = $this->createParticipantWithoutEmail(30);
$this->assertSame(['participants[0].email'], $this->collectFirstParticipantEmailPaths($dto));
}
public function testApplicantEmailComesFromParticipantZeroWhenTheApplicantTravels(): void
{
$dto = $this->createCreateModeDto();
$dto->participants[0]->email = ' [email protected] ';
$dto->applicant = new ParticipantDto();
$dto->applicant->email = '[email protected]';
$this->assertSame('[email protected]', $dto->getApplicantEmail());
}
public function testApplicantEmailComesFromTheApplicantBlockOnACreateModeSplit(): void
{
$dto = $this->createCreateModeDto();
$dto->participants[0]->email = '[email protected]';
$dto->applicantTravels = false;
$dto->applicant = new ParticipantDto();
$dto->applicant->email = '[email protected]';
$this->assertSame('[email protected]', $dto->getApplicantEmail());
}
public function testApplicantEmailComesFromTheAnmelderOnAnEditModeSplit(): void
{
$dto = $this->createEditModeDto(100, 200);
$dto->participants[0]->email = '[email protected]';
$dto->booking->applicant->communication->email = '[email protected]';
$this->assertSame('[email protected]', $dto->getApplicantEmail());
}
/**
* Ages relative to today, since isChild() measures against the current date.
*/
private function createParticipantWithoutEmail(int $years): ParticipantDto
{
$participant = new ParticipantDto();
$participant->index = 0;
$participant->dateOfBirth = (new \DateTimeImmutable('today'))->modify(sprintf('-%d years', $years));
$participant->address = $this->createAddress();
return $participant;
}
/**
* @return list<string>
*/
private function collectFirstParticipantEmailPaths(BookingDto $dto): array
{
$validator = Validation::createValidatorBuilder()->enableAttributeMapping()->getValidator();
$violations = $validator->validate($dto, null, ['booking_create', 'strict_required']);
$paths = [];
foreach ($violations as $violation) {
if ('participants[0].email' === $violation->getPropertyPath()) {
$paths[] = $violation->getPropertyPath();
}
}
return $paths;
}
/**
* @return list<string>
*/