factory = $factory; } public function denormalize($data, string $type, ?string $format = null, array $context = []) { // some test about schema first... $this->performChecks($data); // route to "leave movement" (all concerned leave household) // or "move to another household" (all concerned go to another // household) if (null === $data['destination']) { return $this->denormalizeLeave($data, $type, $format, $context); } return $this->denormalizeMove($data, $type, $format, $context); } public function supportsDenormalization($data, string $type, ?string $format = null) { return MembersEditor::class === $type; } protected function denormalizeLeave($data, string $type, string $format, array $context = []) { $editor = $this->factory->createEditor(null); foreach ($data['concerned'] as $key => $concerned) { $person = $this->denormalizer->denormalize( $concerned['person'] ?? null, Person::class, $format, $context ); $startDate = $this->denormalizer->denormalize( $concerned['start_date'] ?? null, DateTimeImmutable::class, $format, $context ); if ( null === $person && null === $startDate ) { throw new Exception\InvalidArgumentException('position with ' . "key {$key} could not be denormalized: missing " . 'person or start_date.'); } $editor->leaveMovement($startDate, $person); } return $editor; } protected function denormalizeMove($data, string $type, string $format, array $context = []) { $householdContext = $context; $householdContext['groups'][] = 'create'; $household = $this->denormalizer->denormalize( $data['destination'], Household::class, $format, $householdContext ); if (null === $household) { throw new Exception\InvalidArgumentException('household could not be denormalized. Impossible to process'); } $editor = $this->factory->createEditor($household); foreach ($data['concerned'] as $key => $concerned) { $person = $this->denormalizer->denormalize( $concerned['person'] ?? null, Person::class, $format, $context ); $position = $this->denormalizer->denormalize( $concerned['position'] ?? null, Position::class, $format, $context ); $startDate = $this->denormalizer->denormalize( $concerned['start_date'] ?? null, DateTimeImmutable::class, $format, $context ); $holder = (bool) $concerned['holder'] ?? false; $comment = (string) $concerned['comment'] ?? false; if ( null === $person && null === $position && null === $startDate ) { throw new Exception\InvalidArgumentException('position with ' . "key {$key} could not be denormalized: missing " . 'person, position or start_date.'); } $editor->addMovement( $startDate, $person, $position, $holder, $comment ); } return $editor; } private function performChecks($data): void { if (null == $data['concerned'] ?? null && false === ยท\is_array('concerned')) { throw new Exception\UnexpectedValueException("The schema does not have any key 'concerned'"); } if (false === array_key_exists('destination', $data)) { throw new Exception\UnexpectedValueException("The schema does not have any key 'destination'"); } } }