LaravelでIntervention Imageを使って加工した画像をS3へ保存する

LaravelでIntervention Imageを使って加工した画像をS3へ保存する:


はじめに

PHPで画像の加工を行う場合いろいろな方法がありますが、フレームワークにLaravelを利用している場合は「Intervention Image」がオススメです。

導入が簡単でリサイズやクロップの記述も簡単といいことずくめなのですが、

加工した画像をS3へアップロードする際に少し躓いたので備忘録として記します。


Intervention Image

http://image.intervention.io/getting_started/introduction

画像処理のライブラリであるGDと共にIntervention Imageをサーバへインストールします。

# yum install php-gd 
# systemctl reload httpd.service 
# php composer.phar require intervention/image 
Laravelの設定ファイルの$providers配列にIntervention Imageのサービスプロバイダを追加します。

config/app.php
'providers' => [ 
    Intervention\Image\ImageServiceProvider::class, 
], 
同じく設定ファイルの$aliases配列にファサードを追加します。

config/app.php
'aliases' => [ 
    'Image' => Intervention\Image\Facades\Image::class, 
], 
これだけで準備は完了です。


putメソッドを利用した画像アップロード

putメソッドを利用した場合は下記の様にシンプルに記述できます。

生成されたIntervention Imageのインスタンスをstringへキャストするのがポイントでしょうか。

app/Http/Controllers/SampleController.php
<?php 
 
namespace App\Http\Controllers; 
 
use Illuminate\Http\Request; 
use Illuminate\Support\Facades\Storage; 
use Intervention\Image\Facades\Image; 
 
class SampleController extends Controller 
{ 
     /** 
     * Handle a image upload request for the application. 
     * 
     * @param  $request 
     * @return \Illuminate\Http\Response 
     */ 
    public function upload(Request $request) 
    { 
        // バリデーション 
        Validator::make($request->all(), [ 
            'image' => 'file|image|max:1024|nullable' 
        ])->validate(); 
 
        if ($request['image']) { 
            $file = $request->file('image'); 
            $name = $file->getClientOriginalName(); 
 
            // 画像を横幅300px・縦幅アスペクト比維持の自動サイズへリサイズ 
            $image = Image::make($file) 
                ->resize(300, null, function ($constraint) { 
                    $constraint->aspectRatio(); 
                }); 
 
            // envファイルに定義したS3のパスへ画像をアップロード 
            Storage::put(env('S3_SAMPLE_PATH').$name, (string) $image->encode()); 
        } 
 
        return redirect()->route('index'); 
    } 
} 


putFileAsメソッドを利用した画像アップロード

putメソッドを利用できれば簡単でしたが、実際にはS3へアップする際にファイル名を指定したい場合もあるでしょう。

その場合はputFileAsメソッドを利用するのですが、putメソッドのようにシンプルな記述でできずに悩みました。

リサイズした画像をいったんローカルへ保存し、S3へアップロードした後にローカルから削除する、といった流れで行っています。

app/Http/Controllers/SampleController.php
<?php 
 
namespace App\Http\Controllers; 
 
use Carbon\Carbon; 
use Illuminate\Http\File; 
use Illuminate\Http\Request; 
use Illuminate\Support\Facades\Storage; 
use Intervention\Image\Facades\Image; 
 
class SampleController extends Controller 
{ 
     /** 
     * Handle a image upload request for the application. 
     * 
     * @param  $request 
     * @return \Illuminate\Http\Response 
     */ 
    public function upload(Request $request) 
    { 
        // バリデーション 
        Validator::make($request->all(), [ 
            'image' => 'file|image|max:1024|nullable' 
        ])->validate(); 
 
        if ($request['image']) { 
            $now = date_format(Carbon::now(), 'YmdHis'); 
            $file = $request->file('image'); 
            $name = $file->getClientOriginalName(); 
 
            // 画像を横幅300px・縦幅アスペクト比維持の自動サイズへリサイズして一時ファイル保存先へ格納 
            $tmp = storage_path('app/tmp/') . $now . '_' . $name; 
            $image = Image::make($file) 
                ->resize(300, null, function ($constraint) { 
                    $constraint->aspectRatio(); 
                }) 
                ->save($tmp); 
 
            // envファイルに定義したS3のパスへ指定したファイル名で画像をアップロード 
            Storage::putFileAs(env('S3_SAMPLE_PATH'), new File($tmp), $file, 'public'); 
 
            // 一時ファイルを削除 
            Storage::disk('local')->delete(['tmp/'.$now.'_'.$title, 'tmp/'.$now.'_prev_'.$title]); 
        } 
 
        return redirect()->route('index'); 
    } 
} 


おわりに

putメソッドがシンプルな記述だったので、putFileAsメソッドでも同様にできると油断したため、予想以上にはまってしまいました。

コメント

このブログの人気の投稿

投稿時間:2021-06-17 05:05:34 RSSフィード2021-06-17 05:00 分まとめ(1274件)

投稿時間:2021-06-20 02:06:12 RSSフィード2021-06-20 02:00 分まとめ(3871件)

投稿時間:2020-12-01 09:41:49 RSSフィード2020-12-01 09:00 分まとめ(69件)