La validation est une fonctionnalité des modèles Laravel Eloquent qui garantit que les modèles répondent à leurs critères de validation avant d'être enregistrés. S'ils ne sont pas considérés comme valides, le modèle ne sera pas enregistré et les erreurs de validation seront mises à disposition.
La validation permet plusieurs ensembles de règles, en injectant l'ID de modèle dans des règles de validation unique
et en déclenchant des exceptions en cas d'échec des validations. Il est petit et flexible pour s'adapter parfaitement à votre flux de travail et vous aider à enregistrer uniquement les données valides.
Vous cherchez à utiliser la validation sur Laravel 4.2+ ? Jetez un œil à la branche 0.10.x pour la documentation et les instructions d'installation.
La version Laravel 4.2 est mieux adaptée à la validation de formulaires ; il prend en charge les messages de validation personnalisés, les règles de confirmation et plusieurs ensembles de règles. Parce que Laravel 5.0 a la validation FormRequest
la validation est désormais conçue pour garder vos données de base valides et laisser la validation du formulaire au framework.
Vous cherchez à utiliser la validation sur Laravel 5.0 à 5.2 ? Jetez un œil à la branche 2.x pour la documentation et les instructions d'installation.
La version Laravel 5.0 - 5.2 utilisait un contrat ValidationException
obsolète depuis, du framework Laravel. Pour Laravel 5.3, nous étendons maintenant la validation principale ValidationException
, ce qui signifie que le framework sera automatiquement redirigé avec des erreurs lorsqu'une erreur de validation se produit, un peu comme le ferait un FormRequest
.
Continuez à lire – ces instructions sont pour vous !
Accédez simplement au répertoire de votre projet où se trouve le fichier composer.json
et tapez :
le compositeur nécessite Watson/validation
Consultez les instructions d'installation pour Laravel 4.2+. Consultez les instructions d'installation pour Laravel 5.0 - 5.2.
Tout d’abord, ajoutez le trait à votre modèle et ajoutez vos règles et messages de validation si nécessaire.
utiliser WatsonValidatingValidatingTrait ; la classe Post étend Eloquent { utilisez ValidatingTrait ; protected $rules = [ 'title' => 'obligatoire', 'slug' => 'obligatoire|unique:posts,slug', 'content' => 'obligatoire' ]; }
Vous pouvez également ajouter le trait à un BaseModel
si vous en utilisez un et cela fonctionnera sur tous les modèles qui en découlent, sinon vous pouvez simplement étendre WatsonValidatingValidatingModel
au lieu de Eloquent
.
Remarque : vous devrez définir la propriété $rules
sur tous les modèles qui s'étendent à partir d'un BaseModel
qui utilise le trait, ou autrement définir un tableau vide comme $rules
pour le BaseModel
. Si vous ne le faites pas, vous vous retrouverez inévitablement avec LogicException with message 'Relationship method must return an object of type IlluminateDatabaseEloquentRelationsRelation'
.
Désormais, vous avez accès à des fonctionnalités agréables.
// Vérifiez si le modèle est valide ou non.$post->isValid(); // true// Ou vérifiez s'il est invalide ou non.$post->isInvalid(); // false// Une fois que vous avez déterminé la validité du modèle, // vous pouvez obtenir les erreurs.$post->getErrors(); // erreurs MessageBag
La validation du modèle devient également très simple.
if ( ! $post->save()) {// Oups.return redirect()->route('posts.create') ->withErrors($post->getErrors()) ->withInput(); }return redirect()->route('posts.show', $post->id) ->withSuccess("Votre message a été enregistré avec succès.");
Sinon, si vous préférez utiliser des exceptions lors de la validation des modèles, vous pouvez utiliser la méthode saveOrFail()
. Désormais, une exception sera générée lorsque vous tenterez d'enregistrer un modèle non valide.
$post->saveOrFail();
Vous n'avez pas besoin d'intercepter l'exception si vous ne le souhaitez pas. Laravel sait comment gérer une ValidationException
et redirigera automatiquement avec la saisie du formulaire et les erreurs. Si vous voulez vous en occuper vous-même, vous pouvez le faire.
essayez {$post->saveOrFail(); } catch (WatsonValidatingValidationException $e) {$errors = $e->getErrors();return redirect()->route('posts.create') ->avecErreurs($erreurs) ->withInput(); }
Notez que vous pouvez simplement transmettre l'exception à la méthode withErrors()
comme withErrors($e)
et Laravel saura comment la gérer.
Si vous utilisez le modèle et que vous souhaitez effectuer une sauvegarde qui contourne la validation, vous le pouvez. Cela renverra le même résultat que si vous appeliez save()
sur un modèle sans le trait.
$post->forceSave();
Si vous préférez que les exceptions soient levées par défaut lors de l'utilisation de la méthode save()
au lieu d'avoir à utiliser saveOrFail()
vous pouvez simplement définir la propriété suivante sur votre modèle ou BaseModel
.
/** * Indique si le modèle doit lever une ValidationException s'il * échoue à la validation. S’il n’est pas défini, la valeur par défaut est false. * * @var boolean */protected $throwValidationExceptions = true;
Si vous souhaitez effectuer une sauvegarde ponctuelle à l'aide d'exceptions ou de valeurs de retour, vous pouvez utiliser les méthodes saveOrFail()
et saveOrReturn
.
Pour afficher des messages d'erreur de validation personnalisés, ajoutez simplement la propriété $validationMessages
à votre modèle.
/** * Messages de validation à transmettre au validateur. * * @var array */protected $validationMessages = ['slug.unique' => "Un autre article utilise déjà ce slug."];
Vous avez peut-être remarqué que nous utilisons la règle unique
sur le slug, qui ne fonctionnerait pas si nous mettions à jour un modèle persistant. Heureusement, Validation s'en chargera pour vous et ajoutera la clé primaire du modèle à la règle afin que la règle fonctionne comme prévu ; ignorant le modèle actuel.
Vous pouvez ajuster cette fonctionnalité en définissant la propriété $injectUniqueIdentifier
sur votre modèle.
/** * Indique si le modèle doit injecter son identifiant dans les * règles de validation uniques avant de tenter la validation. Si cette propriété * n'est pas définie dans le modèle, elle sera par défaut vraie. * * @var boolean */protected $injectUniqueIdentifier = true;
Prêt à l'emploi, nous prenons en charge la règle unique
fournie par Laravel. Nous prenons également en charge la règle populaire felixkiss/uniquewith-validator, mais vous devrez vous y inscrire. Ajoutez simplement use WatsonValidatingInjectorsUniqueWithInjector
après avoir importé le trait de validation.
Il est également facile de prendre en charge des règles d'injection supplémentaires, si vous le souhaitez. Supposons que vous souhaitiez prendre en charge une règle supplémentaire appelée unique_ids
qui prend simplement la clé primaire du modèle (pour une raison quelconque). Il vous suffit d'ajouter une règle en casse chameau qui accepte tous les paramètres existants et le nom du champ, et renvoie la règle de remplacement.
/** * Préparez une règle unique_ids, en ajoutant un identifiant de modèle si nécessaire. * * @param array $parameters * @param string $field * @return string */protected function prepareUniqueIdsRule($parameters, $field) {// Effectuez un remplacement uniquement si le modèle a été persistant.if ($this->exists) {return 'unique_ids:' . $this->getKey(); }retourne 'identifiants_uniques' ; }
Dans ce cas si le modèle a été enregistré et possède une clé primaire de 10
, la règle unique_ids
sera remplacée par unique_ids:10
.
Divers événements sont déclenchés par le trait pendant le processus de validation, auxquels vous pouvez vous connecter pour avoir un impact sur le processus de validation.
Pour vous connecter, vous devez d'abord ajouter la propriété $observeables
sur votre modèle (ou modèle de base). Cela permet simplement à Eloquent de savoir que votre modèle peut répondre à ces événements.
/** * Événements observables exposés par l'utilisateur * * Tableau @var */protected $observables = ['validating', 'validated'];
Lorsque la validation est sur le point de se produire, l'événement eloquent.validating: ModelName
sera déclenché, où le paramètre $event
sera saving
ou restoring
. Par exemple, si vous mettiez à jour un modèle avec espace de noms AppUser
l'événement serait eloquent.validating: AppUser
. Si vous écoutez l'un de ces événements et renvoyez une valeur, vous pouvez empêcher complètement la validation.
Event::listen('eloquent.validating:*', function($model, $event) {// Validation de la roulette pseudo-russe.if (rand(1, 6) === 1) {return false; } });
Une fois la validation effectuée, il existe également une gamme d'événements validated
auxquels vous pouvez vous connecter, pour les événements passed
, failed
et skipped
. Pour l'exemple d'échec de validation ci-dessus, vous pouvez obtenir l'événement eloquent.validated: AppUser
.
Il existe actuellement un bug dans Laravel (voir numéro 1181) qui empêche les événements de modèle de se déclencher plus d'une fois dans une suite de tests. Cela signifie que le premier test utilisant des tests de modèle réussira mais que tous les tests ultérieurs échoueront. Il existe quelques solutions temporaires répertoriées dans ce fil que vous pouvez utiliser pour faire réussir vos tests entre-temps.
Étant donné que Laravel est passé à Liferaft dans le but de suivre les bugs et les demandes d'extraction, le problème mentionné ci-dessus peut ne pas être disponible. Ce Gist contient un exemple TestCase.php
qui vous montre comment réinitialiser les événements de tous vos modèles entre les tests afin qu'ils fonctionnent comme prévu.
Il existe un certain nombre de façons d'utiliser le modèle de validation dans vos contrôleurs. Cependant, voici un exemple qui utilise le nouveau FormRequest dans Laravel 5 (si vous souhaitez voir un autre exemple de contrôleur sans FormRequest, cochez la version 4.2+ de ce package.
Cet exemple garde votre code propre en permettant à FormRequest de gérer la validation de votre formulaire et au modèle de gérer sa propre validation. En activant les exceptions de validation, vous pouvez réduire le code répétitif du contrôleur (blocs try/catch) et gérer les exceptions de validation de modèle de manière globale (vos demandes de formulaire doivent garder vos modèles valides, donc si votre modèle devient invalide, c'est un événement exceptionnel ).
<?php espace de noms AppHttpControllers ; utilisez AppHttpRequestsPostFormRequest ; utilisez IlluminateRoutingController ; la classe PostsController étend le contrôleur {post $ protégé; fonction publique __construct (Post $ post) {$this->post = $post; }// ...magasin de fonctions public(PostFormRequest $request) {// La publication lèvera une exception si elle n'est pas valide.$post = $this->post->create($request->input());// La publication a été enregistrée avec succès.return redirect()->route( 'posts.show', $post); } }
Vous pouvez ensuite intercepter une exception de validation de modèle dans votre app/Exceptions/Handler.php
et la traiter selon vos besoins.
fonction publique render($request, Exception $e) {if ($e instanceof WatsonValidatingValidationException) {return back()->withErrors($e)->withInput(); }parent::render($request, $e); }