Как заставить уникальную проверку Laravel работать с входным массивом?

#php #laravel #laravel-validation

#php #laravel #laravel-проверка

Вопрос:

UpdateEntityRequest.php:

 'phones'          => 'sometimes|nullable|array',
'phones.*.id'     => 'sometimes|required|integer|distinct|exists:entity_phones,id,entity_id,'.$this->id,
'phones.*.number' => 'required|alpha_num|max:255|distinct|unique:entity_phones,number,'.$this->id.',entity_id',
  

таблица entity_phones:

 id, number, entity_id.
unique constraint: (number, entity_id)
  

EntityRepository.php:

 foreach ($attributes['phones'] as $phone) {
    if (isset($phone['id'])) {
        $entity->phones()->updateOrCreate([
            'id'         => $phone['id'],
            'entity_id'  => $entity->id
        ], $phone);
    } else {
        $entity->phones()->create($phone);
    }
}
  

С моей сущностью может быть связано больше, чем телефон, но не повторяющийся номер. Я намерен проверить уникальный (entity_id, номер) в UpdateEntityRequest.php итак:

  • Если объект phone поставляется без идентификатора, он должен проверить, что комбинация number, entity_id не существует. Но число может существовать с другим entity_id .
  • Если запрос приходит с идентификатором, он должен проверить, что комбинация number, entity_id не существует только в других идентификаторах, но игнорирует данный идентификатор.

У меня возникли проблемы с проверкой уникального правила Laravel только тогда, когда я хочу, чтобы оно выполняло проверку. Любые идеи, как я мог бы сделать это решение, будут оценены.

Ответ №1:

Если вам нужно игнорировать данный идентификатор во время проверки уникальности, попробуйте использовать класс Rule для плавного определения правила.

 use IlluminateValidationRule;

Validator::make($request_data, [
    'number' => [
        'required',
        'alpha_num', (...all your other rules)
        Rule::unique('entity_phones')->ignore($entity_id),
    ],
]);
  

Вы можете прочитать больше в документах laravel об уникальном правиле в параграфе: Принуждение уникального правила игнорировать заданный идентификатор.

Ответ №2:

В итоге я сделал это:

 $phoneIds = $this->input('phones.*.id');

'phones.*.number' =>
                    [
                        'required_with:phones',
                        'alpha_num',
                        'max:255',
                        'distinct',
                        Rule::unique('entity_phones', 'number')
                        ->where('entity_id', $this->id)
                        ->where(function ($query) use ($phoneIds) {
                            return $query->where('id', '!=', array_shift($phoneIds));
                        })
                    ],