【Laravel】ローカルディスクやAmazon S3にアップロードした画像をビューで表示する方法

はじめに

本記事では、ローカルディスクやAmazon S3にアップロードした画像をビューで表示する方法について説明しています。

なお、本記事では画像のアップロードする方法については説明していません。本記事は既に実装済みの画像アップロード処理に追加していく形で説明しているので、まだ実装していない方は以下の記事を参照して実装してください。

アップロードした画像の表示

テーブルの作成

以下のコマンドを実行して、アップロードした画像のURI(参照先)を保存しておくためのテーブルを作成します。

$ php artisan make:migration create_table_posts --table=posts

作成したマイグレーションファイル(database/migrations/Y_m_d_XXX_create_table_posts.php)を以下のように変更します。

    public function up()
    {
        Schema::create('posts', function (Blueprint $table) {
            $table->bigIncrements('id');
            # 以下の行を追加
            $table->string('image');
            $table->timestamps();
        });
    }

以下のコマンドを実行して、マイグレーションを実行します。

$ php artisan migrate

以下のコマンドを実行して、モデルを作成します。

$ php artisan make:model Post

コントローラーの実装

コントローラーを以下のように変更します。

    public function store(Request $request)
    {
        $post = new Post();

        # 画像ファイルのアップロード
        $image = $request->file('image');
        if ( app()->isLocal() || app()->runningUnitTests() ) {
            # 開発環境
            $path = $image->store('public/images');
            $post->image = Storage::url($path);
        }
        else {
            # 本番環境
            $path = Storage::disk('s3')->put('/', $image, 'public');
            $post->image = Storage::disk('s3')->url($path);
        }

        Auth::user()->posts()->save($post);

        return redirect()->route('posts.index');
    }

以下の行で作成したテーブルにアップロード画像のURIを保存しています。

# 開発環境
$post->image = Storage::url($path);

# 本番環境
$post->image = Storage::disk('s3')->url($path);

storeメソッドはstorage/app/public/〜というパスを返します。このパスはブラウザからは参照できません。ブラウザから参照するにはpublic/〜経由でアップロード画像を参照する必要があります。Storage::urlメソッドは、storage/app/public/〜public/〜に変換するメソッドになります。

シンボリックリンクの作成

以下のコマンドを実行して、storage/app/public/〜public/〜を紐付けるシンボリックリンクを作成します。このシンボリックリンクを作成することで、storage/app/public/〜に保存されたアップロード画像がpublic/〜経由で参照可能になります。

$ php artisan storage:link

ビューの実装

アップロード画像の参照可能なURIはテーブルに保存してあるので、以下のように記述するだけです。開発環境の場合はローカル(/public/storage/〜)のURIが、本番環境の場合はAmazon S3のURLが参照されます。

<img src="{{ $post->image }}" />

まとめ

保存される場所と参照する場所が違うため最初は複雑だと思うかもしれませんが、理解してしまえば難しいことはありません。

アップロードした画像がビューで表示できないという場合は、参照しているURIがstorage/app/public/〜になっている可能性があります。ブラウザからはpublic/〜しか参照できないため、URIの変換を忘れないようにしてください。

関連記事

開発環境(ローカルストレージ)と本番環境(Amazon S3)にトリミング+リサイズした画像を保存する方法
# はじめに 以前、以下の記事を書きました。 - [開発環境と本番環境で画像のアップロード先を分岐する方法 \- AUTOVICE](https://www.autovice.jp/articles/68) - [ローカルやAmazon [...]
2020年3月7日 11:56
Laravel Mixの仕組みをわかりやすく解説:CSSをSASS/SCSSで記述する方法
# はじめに Laravel Mixの仕組みをわかりやすく解説します。Laravel Mixを使ってアセットコンパイルを行うことで、SASS/SCSSでCSSを記述できるようになります。 # Laravel Mixの仕組み まずはじめに、 [...]
2020年3月6日 9:25
【Laravel 6.x】Laravelプロジェクトの名称を変更する方法
# はじめに あまりないケースではありますが、一度作成したLaravelプロジェクトの名称を変更する方法を解説します。ここで言うLaravelプロジェクトの名称とは、以下のコマンドの`Sample`のことを指します。 ```terminal [...]
2020年3月4日 16:24
【Laravel】Amazon S3へのアップロードが「403 Access Denied」で失敗する原因と対処方法
# はじめに LaravelでAmazon S3へ画像アップロードする処理を実装し、いざアップロードしようとしたところ、以下のエラーが出て失敗しました。 ``` Error executing "PutObject" on "https: [...]
2020年3月4日 13:33
開発環境と本番環境で画像のアップロード先を分岐する方法
# はじめに この記事では、以下の方針で画像のアップロード先を分岐する方法について解説しています。 - 開発環境:ローカル(storage/app/public/) - 本番環境:Amazon S3 # 事前準備 AWSに未登録の [...]
2020年3月4日 12:52
独自ポリシーの導入手順と注意点(ハマリポイント)を解説
# はじめに ユーザーと記事を関連付けておいて、編集や削除は記事の作成者のみ許可したいときにはポリシーを作成します。今回はポリシーの導入手順と注意点(ハマリポイント)を解説します。 # 導入手順 ## ポリシー作成 ターミナルで以下 [...]
2020年3月1日 10:32
ユーザー認証機能の導入手順と生成されたフォームを日本語化する方法を解説
# はじめに Laravelではユーザー認証機能の導入が簡単にできてしまいます。この記事ではLaravelプロジェクトにユーザー認証機能を追加する手順と、生成されたフォーム(デフォルトでは英語)を日本語化する方法を解説します。 # 前提 [...]
2020年2月29日 13:54
【Laravel 6.x】ネスト構造になっているRESTfulルーティングの定義方法
# はじめに RESTfulルーティングを定義するときは`Route::resource`を使いますが、ネスト構造になっているRESTfulルーティングの定義方法を調べたので記事にします。 # 前提 おそらく、Laravel 6.xのみ対 [...]
2020年2月28日 20:06