53.重构垃圾检测机制

未匹配的标注

本节说明

  • 对应视频教程第 53 小节:Refactoring to Custom Validation

本节内容

目前我们已经实现了检测机制, 但是你是否注意到我们将验证过程分成了两个步骤:首先, 我们触发 Laravel 的内置验证器, 然后我们应用我们的检测机制进行检测。在本节我们将创建一个自定义验证规则, 并通过$this->validate(request(),['body' => 'required|spamfree'])这样的代码即可调用。首先我们新建一个文件:
forum\app\Rules\SpamFree.php

<?php namespace App\Rules; use App\Inspections\Spam; class SpamFree { public function passes($attribute,$value) { try { return ! resolve(Spam::class)->detect($value); }catch (\Exception $e){ return false; } } }

注:在 Laravel 5.5 中,你可以更加方便地进行自定义规则的编写,详见 自定义验证规则

接着,我们需要对规则进行注册:
forum\app\Providers\AppServiceProvider.php

 . . public function boot() { // Carbon::setLocale('zh'); \View::composer('*',function ($view){ $channels = \Cache::rememberForever('channels',function (){ return Channel::all(); }); $view->with('channels',$channels); }); \Validator::extend('spamfree','App\Rules\SpamFree@passes'); } . .

现在我们可以简化我们的控制器代码了:
forum\app\Http\Controllers\RepliesController.php

<?php namespace App\Http\Controllers; use App\Reply; use App\Thread; class RepliesController extends Controller { . . public function store($channelId,Thread $thread) { try{ $this->validate(request(),['body' => 'required|spamfree']); $reply = $thread->addReply([ 'body' => request('body'), 'user_id' => auth()->id(), ]); }catch (\Exception $e){ return response( 'Sorry,your reply could not be saved at this time.',422 ); } return $reply->load('owner'); } public function update(Reply $reply) { $this->authorize('update',$reply); try{ $this->validate(request(),['body' => 'required|spamfree']); $reply->update(request(['body'])); }catch (\Exception $e){ return response( 'Sorry,your reply could not be saved at this time.',422 ); } } . . }

forum\app\Http\Controllers\ThreadsController.php

<?php namespace App\Http\Controllers; use App\Filters\ThreadsFilters; use App\Channel; use App\Thread; use Illuminate\Http\Request; class ThreadsController extends Controller { . . public function store(Request $request) { $this->validate($request,[ 'title' => 'required|spamfree', 'body' => 'required|spamfree', 'channel_id' => 'required|exists:channels,id' ]); $thread = Thread::create([ 'user_id' => auth()->id(), 'channel_id' => request('channel_id'), 'title' => request('title'), 'body' => request('body'), ]); return redirect($thread->path()) ->with('flash','Your thread has been published!'); } . . }

现在我们尝试发布话题:
file
消息提示不友好,我们进行友好化处理:
forum\resources\lang\en\validation.php

. . 'unique' => 'The :attribute has already been taken.', 'uploaded' => 'The :attribute failed to upload.', 'url' => 'The :attribute format is invalid.', 'spamfree' => 'The :attribute contains spam.', . .

注:在 Laravel 5.5 中,你可以通过重写messages()方法很方便地自定义消息提示,详见 自定义错误消息

现在我们再次尝试:
file
最后我们运行全部测试:
file
有一个测试未通过,我们来看一下那个未通过的测试:

/** @test */ public function replies_contain_spam_may_not_be_created() { $this->signIn(); $thread = create('App\Thread'); $reply = make('App\Reply',[ 'body' => 'something forbidden' ]); $this->expectException(\Exception::class); $this->post($thread->path() . '/replies',$reply->toArray()); }

因为我们已经更改了处理逻辑,所以这个测试需要更新:

/** @test */ public function replies_contain_spam_may_not_be_created() { $this->signIn(); $thread = create('App\Thread'); $reply = make('App\Reply',[ 'body' => 'something forbidden' ]); $this->post($thread->path() . '/replies',$reply->toArray()) ->assertStatus(422); }

再次运行测试:
file

本文章首发在 LearnKu.com 网站上。

上一篇 下一篇
《L04 微信小程序从零到发布》
从小程序个人账户申请开始,带你一步步进行开发一个微信小程序,直到提交微信控制台上线发布。
《L02 从零构建论坛系统》
以构建论坛项目 LaraBBS 为线索,展开对 Laravel 框架的全面学习。应用程序架构思路贴近 Laravel 框架的设计哲学。
讨论数量: 0
发起讨论 只看当前版本


暂无话题~