20210121のPHPに関する記事は8件です。

React Developer Toolsのインストールを推されるコンソールメッセージ消してみた。

行いたいこと

ブラウザのコンソールに出てる以下の文章を本番環境で消したかった。
Download the React DevTools for a better development experience: https://fb.me/react-devtools
image.png

やったこと

<!doctype html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
  <head>
<!-- 略 -->
  </head>
  <body>
    <script>
      // 本番環境上でコンソール上のdevtoolに関するメッセージを本番環境では表示しないようにする。
      @production
        window.__REACT_DEVTOOLS_GLOBAL_HOOK__ = {
          supportsFiber: true,
          inject: function() {},
          onCommitFiberRoot: function() {},
          onCommitFiberUnmount: function() {},
        };
      @endproduction
    </script>
    <div id="app"></div>
  </body>
</html>

解説

グローバル変数に以下の内容を代入すれば、devtoolに関するメッセージは消える
※ただしバンドルされるコード内に記載しても意味がない。

  window.__REACT_DEVTOOLS_GLOBAL_HOOK__ = {
          supportsFiber: true,
          inject: function() {},
          onCommitFiberRoot: function() {},
          onCommitFiberUnmount: function() {},
        };

補足(Laravel)

投稿主の環境はPHP(Laravel) + React.jsの構成になっている。
ちょうどいいからLaravelのBlade(テンプレートエンジン)上で、本番環境では、出ないようにするために、
@production@endproductionで挟んでいる。

@productionの解説
https://readouble.com/laravel/7.x/ja/blade.html#if-statements

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【コピペ】Docker ComposeでLaravel開発環境を構築その肆

前回、Laravelを別リポジトリ管理にして、かなりスッキリした。
【コピペ】Docker ComposeでLaravel開発環境を構築その参

でも、ふと思った、、、Laravelのプロジェクト名を変えたいな。。。
今は、Nginxのconfにベタ書きなので、.envから設定したいなーって事で、やってみた。
ついでに、色々バージョン上げよう!

マシンスペック

  • Mac mini 2018
  • macOS Catalina(10.15.x)
  • Intel Core-i7 3.2GHz 6コア
  • メモリ 32GB
  • SSD 512GB

Docker環境

  • Nginx 最新版
  • PHP(PHP-FPM) 7.1.xPHP(PHP-FPM) 7.4.x
  • MySQL 5.7.xMySQL 8.x
  • Composer 最新版Composer 2.x
  • Laravel 5.6Laravel 8.x

やること

  • Docker Composeで環境変数を使う
  • 色々バージョンアップする

補足

各環境を行ったり来たりするので、下記のように記載します。

[Mac]$ MacのターミナルでMac内の作業
[PHP]$ MacのターミナルからPHPコンテナに接続して作業

.envファイルを作成する

環境ごとに.env作成したいので、.env.exampleを作成する。
中身は下記。

# APP名
APP_NAME=laravel

# XDebugポート
XDEBUG_PORT=9000

# DB
DATABASE_NAME=hoge
DATABASE_USER=fuga
DATABASE_PASSWORD=docker#DOCKER1234
DATABASE_ROOT_PASSWORD=docker#DOCKER1234

.gitignoreの編集

https://github.com/bobtabo/docker2/blob/master/.gitignore

  • .envは除外
.env

docker-compose.ymlを編集

https://github.com/bobtabo/docker2/blob/master/docker-compose.yml

version: '3'

volumes:
    phpsocket:

services:
  nginx:
    〜 略 〜
    volumes:
      - ./src:/home/docker
      - phpsocket:/var/run
    depends_on:
      - php

  php:
    〜 略 〜
      - '9000:9000'
    volumes:
      - ./src:/home/docker
      - phpsocket:/var/run
    〜 略 〜

  db:
    image: mysql:5.7
    〜 略 〜
      MYSQL_DATABASE: hoge
      MYSQL_USER: fuga
      MYSQL_PASSWORD: docker#DOCKER1234
      MYSQL_ROOT_PASSWORD: docker#DOCKER1234
    〜 略 〜

環境ファイルを各コンテナで参照したいので、下記に変更。

version: '3.8'

volumes:
    phpsocket:

services:
  nginx:
    〜 略 〜
    volumes:
      - ./nginx/templates:/etc/nginx/templates
      - ./src/${APP_NAME}:/var/www/html
      - phpsocket:/var/run
    depends_on:
      - php
    environment:
      - APP_NAME=${APP_NAME}

  php:
    〜 略 〜
      - '${XDEBUG_PORT}:9000'
    volumes:
      - ./src:/home/docker
      - phpsocket:/var/run
    〜 略 〜

  db:
    image: mysql:8
    〜 略 〜
      MYSQL_DATABASE: ${DATABASE_NAME}
      MYSQL_USER: ${DATABASE_USER}
      MYSQL_PASSWORD: ${DATABASE_PASSWORD}
      MYSQL_ROOT_PASSWORD: ${DATABASE_ROOT_PASSWORD}
    〜 略 〜

ドキュメントルートは後述(Nginxのconf編集)の理由から /var/www/html に変更。
Laravel5.6→8.xに入れ替える際、/var/www/html を削除できなかった。(いつか調べる)
Nginxコンテナで/var/www/htmlをマウント、PHPコンテナで/home/dockerをマウントする。
/home/docker/${APP_NAME}を削除して新たにプロジェクト作成しても、/var/www/html に即反映しなかったので、その際は下記で復活する。

[Mac]$ docker-compose down
[Mac]$ docker-compose up -d

Nginxのconf編集

https://github.com/bobtabo/docker2/blob/master/nginx/conf.d/default.conf

・・・
server_name laravel.local;
・・・
location / {
    root /home/docker/laravel/public;
    ・・・
}
・・・
location ~ \.php$ {
    root /home/docker/laravel/public;
    ・・・
}

上記に環境変数を埋め込むように修正。

・・・
server_name ${APP_NAME}.local;
・・・
location / {
    root /home/docker/${APP_NAME}/public;
    ・・・
}
・・・
location ~ \.php$ {
    root /home/docker/${APP_NAME}/public;
    ・・・
}

ただ、ドキュメントルートの環境変数埋め込みが、どうやってもエラーになって無理だったので、ドキュメントルートを固定。
結局こうなりました。

・・・
server_name ${APP_NAME}.local;
・・・
location / {
    root /var/www/html/public;
    ・・・
}
・・・
location ~ \.php$ {
    root /var/www/html/public;
    ・・・
}

後述(default.confの置換)でファイル名を、conf.d/default.conf → templates/default.conf.templateにリネーム。

default.confの置換

https://github.com/bobtabo/docker2/blob/master/nginx/Dockerfile

# 設定の置換
COPY conf.d/default.conf /etc/nginx/conf.d/default.conf

docker-compose.ymlのvolumesで解決する。

services:
  nginx:
    〜 略 〜
    volumes:
      - ./nginx/templates:/etc/nginx/templates

なので、Dockerfile内でのCOPYは不要になった

Composer2.xをインストールする修正

https://github.com/bobtabo/docker2/blob/master/php/Dockerfile

COPY --from=composer:latest /usr/bin/composer /usr/bin/composer

latestにしてたから最新版が入ってると思いきや、何故か 1.x だったので 2.x で固定。

COPY --from=composer:2 /usr/bin/composer /usr/bin/composer

XDebugのバージョン固定

https://github.com/bobtabo/docker2/blob/master/php/Dockerfile

RUN pecl install xdebug

このままだと、Xdebug 3.xがインストールされる。
Xdebug 2.x と Xdebug 3.x は、設定ファイルの記述が異なり、今までの設定だと動かない。(ハマった)
Xdebug 2.xに固定。(3.xの設定は、また今度)

RUN pecl install xdebug-2.9.8

Laravelの準備

[Mac]$ docker-compose exec --user 1000 php bash

[PHP]$ rm -fdR laravel
[PHP]$ composer create-project --prefer-dist laravel/laravel laravel "8.*"
[PHP]$ cd laravel
[PHP]$ composer require --dev barryvdh/laravel-ide-helper
[PHP]$ composer require --dev squizlabs/php_codesniffer
[PHP]$ mkdir bin
[PHP]$ vi bin/clear-laravel.sh
---
#!/bin/bash
php artisan view:clear
php artisan cache:clear
php artisan config:clear
php artisan route:clear
php artisan clear-compiled
php artisan config:cache
composer dump-autoload
php artisan ide-helper:generate
php artisan ide-helper:models -N
php artisan ide-helper:meta
find . -name '._.DS_Store' -type f -ls -delete
---
:wq
[PHP]$ vi .env.example
---
:%s/DB_HOST=127.0.0.1/DB_HOST=mysql/g
:%s/DB_DATABASE=homestead/DB_DATABASE=hoge/g
:%s/DB_USERNAME=homestead/DB_USERNAME=fuga/g
:%s/DB_PASSWORD=secret/DB_PASSWORD=docker#DOCKER1234/g
---
:wq

完成!!
https://github.com/bobtabo/docker3

※参考
https://qiita.com/shin-go/items/6cb4824944ddffb6e6a7

使い方

[Mac]$ cd <任意のディレクトリ>
[Mac]$ git clone https://github.com/bobtabo/docker3.git docker
[Mac]$ cd docker
[Mac]$ cp -p .env.example .env
[Mac]$ docker-compose up -d
・・・
Creating mysql ... done
Creating php   ... done
Creating nginx ... done

[Mac]$ docker-compose exec --user 1000 php bash

[PHP]$ pwd
/home/docker

[PHP]$ cd laravel
[PHP]$ composer install
[PHP]$ chmod -R 777 storage
[PHP]$ chmod -R 777 bootstrap/cache
[PHP]$ cp -p .env.example .env
[PHP]$ php artisan key:generate
[PHP]$ chmod 755 bin/clear-laravel.sh
[PHP]$ bin/clear-laravel.sh
[PHP]$ php artisan migrate:refresh --seed

動作確認(Macのhosts編集)

[Mac]$ sudo vi /private/etc/hosts
★下記を点線内を追記
---
127.0.0.1 laravel.local
---
:wq

ブラウザで動作確認
http://laravel.local/
スクリーンショット 2021-01-21 23.02.41.png

コンテナ削除

[Mac]$ docker-compose down --rmi all --volumes

※参考
https://qiita.com/suin/items/19d65e191b96a0079417

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

Apache2.4 権限周りの初期設定

概要

LAMP学習中の環境エラー対処の備忘録です。
せっかくなので qiita にします。
ポリシーとして解決しなかったことは書きません。
随時更新。

環境

awsです。

$ whoami
root
$ cat /etc/os-release 
NAME="Red Hat Enterprise Linux"
VERSION="8.3 (Ootpa)"

Apache エラー: 403 Forbidden

apache ユーザに権限を渡す必要がある。
ファイルだけでなくディレクトリにも権限付与するのを忘れずに。

$ chmod -R 775 /var/www
# ↓この辺の権限を全部かえる
   /var/www
         \_html
            \_*.html
             _*.php

phpエラー: Warning: fopen(XXX.txt):

failed to open stream: Permission denied in /var/www/html/XXX.php on line XXX ていうエラー(正確には警告)
selinuxが有効になっているのが原因だった。
ファイルやディレクトリの権限をいじっても無理

# 有効を解除する(Permissiveにする)
$ setenforce 0

# 再起動したときの自動有効化を停止する
$ sed "s/SELINUX=enabled/SELINUX=disabled/g" /etc/selinux/config

setenforceをやらないで、sed+再起動でも良い。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

PHPで個人開発してたら、PHPがめっちゃ叩かれてて辛みだった話

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Laravel】バリデーションやフォームリクエストのattributesとは?カスタム属性名の設定方法

バリデーション関連のファイルでattributesというのが出てくる。この役割と使い方について。

目次

  1. いつ使うか?
  2. 属性名の変更方法
  3. フォームリクエストを使用している場合


いつ使うか?

バリデーションでデフォルトのエラーメッセージを表示すると、その属性名が表示される。この属性名は変数で適用されている。

attributesを編集することで、この属性名を好きな値に変更することができる。


デフォルトの設定例

name属性に以下バリデーションが適用されている場合

バリデーションルール
'name' => 'required|min:3|max:10',
image.png

resources > lang > en > validation.php で定義された内容が表示されている。

image.png

validation.php
    'min' => [
        'string' => 'The :attribute must be at least :min characters.',
    ],

ここで、属性名は:attributeというように可変な値で定義されている。


属性名の変更方法

上記validation.phpの一番下にあるattributesに追記する。

validation.php
    'attributes' => [
        'name' => '名前',
    ],



▼実行例

image.png

:attributeの部分が指定した「名前」に変更されている。


メッセージを変更する方法

メッセージを変更したい場合は、同ファイルの下の方にあるcustomに追記する。

validation.php
    'custom' => [
        //以下追記
        'name' => [
            'min' => ':attributeは:min 文字以上で入力してください'
        ],
    ],



▼実行例

image.png


日本語化

現在、enディレクトリ配下のファイルをいじっているが、日本語なので、本来はjaディレクトリのファイルをいじるべき。

日本語化の方法はこちらを参照。


フォームリクエストを使用している場合

フォームリクエストを使用している場合、各ファイルのクラスの定義内でattributeを設定することができる

フォームリクエストとは?

フォームリクエストにカスタム属性を追加

attributesメソッドを新たに作成する。

作成例
    public function attributes()
    {
        return [
            'name' => '名前',
        ];
    }



▼フォームリクエストの設定例

MailFormRequest.php
<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class MailFormRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        return true;
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            'name' => 'required|min:3|max:10',
        ];
    }


    public function messages()
    {
        return [
            'name.required' => '名前を入力して下さい。',
            'name.max' => ':attributeは:max文字以下で入力して下さい。',
            'name.min' => ':attributeは:min文字以上で入力して下さい。',
        ];
    }

    public function attributes()
    {
        return [
            'name' => '名前',
        ];
    }
}

▼バリデーション実行結果

image.png
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Laravel】ルート名を使って条件分岐をする方法。ページごとに処理を切り分ける。

ページによって処理を切り分けたい場合、ルート名を使うことで簡単に実現できる。

Request::routeIs('ルート名')
- RequestファサードのrouteIsメソッド
- 指定したルート名の場合はtrue、それ以外の場合はfalseとなる。


使い方(.blade.php)
        @if( Request::routeIs('english'))
          <h1>Hello!!!</h1>
        @endif

ルート名が、englishのとき、h1タグを表示する処理となる。

ルーティング(web.php)
Route::get('greetings/english', 'GreetingController@english')->name('english');

->name('english')でルート名を指定している。


使いどころ

条件分岐をページ固有の変数(例えばテキスト)で指定すると、変数の中身が変わったときに、処理が適用されなくなってしまう。

なのでページによって切り分ける場合は、Request::routeIsメソッドを使う。

NG事例
        @if( $language === "english" ))
          <h1>Hello!!!</h1>
        @endif

変数$languageの値が、「英語」や「eng」になった場合に適用されなくなる。


(補足)パスで処理を切り分ける場合

ルート名ではなくパスで切り分ける場合は、Route::is()を使う。

使い方(.blade.php)
        @if( Request::is(/greetings/english))
          <h1>Hello!!!</h1>
        @endif
  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Laravel】メール送信内容をバリデーションする方法(with フォームリクエスト)。エラーメッセージの変更方法など

Laravelのフォームリクエストという便利機能を使ってバリデーションを実装する方法について。

フォームリクエストを使わないコントローラのみのバリデーション方法の続きです。

メール送信機能の作成方法については以下を参照。
【Laravel】Localhostでgmailを使ってメールを送信する方法。Mailableを使わない方法

【Laravel】Mailableを使ってメールを送信する方法。データや画像を添付する方法や入力データをメール本文に渡す方法

目次

  1. フォームリクエストとは?
  2. フォームリクエストの作成
  3. バリデーションルールの作成
  4. authorizeメソッドの編集
  5. コントローラの編集
  6. バリデーション処理の確認
  7. エラーメッセージの変更
  8. (参考)使用コード一覧


フォームリクエストとは?

バリデーションのコードをコントローラの外に記述する方法。Requestsディレクトリの中のファイルに専用のクラスを作成する。

バリデーションはコントローラにデータを渡す前に実行される。

1. フォームリクエストの作成

以下コマンドを使えばファイルが自動生成できる。(自分でクラスを作成することもできる)

$ php artisan make:request フォームリクエスト名



▼実例

$ php artisan make:request MailFormRequest
Request created successfully.

ファイルは、app > Http > Requests 配下に生成される。

image.png

フォームリクエストの中身

<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class MailFormRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        return false;
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            //
        ];
    }
}

認証関連のバリデーションを行うauthorizeメソッドと、バリデーションルールを記述するrulesメソッドが用意されている。


2. バリデーションルールの作成

ルールはrulesメソッドの中に記述する。

    public function rules()
    {
        return [
            'name' => 'required|min:3|max:10',
        ];
    }

ルールを複数設置する場合はカンマでつなげていく。

'name' => 'required|min:3|max:10'
渡されたname属性に対し、required(必須)、min:3(3文字以上)、max:10(10文字以下)の3つのルールを適用している。


3. authorizeメソッドの編集

フォームリクエストのauthorizeメソッドは初期状態でfalseになっている。

この状態だと認証をパスしていない場合は403 |
THIS ACTION IS UNAUTHORIZED.
に飛ばされる。

image.png

今回は認証設定をしないため、この値をtrueに変更する。

    public function authorize()
    {
        return true;
    }


4. コントローラの編集

4-1. 冒頭で作成したフォームリクエストのuse宣言をする。

use App\Http\Requests\[フォームリクエスト名];

4-2. sendアクションにバリデーション後のデータを渡す

public function send([フォームリクエスト名] $変数)

DI(依存注入)で、フォームリクエストクラスのインスタンスを変数に入れて渡す。

▼実例

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Mail;                   //Mailファサード使用
use App\Mail\ValidatedMail; //Mailable使用
use App\Http\Requests\MailFormRequest;  //追記(フォームリクエスト)

class ValidatorController extends Controller
{
    public function index() //コンタクトフォームの表示
    {
        return view('contact.validate');
    }

    public function send(MailFormRequest $validatedRequest)  //メールの自動送信設定
    {
        $data = $validatedRequest;

        Mail::to('xxx@gmail.com')
                ->send(new ValidatedMail($data));

        return back()->withInput()
                     ->with('sent', '送信完了しました。');    //送信完了を表示
    }
}

以上で設定が完了。

5. バリデーション処理の確認

image.png

設定通りにバリデーションできた。


エラーメッセージの変更

デフォルトでは英語の定型メッセージが表示されるため、これを好きな文字列に変更する。

フォームリクエストにmessagesメソッドを追加して戻り値で指定する。

    public function messages()
    {
        return [
            'name.required' => '名前を入力して下さい。',
            'name.max' => ':max 文字以下で入力して下さい。',
            'name.min' => ':min 文字以上で入力して下さい。',
        ];
    }

カスタムメッセージの指定方法は2パターン。今回は(2)を使用。

(1)ルール毎にメッセージを指定する場合
・'ルール' => 'カスタムメッセージ'

(2)属性に適用したルール毎にメッセージを指定する場合
・'属性名.ルール' => 'カスタムメッセージ'



▼処理の確認

image.png

以上で完了。


(参考)使用コード一覧

今回のテストで使用したファイルとコードは以下。

  1. 環境変数
  2. ルーティング
  3. コントローラ
  4. Mailableクラス
  5. フォームリクエスト
  6. コンタクトフォーム
  7. メール本文

1. 環境変数

.env
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=your address@gmail.com
MAIL_PASSWORD=your app password
MAIL_ENCRYPTION=tls
MAIL_FROM_NAME="mail title"

2. ルーティング

web.php
//Validatorファサード
Route::get('validator', 'ValidatorController@index');
Route::post('validator', 'ValidatorController@send');

3. コントローラ

ValidatorController.php
<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Mail;                   //追記
use App\Mail\ValidatedMail; //追記
use App\Http\Requests\MailFormRequest;  //追記(フォームリクエスト)

class ValidatorController extends Controller
{
    //以下追記
    public function index() //コンタクトフォームの表示
    {
        return view('contact.validate');
    }

    public function send(MailFormRequest $validatedRequest)  //メールの自動送信設定
    {
        $data = $validatedRequest;

        Mail::to('xxx@gmail.com')
                ->send(new ValidatedMail($data));

        return back()->withInput()
                     ->with('sent', '送信完了しました。');    //送信完了を表示
    }
}

4. Mailableクラス

ValidatedMail.php
<?php

namespace App\Mail;

use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Mail\Mailable;
use Illuminate\Queue\SerializesModels;

class ValidatedMail extends Mailable
{
    use Queueable, SerializesModels;
    public $data;
    /**
     * Create a new message instance.
     *
     * @return void
     */
    public function __construct($data)
    {
        $this->data = $data;
    }

    /**
     * Build the message.
     *
     * @return $this
     */
    public function build()
    {
        //以下追記
        return $this->view('emails.validated')
                    ->subject('メールの標題')
                    ->with('data', $this->data);
    }
}

5. フォームリクエスト

MailFormRequest.php
<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class MailFormRequest extends FormRequest
{
    /**
     * Determine if the user is authorized to make this request.
     *
     * @return bool
     */
    public function authorize()
    {
        return true;
    }

    /**
     * Get the validation rules that apply to the request.
     *
     * @return array
     */
    public function rules()
    {
        return [
            'name' => 'required|min:3|max:10',
        ];
    }


    public function messages()
    {
        return [
            'name.required' => '名前を入力して下さい。',
            'name.max' => ':max 文字以下で入力して下さい。',
            'name.min' => ':min 文字以上で入力して下さい。',
        ];
    }
}

6. コンタクトフォーム

validate.blade.php
@if ( Session::has('sent'))
<div>
    <p>{{old('name')}}さん{{ session('sent') }}</p>
</div>
@endif

<form action="{{ url('validator') }}" method="POST">
@csrf

 <p>名前<input type="text" name="name" value="{{ old('name') }}" ></p>
  @error('name')
    <p style="color:red;">{{ $message }}</p>
  @enderror

 <input type="submit" value="送信する">
</form>

7. メール本文

validated.blade.php
<p>名前{{ $data['name'] }}さんから連絡がありました</p>


まとめ

これまで、以下3つの方法でバリデーションを試してきた。

  1. Requestファサードのvalidateメソッドでコントローラに直接記述
  2. Validatorファサードでコントローラに直接記述
  3. フォームリクエストを使用



カスタムメッセージを表示したり、バリデーションを使いまわすなど利便性が高いのは、(3)のフォームリクエスト

管理するファイル数を増やしたくない場合は(2)のValidatorファサードの使用がいいと感じた。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Laravel】メール送信用入力フォームのバリデーション(validation)設定方法。コントローラを使ったバリデーションとエラーメッセージの変更

Laravelのメール送信機能の一環で、入力フォームのバリデーションを設定する方法について。

メール送信機能の作成方法は以下を参照。
【Laravel】Localhostでgmailを使ってメールを送信する方法。Mailableを使わない方法

【Laravel】Mailableを使ってメールを送信する方法。データや画像を添付する方法や入力データをメール本文に渡す方法

Larael公式 バリデーション

目次

  1. バリデーションの記述場所
  2. バリデーションのメソッド
  3. バリデーションルール一覧
  4. コントローラにバリデーションを実装する方法
    1. コントローラの編集
    2. コンタクトフォーム(ビュー)の編集
    3. バリデーションの確認
  5. エラーメッセージの変更
    1. validation.phpのcustom配列に追記する
    2. validation.phpの本文を書き換える
    3. 日本語の言語ファイルを作成する
  6. Varidatorファサードを使ったバリデーション
  7. フォームリクエストでバリデーションする方法


バリデーションの記述場所

バリデーションの記述場所は2パターンある。
(1) コントローラ
(2) フォームリクエスト

簡単なバリデーションであればコントローラへの記述で十分。

フォームリクエスト(ファイル)を使う場合は、そのクラスをコントローラで読み込む。



▼フォームリクエストを使うメリット

  • バリデーションの処理のみを書けるため、コントローラがシンプルで可読性が上がる
  • エラーメッセージを各フォームリクエスト毎に設定できる。
  • 複数のフォームリクエストを作成することでバリデーションのパターンをいくつも持てる。


バリデーションのメソッド

バリデーションのメソッドは、Requestファサードのvalidateメソッドを使うパターンと、validatorファサードのメソッドを使うパターンが用意されている。

若干処理の記述方法が違ったり、エラー発生時の挙動の違いがある。


validateメソッドとValidatorファサードの違い

validateメソッドは例外発生時に自動で元のページにリダイレクトする。

一方、Validatorファサードは自動リダイレクト機能が実装されていないので、使いたい場合は自分で記述するか、Validatorファサードのvalidationメソッドを呼び出す。

呼び出し方法

▼validateメソッド

$validatedData = $request->validate([
   '属性名' => 'バリデーションルール',
   'title' => 'required|unique:posts|max:255',
   'body' => 'required',
]);



▼Validatorファサード

$validator = Validator::make($request->all(), [
            '属性名' => 'バリデーションルール',
            'title' => 'required|unique:posts|max:255',
            'body' => 'required',
        ]);


Validatorファサードのリダイレクト実装方法

▼Validatorファサードの中でvalidateメソッドを使う例

Validator::make($request->all(), [
    'title' => 'required|unique:posts|max:255',
    'body' => 'required',
])->validate();


▼Validatorファサードでリダイレクト処理を自分で記述する例

        $validator = Validator::make($request->all(), [
            'title' => 'required|unique:posts|max:255',
            'body' => 'required',
        ]);

        if ($validator->fails()) {
            return redirect('post/create')
                        ->withErrors($validator)
                        ->withInput();
        }


バリデーションルール

バリデーションを実際に記述する際は、以下のようにバリデーションルールをパイプ( | )でつないでいく。

'対象の属性' => 'ルール1|ルール2|ルール3|,,,',

ルールは1から順に適用される。

バリデーションで使えるルールは多数用意されている。

image.png

バリデーションルール一覧


主なバリデーションルール

ルール名 内容
required 値が必須。ない場合はエラーになる。
email e-mailのフォーマットのみ許容する
image イメージ画像 (jpg, jpeg, png, bmp, gif, svg, or webp)のみ許容する
max:value 指定した数字以下のみ許容。
min:value 指定した数字以上のみ許容。
url urlのみ許容する。
bail 例外が発生した時点でバリデーションチェックを終了する
accepted アクティブかどうかを調べる。'yes', 'on', 1, trueのみ許容する。
after:date 指定日以降のみ許容する
alpha_num アルファベットと数字のみ許容する

@fagaiさんのページがわかりやすいです。


コントローラにバリデーションを実装する方法

編集するのは2つのファイルのみでOK。(既にメール送信ができる状態)

1. コントローラの編集

バリデーションの設定はとても簡単。以下コードをsendアクションに追加するのみ。

追記する内容
 $validateData = $request->validate([
            'name' => 'required|string|max:10|min:3',
        ]);

        $data = $validateData;

$request->validate([バリデーションの条件])
validateメソッドを使用。

'name' => 'required|string|max:10|min:3'
属性名nameに対して、required(必須)、string(文字列)、max:10(10文字以内)、min:3(3文字以上)の条件を割り当て。

$data = $validateData;
バリデーション後のデータを変数dateに入れる。
例外があった場合はそのエラーメッセージが入る。



▼コントローラの記述例

ValidateController.php
<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Mail;                   //追記
use App\Mail\ValidatedMail; //追記

class ValidateController extends Controller
{
    public function index() //コンタクトフォームの表示
    {
        return view('contact.validate');
    }

    public function send(Request $request)  //メールの自動送信設定
    {
        //バリデーション
        $validateData = $request->validate([
            'name' => 'required|string|max:10|min:3',
        ]);

        $data = $validateData;

        //メール送信処理
        Mail::to('xxx@gmail.com')
                ->send(new ValidatedMail($data));

        return back()->withInput()
                     ->with('sent', '送信完了しました。');    //送信完了を表示
    }
}


2. コンタクトフォーム(ビュー)の編集

例外が発生したときに、例外の内容をビューに表示できるようにする。

追記内容
@error('name')
  <p style="color:red;">{{ $message }}</p>
@enderror

これを追加するだけで、エラー発生時に内容が表示される。

バリデーションで例外が発生すると元のページにリダイレクトされ、その際に、エラー内容がそのページに渡される

追記したコードは受け取ったエラー内容を表示する処理となる。

@error('属性名')
指定した属性でエラーが発生した場合に以下処理が表示される。
エラー内容は自動的に$messageに入る。

@enderrorで処理を閉じる。



<p style="color:red;">{{ $message }}</p>
pタグ赤色で表示するように指定。ここは別になんでもいい。
大切なのは、$messageにエラーメッセージが格納されているということ。


3. バリデーションの確認

実際にブラウザでバリデーションが機能しているか確認してみる。

image.png

↓文字数が2文字以下

image.png

3文字以上じゃなきゃダメというエラーメッセージが表示される。



▼その他のエラーもちゃんと表示される。

image.png
image.png


エラーメッセージの変更

デフォルトの状態では、エラーメッセージは決められたテキスト(英語)が表示される。

デフォルトのエラーメッセージの置き場所

resources > lang > en > validation.php

image.png

▼minの場合

    'min' => [
        'numeric' => 'The :attribute must be at least :min.',
        'file' => 'The :attribute must be at least :min kilobytes.',
        'string' => 'The :attribute must be at least :min characters.',
        'array' => 'The :attribute must have at least :min items.',
    ],

入力された型によってメッセージが変わるようになっている。

  • :attributeに指定した属性名が入る。
  • :minに指定した文字数が入る。


エラーメッセージの変更

コントローラにバリデーションを直接記述する場合のエラーメッセージ変更方法は3つある。

  1. validation.phpのcustom配列に追記する
  2. validation.phpの本文を書き換える
  3. 日本語の言語ファイルを作成する

Voridatorファサードやフォームリクエストを使う場合は、ファイルに直接記述できる。


1. validation.phpのcustom配列に追記する

最もシンプルな方法。No2と異なり変更箇所がわかりやすい。

image.png
このファイルの下の方にある、custom部分に追記する。

validation.php
    'custom' => [
        'attribute-name' => [
            'rule-name' => 'custom-message',
        ],
        //以下追記
        'name' => [
            'min' => ':min 文字以上で入力してください'
        ],
    ],

 ↓ 保存してバリデーションを実行

image.png

日本語化に成功。


2. validation.phpの本文を書き換える

例えば、minstringを書き換える場合は以下のようになる。

validation.php
    'min' => [
        'numeric' => 'The :attribute must be at least :min.',
        'file' => 'The :attribute must be at least :min kilobytes.',
        // 'string' => 'The :attribute must be at least :min characters.',
        'string' => '名前は :min 文字以上で入力してください.',
        'array' => 'The :attribute must have at least :min items.',
image.png


3. 日本語の言語ファイルを作成する

日本語の言語ファイルを作成し、設定言語を日本語に切り替える方法。

本格的に日本語化したい場合は使えるが、翻訳作業に時間がかかる、、

3-1. jaディレクトリを作成

enディレクトリ配下をコピーしてjaディレクトリに貼り付け。

image.png

3-2. validation.phpのメッセージを書き換える

jaディレクトリのファイルを日本語化する。
大変なので、今回はrequiredのみ日本語化

validation.php
'required' => 'この項目は必須です。',

3-3. 設定言語をjaに変更する

config > app.php のlocale(言語設定)をenからjaに変更する。

image.png

app.php
    /*
    |--------------------------------------------------------------------------
    | Application Locale Configuration
    |--------------------------------------------------------------------------
    |
    | The application locale determines the default locale that will be used
    | by the translation service provider. You are free to set this value
    | to any of the locales which will be supported by the application.
    |
    */

    'locale' => 'ja',

以上で設定完了。



▼検証結果

image.png

jaディレクトリの内容が適用できた。


日本語翻訳版validation.php

Laravel公式ページに翻訳後のvalidation.phpあります。


Varidatorファサードを使ったバリデーション

requestファサードのvalidateメソッドではなく、Varidatorファサードを使った場合の記述方法について。

Validatorファサードを使う場合はコントローラの冒頭に以下を記述する。

追記内容
use Illuminate\Support\Facades\Validator;



Validatorのmakeメソッドでバリデーションを定義する。makeメソッドは引数を3つとる。

Validator::make(対象データ, バリデーションルール, エラーメッセージ)
  • 第1引数:バリデーション対象のデータ
  • 第2引数:バリデーションルール
  • 第3引数:カスタムエラーメッセージ(なくてもいい)

バリデーションルールやエラーメッセージは変数で渡すことが多い。

ルールには$rules, エラーメッセージは$messagesを渡すなど。


実例

1. コントローラの編集

コントローラのsendアクションに以下を追加する。

追記内容
use Illuminate\Support\Facades\Validator;

Validatorファサードを使うために冒頭に表示する。

追記内容
        //バリデーションルール
        $rules = [
            'name' => 'required|min:3|max:10',
        ];

        //Validator
        $validator = Validator::make($request->all(), $rules)
                    ->validate();       

$rules
属性に対しバリデーションルールを設定する。
カンマでつないで複数設定できる。

$request->all()
渡されたすべてのデータをバリデーション対象とする。

->validate();
validateメソッドで自ページに自動リダイレクトする。

この処理は以下記述と同じ。

        if ($validator->fails()) {
            return redirect('validate')
                        ->withErrors($validator)
                        ->withInput();
        }

バリデーションで例外が発生したら、URI:validateにリダイレクト(ここでは自ページ)

withErrors()
リダイレクト画面に$errorsでエラーデータを渡す。

withInput()
フォームの入力内容をリダイレクト画面に渡す。old()で呼び出せる。


コントローラの記述例

コントローラの記述は以下のようになる。

ValidateController.php
<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Mail;                   //追記
use App\Mail\ValidatedMail; //追記
use Illuminate\Support\Facades\Validator; //追記

class ValidateController extends Controller
{
    public function index() //コンタクトフォームの表示
    {
        return view('contact.validate');
    }

    public function send(Request $request)  //メールの自動送信設定
    {
        //バリデーションルール
        $rules = [
            'name' => 'required|min:3|max:10',
        ];

        //Validator
        $validator = Validator::make($request->all(), $rules, $messages)
                    ->validate();

        Mail::to('xxx@gmail.com')
                ->send(new ValidatedMail($validator));

        return back()->withInput()
                     ->with('sent', '送信完了しました。');    //送信完了を表示
    }
}


2. コンタクトフォーム(ビュー)の編集

例外が発生したときに、例外の内容をビューに表示できるようにする。

追記内容
@error('name')
  <p style="color:red;">{{ $message }}</p>
@enderror

これを追加するだけで、エラー発生時に内容が表示される。

バリデーションで例外が発生すると元のページにリダイレクトされ、その際に、エラー内容がそのページに渡される

追記したコードは受け取ったエラー内容を表示する処理となる。

@error('属性名')
指定した属性でエラーが発生した場合に以下処理が表示される。
エラー内容は自動的に$messageに入る。

@enderrorで処理を閉じる。



<p style="color:red;">{{ $message }}</p>
pタグ赤色で表示するように指定。ここは別になんでもいい。
大切なのは、$messageにエラーメッセージが格納されているということ。


3. バリデーションの確認

実際にブラウザでバリデーションが機能しているか確認してみる。

▼実行結果

image.png

バリデーション成功。


エラーメッセージをカスタムする

エラーメッセージをカスタムする方法は4つある。

1. validation.phpのcustom配列に追記する
2. validation.phpの本文を書き換える
3. 日本語の言語ファイルを作成する
4. 第3引数でメッセージを渡す

No.1~3はRequestファサードのvalidateメソッドを使った場合も共通。validateメソッドのカスタムメッセージ表示方法

No.4がValidatorファサード特有の便利機能。


第3引数でメッセージを渡す方法

ルールの指定方法は2つある。

(1)ルール毎にメッセージを指定する場合
'ルール' => 'カスタムメッセージ'

(2)属性に適用したルール毎にメッセージを指定する場合
'属性名.ルール' => 'カスタムメッセージ'

この記述であれば、formの中に同じルールが複数ある場合に、メッセージの出しわけができる。


追記内容
        //バリデーションルール
        $rules = [
            'name' => 'required|min:3|max:10',
        ];

        //追記
        $messages = [
            'name.max' => ':max 文字以下で入力して下さい。',
            'name.min' => ':min 文字以上で入力して下さい。',
        ];

        //Validator
        $validator = Validator::make($request->all(), $rules, $messages)        //追記
                    ->validate();       

▼実行結果

image.png


まとめ

Requestファサードのvalidateメソッドを使うよりも、Validatorファサードを使った方が記述がわかりやすい。(個人的見解)




フォームリクエストでバリデーションする方法

長くなったので別記事に記述します。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む