☺️

LaravelのDocker環境を簡単に構築できるLaravel Sailを使ってみた

7 min read

Laravel Sailを使うと簡単にDockerの開発環境を構築できると社内で耳にしたので,どんなものかざっくり使ってみました.

実行環境は以下になります.

OS : MacOS Catalina(バージョン10.15.2)
Docker version :  20.10.8

インストールと起動

日本語バージョンのドキュメント記載通り,コマンドを実行します.利用するサービスとしてmysqlとredisを選択しました.

curl -s "https://laravel.build/example-app?with=mysql,redis" | bash

完了すると,example-app/内にdocker-compose.ymlとLaravelの初期ファイルが作成されています.
移動をし,docker-composeを起動します.

(追記)
日本語バージョンのドキュメントだとdocker-composeコマンドではなく./vendor/bin/sailでやっていることに後で気が付きました.(docker-composeでも動くと確認できた一つの知見だと思えばいいか)

cd example-app
docker-compose up -d

docker-composeコマンド時に次のような警告が出ました.環境変数とかが足りてないぽかったですが,動きはしたので一旦無視しました.

WARN[0000] The "WWWGROUP" variable is not set. Defaulting to a blank string.
WARN[0000] The "WWWUSER" variable is not set. Defaulting to a blank string.

これでmysqlとlaravel, redisの3つのコンテナが立ち上がます.
http://localhost を開くとLaravelのデフォルトページを表示できました.
なんて簡単.

PHPのバージョンは8.0.10でした.

docker-compose exec laravel.test php -v
...
PHP 8.0.10 (cli) (built: Aug 26 2021 15:50:25) ( NTS )

API作成,実行

APIを追加して動くか確認をしていきます.
まずはコントローラを作成します.

docker-compose exec laravel.test php artisan make:controller GetInitController

作成されたGetInitController.phpを次のように編集します

GetInitController.php
class GetInitController extends Controller
{
    public function index() {
        return 'GetInitController@index';
    }
}

api.phpにエンドポイントを追記します.

※コントローラのファイル指定方法がLaravel8から若干変わっているようなのでご注意を(今回は「web.phpで完全な名前空間を使用する」に寄せています)
参考 : Laravel8を試したら即効でエラー「Target class [〇〇〇Controller] does not exist.」が表示された

api.php
Route::get('init', 'App\Http\Controllers\GetInitController@index');

これでhttp://localhost/api/init にアクセスすると,GetInitController.phpでreturnした'GetInitController@index'がレスポンスとして返ってくることを確認できました.

テスト実行

テストを実行してみます.

docker-compose exec laravel.test ./vendor/bin/phpunit

実行結果は次のようになり,テストが実行できることを確認できました.

OK (2 tests, 2 assertions)

マイグレーション実行

マイグレーションファイルを作成します.

docker-comopose exec laravel.test php artisan make:migration create_articles_table

作成されたCreateArticlesTable.phpを次のように編集します.

CreateArticlesTable.php
public function up()
{
    Schema::create('articles', function (Blueprint $table) {
        $table->id();
        $table->string('title');
        $table->string('contents');
        $table->timestamps();
    });
}

マイグレーションを実行します.

docker-compose exec laravel.test php artisan migrate

DBに入ってテーブルが作成されているか確認をします.(面倒くさいのでパスワードを直書きしてしまっていますが,コマンドの履歴に残るので注意が必要です)

mysql -u root -h 127.0.0.1 -P 3306 -ppassword
use example_app;
show columns from articles;

show columns文で結果が次のようになり,マイグレーションが流されていることを確認できました.

+------------+---------------------+------+-----+---------+----------------+
| Field      | Type                | Null | Key | Default | Extra          |
+------------+---------------------+------+-----+---------+----------------+
| id         | bigint(20) unsigned | NO   | PRI | NULL    | auto_increment |
| title      | varchar(255)        | NO   |     | NULL    |                |
| contents   | varchar(255)        | NO   |     | NULL    |                |
| created_at | timestamp           | YES  |     | NULL    |                |
| updated_at | timestamp           | YES  |     | NULL    |                |
+------------+---------------------+------+-----+---------+----------------+

Seeder実行

Seederクラスを作成します.

docker-compose exec laravel.test php artisan make:seeder ArticlesTableSeeder

作成したArticlesTableSeeder.phpを次のように編集します.

ArticlesTableSeeder.php
<?php

namespace Database\Seeders;

use Illuminate\Database\Seeder;
use Illuminate\Support\Facades\DB;

class ArticlesTableSeeder extends Seeder
{
    /**
     * Run the database seeds.
     *
     * @return void
     */
    public function run()
    {
        DB::table('articles')->insert([
            'title' => 'titiletitiletitile',
            'contents' => 'contentscontentscontents',
        ]);
        DB::table('articles')->insert([
            'title' => 'あああああ',
            'contents' => '日本語',
        ]);
    }
}

Seederを実行します.

docker-compose exec laravel.test php artisan db:seed --class=ArticlesTableSeeder

DBに入ってレコードが追加されているか確認します.

mysql -u root -h 127.0.0.1 -P 3306 -ppassword
use example_app;
select * from articles;

select文で結果が次のようになり,Seederの実行を確認できました.

+----+--------------------+--------------------------+------------+------------+
| id | title              | contents                 | created_at | updated_at |
+----+--------------------+--------------------------+------------+------------+
|  1 | titiletitiletitile | contentscontentscontents | NULL       | NULL       |
|  2 | あああああ              | 日本語                     | NULL       | NULL       |
+----+--------------------+--------------------------+------------+------------+
2 rows in set (0.00 sec)

DBからデータを取得

DBからデータを取得し,レスポンスできるか確認します.
DBにアクセスできるようにするためにArticleテーブルのモデルを作成します.

docker-compose exec laravel.test php artisan make:model Articles

作成したArticles.phpを次のように編集します.

Articles.php
class Articles extends Model
{
    use HasFactory;

    protected $fillable = [
        'title',
        'contents',
    ];
}

DBからデータを取得するコントローラを作成します.

docker-compose exec laravel.test php artisan make:controller GetArticlesController

作成したGetArticlesController.phpを次のように編集します.

GetArticlesController.php
class GetArticlesController extends Controller
{
    public function index()
    {
        return DB::table('articles')->find(1);
    }
}

api.phpにエンドポイントを追記します.

api.php
Route::get('articles', 'App\Http\Controllers\GetArticlesController@index');

http://localhost/api/articles にアクセスして次のようなDBのレコードのレスポンスが返ってきていることを確認できました.

{"id":1,"title":"titiletitiletitile","contents":"contentscontentscontents","created_at":null,"updated_at":null}

redisへの保存・取得

新しいコントローラを作るのが面倒くさくなってきたので,GetInitController.phpを次のように編集します.

GetInitController.php
use Illuminate\Support\Facades\Redis;

class GetInitController extends Controller
{
    public function index() {
        Redis::set('name', 'Taylor');
        return Redis::get('name');
    }
}

http://localhost/api/init にアクセスして'Taylor'が返ってきていることを確認し,
Redis::set('name', 'Taylor');の部分をコメントアウトしてhttp://localhost/api/init をリロードしても'Taylor'が返ってきているので,redisへの保存・取得を確認できました.

使ってみた感想

非常に簡単にLaravelのDocker環境を構築して,基本的な動作確認も問題なしでした.docker-compose.ymlを覗いてみると,ありがたいことに色々な設定がデフォルトでされていますが,消しておいても良い設定もありそうです.軽くLaravelで動作をみたいというときには,オススメの方法でした.

Discussion

ログインするとコメントできます