LaravelでWeb APIを開発するときの話

LaravelでWeb APIを開発する時ってどうしていますか?

routeをapi.phpに入れると…

api/ほげほげになりますよね

これってWeb API開発をする時ってメンドくさくなりますよね

http://localhost/hogeservice/v1/fuge

とバージョン(v1)以下にプロジェクトを差し込んで運用を考えるとapi.phpに入れると変になります

http://localhost/hogeservice/v1/api/fuge

になってします

これを対策にweb.phpに入れると解決しますが…

ダサいです。

ちゃんとapiなのでapi.phpに入れて開発したいのでその対策を考えてみます

開発環境

はじめに開発環境を確認します

$ php -v
PHP 8.1.11 (cli) (built: Sep 29 2022 20:02:53) (NTS)
Copyright (c) The PHP Group
Zend Engine v4.1.11, Copyright (c) Zend Technologies
    with Zend OPcache v8.1.11, Copyright (c), by Zend Technologies
$ composer -V
Composer version 2.4.2 2022-09-14 16:11:15
$ php artisan -V
Laravel Framework 9.38.0

変更箇所

変更箇所はシンプルです。

app/Providers/RouteServiceProvider.php

$this->routes(function () {
    Route::middleware('api')
        ->prefix('api')
        ->group(base_path('routes/api.php'));

Route::middleware('api')
    ->group(base_path('routes/api.php'));

と prefixを削ればOKです

これで

変更前が

$ curl http://localhost:8000/api/bird
"hello!"

だったものが

$ curl http://localhost:8000/api/bird

404エラー

$ curl http://localhost:8000/bird
"hello!"

と/apiなしでアクセスできます

終いに

今回はlaravelのweb api開発でapi.phpを使った方法を書いてみました。

web.phpに書いたらちょっと違うかななんて思ったので記事にしてみました

そうすると、web.phpとapi.php両方に書いたらどうなるのか?と思うでしょうが確認するとweb.phpが採用されました。なんででしょうねw

メモ

動作検証用のプロジェクトの作成とかはこんな感じで

$ composer create-project laravel/laravel laravel-api-sample

$ php artisan create:controller BirdController
class BirdController extends Controller
{
    public function index(){
        $message = 'hello!';

        return response()->json($message);
    }
    public function index2(){
        $message = 'hello!2';

        return response()->json($message);
    }
}

routes/api.php

Route::get('/bird' , [BirdController::class,'index']);

動作検証用 : web.phpとapi.phpの優先順位調査

routes/web.php

Route::get('/bird' , [BirdController::class,'index2']);

api.phpとweb.phpに同じpathを入れると

$ curl http://localhost:8000/bird
"hello!2"

web.phpが採用される