自定义校验器

Yii提供了一套内置表单校验器,基本覆盖了所有典型的开发需求,并且是高度可配置的。但是,在一些情况下,开发者可能需要创建一个自定义校验器。

本小节会给出一个例子,创建一个检查单词个数的独立校验器。

准备

按照官方指南http://www.yiiframework.com/doc-2.0/guide-start-installation.html的描述,使用Composer包管理器创建一个新的应用。

如何做…

  1. 创建一个独立校验器@app/components/WordsValidator.php
  1. <?php
  2. namespace app\components;
  3. use yii\validators\Validator;
  4. class WordsValidator extends Validator
  5. {
  6. public $size = 50;
  7. public function validateValue($value){
  8. if (str_word_count($value) > $this->size) {
  9. return ['The number of words must be less than {size}', ['size' => $this->size]];
  10. }
  11. return false;
  12. }
  13. }
  1. 创建一个Article模型@app/models/Article.php
  1. <?php
  2. namespace app\models;
  3. use app\components\WordsValidator;
  4. use yii\base\Model;
  5. class Article extends Model
  6. {
  7. public $title;
  8. public function rules()
  9. {
  10. return [
  11. ['title', 'string'],
  12. ['title', WordsValidator::className(), 'size' =>
  13. 10],
  14. ];
  15. }
  16. }
  1. 创建@app/controllers/ModelValidationController.php
  1. <?php
  2. namespace app\controllers;
  3. use app\models\Article;
  4. use yii\helpers\Html;
  5. use yii\web\Controller;
  6. class ModelValidationController extends Controller
  7. {
  8. private function getLongTitle()
  9. {
  10. return 'There is a very long content for current article, '.'it should be less then ten words';
  11. }
  12. private function getShortTitle()
  13. {
  14. return 'There is a shot title';
  15. }
  16. private function renderContentByModel($title)
  17. {
  18. $model = new Article();
  19. $model->title = $title;
  20. if ($model->validate()) {
  21. $content = Html::tag('div', 'Model is valid.',[
  22. 'class' => 'alert alert-success',
  23. ]);
  24. } else {
  25. $content = Html::errorSummary($model, [
  26. 'class' => 'alert alert-danger',
  27. ]);
  28. }
  29. return $this->renderContent($content);
  30. }
  31. public function actionSuccess()
  32. {
  33. $title = $this->getShortTitle();
  34. return $this->renderContentByModel($title);
  35. }
  36. public function actionFailure()
  37. {
  38. $title = $this->getLongTitle();
  39. return $this->renderContentByModel($title);
  40. }
  41. }
  1. 访问index.php?r=model-validation/success来运行modelValidation控制器的success动作:

自定义校验器 - 图1

  1. 访问index.php?r=model-validation/failure来运行modelValidation控制器的failure动作:

自定义校验器 - 图2

  1. 创建@app/controllers/AdhocValidationController.php
  1. <?php
  2. namespace app\controllers;
  3. use app\components\WordsValidator;
  4. use app\models\Article;
  5. use yii\helpers\Html;
  6. use yii\web\Controller;
  7. class AdhocValidationController extends Controller
  8. {
  9. private function getLongTitle()
  10. {
  11. return 'There is a very long content for current article, '.'it should be less then ten words';
  12. }
  13. private function getShortTitle()
  14. {
  15. return 'There is a shot title';
  16. }
  17. private function renderContentByTitle($title)
  18. {
  19. $validator = new WordsValidator([
  20. 'size' => 10,
  21. ]);
  22. if ($validator->validate($title, $error)) {
  23. $content = Html::tag('div', 'Value is valid.',[
  24. 'class' => 'alert alert-success',
  25. ]);
  26. } else {
  27. $content = Html::tag('div', $error, [
  28. 'class' => 'alert alert-danger',
  29. ]);
  30. }
  31. return $this->renderContent($content);
  32. }
  33. public function actionSuccess()
  34. {
  35. $title = $this->getShortTitle();
  36. return $this->renderContentByTitle($title);
  37. }
  38. public function actionFailure()
  39. {
  40. $title = $this->getLongTitle();
  41. return $this->renderContentByTitle($title);
  42. }
  43. }
  1. 访问index.php?r=adhoc-validation/success来运行adhocValidation控制器的success动作:

自定义校验器 - 图3

  1. 访问index.php?r=adhoc-validation/failure来运行adhocValidation控制器的failure动作:

自定义校验器 - 图4

工作原理

首先我们创建了一个独立的校验器,它会使用str_word_count函数来检查单词的数量,然后演示了两个使用例子:

  • 作为Article模型的校验规则使用这个校验器
  • 作为一个特定的校验器使用这个校验器

参考

欲了解更多信息,参考如下链接: