2018/10/12

Laravelの勉強を進めていくにつれてよく出てくる単語が "RESTful" という単語です。
読み方は "レストフル" で間違いないかと思います。
RailsではRESTfulを推奨していて、それにそった機能設計が為されているそうです。
Laravelもこの流れにのっているのでしょう。
とりあえずさらっとですが調べてみたのですが難しい。。ずっと逃げ回っていました。
しかしあまりにもLaravelの構築において出現頻度が高いので腰を据えて勉強してみました。
今回はRestfulについての記事です。
RESTfulとは?
RESTとはWEBの設計思想のひとつです。
どのような設計思想か?
あるリソース(ここではDBのレコード)を取得するのか更新するのかは、HTTPのリクエストメソッドとURIに応じて操作をするというものです。

代表的なHTTPメソッドとその定義を見てみます。
| メソッド | 役割 |
|---|---|
| GET | リソースの取得(読み込み) |
| POST | リソースの新規作成 |
| PUT | 既存リソースの更新 |
| DELETE | リソースの削除 |
ここからさらにURIを付け加えたのが以下になります。
※操作対象が記事(Article)の場合
| METHOD | URI | ACTION | 操作内容 |
|---|---|---|---|
| GET | /articles | ArticlesController@index | 一覧表示 |
| GET | /articles/create | ArticlesController@create | 新規作成 |
| POST | /articles | ArticlesController@store | 新規保存 |
| GET | /articles/{article} | ArticlesController@show | 表示 |
| GET | /articles/{article}/edit | ArticlesController@edit | 編集 |
| PUT/PATCH | /articles/{article} | ArticlesController@update | 更新 |
| DELETE | /articles/{article} | ArticlesController@destroy | 削除 |
RESTの概念に基づいて設計されたものをRESTfulと言います。
Laravelでは RESTful にコントローラやルーティングの設定ができるようになっています。
RESTfulなコントローラを作成する
Laravelでは RESTful なControllerのひな形を簡単に作成することができます。
php artisan make:controller ProductController --resource
このコマンドを実行すると以下のようなひな形ができます。
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Http\Requests;
use App\Models\Product;
class ProductController extends Controller
{
/**
* 検索表示
*
* @return \Illuminate\Http\Response
*/
public function index()
{
//
}
/**
* 新規作成画面
*
* @return \Illuminate\Http\Response
*/
public function create()
{
//
}
/**
* DBレコード新規作成
*
* @param \Illuminate\Http\Request $request
* @return \Illuminate\Http\Response
*/
public function store(Request $request)
{
//
}
/**
* 表示画面
*
* @param \App\Models\Product $product
* @return \Illuminate\Http\Response
*/
public function show(Product $product)
{
//
}
/**
* 編集画面
*
* @param \App\Models\Product $product
* @return \Illuminate\Http\Response
*/
public function edit(Product $product)
{
//
}
/**
* DBレコード編集
*
* @param \Illuminate\Http\Request $request
* @param \App\Models\Product $product
* @return \Illuminate\Http\Response
*/
public function update(Request $request, Product $product)
{
//
}
/**
* DBレコード削除
*
* @param \App\Models\Product $product
* @return \Illuminate\Http\Response
*/
public function destroy(Product $product)
{
//
}
}
これらのメソッドはRESTfulのパターンに基づいて命名されています。
このコントローラを "RESTコントローラ" または "Resourceコントローラ" と読んだりします。
ルーティングで Route::Resource を使う
Restfulなコントローラを作成したら次はルーティングですよね。
Laravel5.2ではルーティングの設定で Route::resource という書き方ができるようになりました。
以下の1行だけで全てのパターンのルートを定義することができます。
Route::resource('product', 'ProductController.php');
ちなみに Route::controller という記述は5.2ではなくなりました。(コードではまだ対応しているようです)
実現したいこと
以前作成したコントローラをRESTに基づいたメソッド名に編集します。
また操作対象(greeting)のビューファイルは "greeting" フォルダに入れます。
手順
1. コントローラの編集
またデフォルトで入力画面を表示させていたのですが、一覧表示に変更します。
DBを操作する処理( store / update / destroy )に関してはFlashメッセージを流すことにします。
まずは一覧表示ですね。
一覧表示
新しい順に並ぶように今回少し編集しました。
ビューファイルですが、greetingフォルダを作成してそのフォルダの中にテンプレートファイルをまとめることにします。
greeting/index.blade.phpを呼び出す場合は
view('/greeting.index')
と "."(カンマ) を記述します。 ※"/"(スラッシュ)でないので注意
/*-------------------------------------------------------
* 一覧表示
--------------------------------------------------------*/
public function index()
{
# 新しい順に並べる(今回新しく追加)
$data = Greeting::latest('created_at')->get();
return view('greeting.index')->with('message','あいさつした人のリスト')->with('data',$data);
}
新規作成
/*-------------------------------------------------------
* 新規作成
--------------------------------------------------------*/
public function create()
{
return view('greeting.create')->with('message','あなたの名前を入力してください。');
}
新規保存
EloquentでDBの保存処理をします。
保存の処理が終わったらTOPにリダイレクトします。
public function store(GreetingRequest $request)
{
# 新しいレコードの追加
$greeting = new Greeting();
$greeting->onamae = $request->input('onamae');
$greeting->save();
# View表示
$res = "こんにちは!" . $request->input('onamae')."さん!!";
$data = Greeting::latest('created_at')->get();
return redirect('/greeting/')->with('message',$res)->with('data',$data)->with('status','新規保存の処理完了!');
}
表示
一覧からどれか1つクリックするとそのレコードの詳細が表示される画面のことですね。
1つのレコードに項目がたくさんあったら詳細画面は必要ですが、ここでは名前しかカラムがないので省略します。
/*-------------------------------------------------------
* 表示
--------------------------------------------------------*/
public function show($id)
{
//
}
編集
/*-------------------------------------------------------
* 編集
--------------------------------------------------------*/
public function edit($id)
{
$data = Greeting::findOrFail($id);
return view('greeting.edit')->with('message','編集フォーム')->with('data',$data);
}
更新
/*-------------------------------------------------------
* 更新
--------------------------------------------------------*/
public function update(GreetingRequest $request,$id)
{
$greeting = Greeting::findOrFail($id);
$greeting->onamae = $request->input('onamae');
$greeting->save();
return redirect('/greeting/')->with('status', '更新処理完了!');
}
削除
/*-------------------------------------------------------
* 削除
--------------------------------------------------------*/
public function destroy($id)
{
$greeting = Greeting::findOrFail($id);
$greeting->delete();
$data = Greeting::all();
return redirect('/greeting/')->with('status', '削除処理完了!')->with('data',$data);
}
2. Bladeテンプレート
コントローラのメソッドにあわせたビュー名に変更します。
一覧表示
all.blade.php ⇒ index.blade.php
入力画面
greeting.blade.php ⇒ create.blade.php
フォームのアクションは "greeting" のみでOKです。
<form class="form-signin" role="form" method="post" action="{{url('/greeting')}}">
HTTPメソッドが POST なのでGreetingControllerのstoreメソッドにアクセスしてくれます。
編集画面
edit.balde.php は名前はこのままでOKですね。
フォームのアクションは "greeting" のみでOKです。
<form class="form-signin" role="form" method="post" action="{{url('/greeting',$data->id)}}">
HTTPメソッドは隠しメソッドで "PATCH" に指定しているのでGreetingControllerのupdateメソッドにアクセスしてくれます。
3. グローバルメニューの修正
グローバルメニューの箇所を修正します。
:
<div id="navbar" class="collapse navbar-collapse">
<?php $var = $_SERVER["REQUEST_URI"]; ?>
<?php $link_navi = ""; ?>
<?php if(preg_match("/greeting$/", $var)){ $link_navi = "一覧表示"; } ?>
<?php if(preg_match("/create/", $var)){ $link_navi = "入力フォーム"; } ?>
<ul class="nav navbar-nav">
<li @if($link_navi=='一覧表示')class="active"@endif><a href="/greeting/">一覧表示</a></li>
<li @if($link_navi=='入力フォーム')class="active"@endif><a href="/greeting/create">入力フォーム</a></li>
</ul>
</div>
:
4. ルーティングの設定
前回のルーティングの設定はこのように記述していました。
Route::get('/greeting', 'GreetingController@getIndex'); /*index*/
Route::post('/greeting', 'GreetingController@postIndex'); /*index*/
Route::get('greeting/all', 'GreetingController@all'); /*一覧画面*/
Route::get('greeting/edit/{id}', 'GreetingController@edit'); /*編集画面*/
Route::patch('greeting/update/{id}', 'GreetingController@update'); /*編集フォーム⇒UPDATE処理*/
Route::delete('greeting/destroy/{id}', 'GreetingController@destroy'); /*削除*/
Route::resource を使うと上記で記述した内容が1行で済みます。
Route::resource('greeting', 'GreetingController');
URIを確認します。
php artisan route:list
はまったところ
RESTfulとは別にResourceful(リソースフル)という用語もチラチラと見かけます。
で、RESTfulの勉強でこの用語も調べてみました。
しかしResourcefulの意味を調べても中々出てこない。。
どうやらLaravelドキュメントの誤訳のようです。
Resourceful/リソースフル~Laravelのルーティング~
Laravelでは RESTful なControllerのひな形を簡単に作成することができます。
php artisan make:controller ProductController --resource
上記のコマンドで生成されたコントローラはRESTfulコントローラと呼ばれたりResourceコントローラと呼ばれたり。。
憶測ですがResourcefulという用語が生まれたのはこれが原因かもしれませんね。
仕事で Laravel を使っています。気づいたことや新しい発見など情報を発信していきます。問い合わせはこちら。







