[Laravel]ルーティングファイルを分割して管理する

Laravelでは基本`route/web.php`にルーティングを書いていくことになります。
APIルーティングを書く場合は`api.php`に書くこともあるかと思います。

今回は、アレコレと編集をして新しいルーティングファイルを追加したいと思います。

### 手順１ 新しいルーティングファイルを作成
routeディレクトリ内に新しいルーティングファイルを作ります。[

```php

routes/batch.php
```

作成したファイルに、適当にルーティングを書いておきましょう。

```php:batch.php
<?php

Route::get('/', function() {
    return 'hoge';
});
```

### 手順2 サービスプロバイダに登録
`app/Providers/RouteServiceProvider.php`に作成したファイルを登録します。

Before↓

```php:RouteServiceProvider.php

<?php

namespace App\Providers;

use Illuminate\Support\Facades\Route;
use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;

class RouteServiceProvider extends ServiceProvider
{
    /**
     * This namespace is applied to your controller routes.
     *
     * In addition, it is set as the URL generator's root namespace.
     *
     * @var string
     */
    protected $namespace = 'App\Http\Controllers';

    /**
     * Define your route model bindings, pattern filters, etc.
     *
     * @return void
     */
    public function boot()
    {
        //

        parent::boot();
    }

    /**
     * Define the routes for the application.
     *
     * @return void
     */
    public function map()
    {
        $this->mapApiRoutes();

        $this->mapWebRoutes();

        //
    }

    /**
     * Define the "web" routes for the application.
     *
     * These routes all receive session state, CSRF protection, etc.
     *
     * @return void
     */
    protected function mapWebRoutes()
    {
        Route::middleware('web')
             ->namespace($this->namespace)
             ->group(base_path('routes/web.php'));
    }

    /**
     * Define the "api" routes for the application.
     *
     * These routes are typically stateless.
     *
     * @return void
     */
    protected function mapApiRoutes()
    {
        Route::prefix('api')
             ->middleware('api')
             ->namespace($this->namespace)
             ->group(base_path('routes/api.php'));
    }
}

```

After↓

```php:RouteServiceProvider.php
<?php

namespace App\Providers;

use Illuminate\Support\Facades\Route;
use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;

class RouteServiceProvider extends ServiceProvider
{
    /**
     * This namespace is applied to your controller routes.
     *
     * In addition, it is set as the URL generator's root namespace.
     *
     * @var string
     */
    protected $namespace = 'App\Http\Controllers';

    /**
     * Define your route model bindings, pattern filters, etc.
     *
     * @return void
     */
    public function boot()
    {
        parent::boot();
    }

    /**
     * Define the routes for the application.
     *
     * @return void
     */
    public function map()
    {
        $this->mapApiRoutes();

        $this->mapWebRoutes();
        // map〇〇Routesメソッドでルーティングをマッピング(展開)する
        $this->mapBatchRoutes();
    }

    /**
     * Define the "web" routes for the application.
     *
     * These routes all receive session state, CSRF protection, etc.
     *
     * @return void
     */
    protected function mapWebRoutes()
    {
        Route::middleware('web')
             ->namespace($this->namespace)
             ->group(base_path('routes/web.php'));
    }

    /**
     * Define the "api" routes for the application.
     *
     * These routes are typically stateless.
     *
     * @return void
     */
    protected function mapApiRoutes()
    {
        Route::prefix('api')
             ->middleware('api')
             ->namespace($this->namespace)
             ->group(base_path('routes/api.php'));
    }

    // 作成したルーティングファイルを書く
    /**
     * Define the "batch" routes for the application.
     *
     * These routes are typically stateless.
     *
     * @return void
     */
    protected function mapBatchRoutes()
    {
        Route::prefix('batch')
             ->middleware('batch')
             ->namespace($this->namespace)
             ->group(base_path('routes/batch.php'));
    }
}
```
### 補足

何やらRouteに色々くっつけて書かれてますね。
代表的なオプションメソッドの機能を書いておきます。

お好みで

| 種類             |      機能          | 
|:-----------------|------------------:|
| [prefix](https://readouble.com/laravel/6.x/ja/routing.html)| ルーティングURLの頭に共通のURLを付けられる | 
| [middleware](https://readouble.com/laravel/6.x/ja/routing.html#route-group-middleware) | ルーティングに共通のミドルウェア(前処理)を適用できる。ミドルウェアの設定は`app/Http/kernel.php`で行う | 
| [namespace](https://readouble.com/laravel/6.x/ja/routing.html#route-group-namespaces)       | 名前空間の定義(Contrllerを繋ぐ時のパスの起点を指定できる)|
| [group](https://readouble.com/laravel/6.x/ja/routing.html#route-groups)               |ヒゲカッコ{}で囲んだルーティング群にオプションを一括して適用する。|

Beforeの時点のRouteServiceProviderを見てみると、`mapApiRoutes `には`prefix('api')`が付いてますね。
なので、api.phpに書かれたルートに繋ぐには`homepage.jp/api/xxxx`というURLで繋がるということが分かります。

#### web.phpとapi.phpの使い分け

もう一つ、自分が学びはじめに思った疑問「`web.php`があるのに、`api.php`があるのはなぜ?」という点について補足します。

端的にいうと「アプリケーションを管理しやすくするためにルーティングをファイル単位で分けているだけ」です。

webアプリケーションはblade(HTMLとDBなどから取得したデータ)を返すのに対し、
APIは一部のルーティングを除いて大多数のアクションはDBから取得したデータをJSONなどの形式で返却します(SPAアプリケーションに多い)。

実質的にはどちらも同じルーティングファイルなので、apiの処理を`web.php`に書いたりしても問題ありません。
(ただ、Laravelは`App\Http\kernel.php`に各ルーティングのミドルウェアを設定しているので、色々と設定の確認・編集が必要です)

### まとめ
ユーザーと管理者の二面アプリケーションを作成する時なんかは、ファイル単位でルーティングも分けたくなります。
そういったケースがあったら試してみてください!