質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Laravel

LaravelとはTaylor Otwellによって開発された、オープンソースなPHPフレームワークです。Laravelはシンプルで表現的なシンタックスを持ち合わせており、ウェブアプリケーション開発の手助けをしてくれます。

Amazon S3

Amazon S3 (Simple Storage Service)とはアマゾン・ウェブ・サービスが提供するオンラインストレージサービスです。

AWS(Amazon Web Services)

Amazon Web Services (AWS)は、仮想空間を機軸とした、クラスター状のコンピュータ・ネットワーク・データベース・ストーレッジ・サポートツールをAWSというインフラから提供する商用サービスです。

Q&A

解決済

2回答

10592閲覧

【Laravel】【AWS S3】LaravelでAWS S3に画像をアップロードできない(`400 Bad Request` )

NULL_000000

総合スコア3

Laravel

LaravelとはTaylor Otwellによって開発された、オープンソースなPHPフレームワークです。Laravelはシンプルで表現的なシンタックスを持ち合わせており、ウェブアプリケーション開発の手助けをしてくれます。

Amazon S3

Amazon S3 (Simple Storage Service)とはアマゾン・ウェブ・サービスが提供するオンラインストレージサービスです。

AWS(Amazon Web Services)

Amazon Web Services (AWS)は、仮想空間を機軸とした、クラスター状のコンピュータ・ネットワーク・データベース・ストーレッジ・サポートツールをAWSというインフラから提供する商用サービスです。

0グッド

1クリップ

投稿2021/12/23 04:00

編集2021/12/23 04:13

前提・実現したいこと

LaravelでAWS S3に画像をアップロードする機能を実装しています。
以下のようなエラーが発生しました。

  • The bucket does not allow ACLs
  • 400 Bad Request

原因がわかる方がいましたら、ぜひ教えていただきたいです。

イメージ説明

発生している問題・エラーメッセージ

Error executing "PutObject" on "https://laravel-vue-app-to-do-sengen-backet.s3.ap-northeast-1.amazonaws.com/image/hbzqDxchRSed2TNRlDXeKe5gIfAmMaWQoDrr9JKu.jpg"; AWS HTTP error: Client error: `PUT https://laravel-vue-app-to-do-sengen-backet.s3.ap-northeast-1.amazonaws.com/image/hbzqDxchRSed2TNRlDXeKe5gIfAmMaWQoDrr9JKu.jpg` resulted in a `400 Bad Request` response: <?xml version="1.0" encoding="UTF-8"?> <Error><Code>AccessControlListNotSupported</Code><Message>The bucket does not all (truncated...) AccessControlListNotSupported (client): The bucket does not allow ACLs - <?xml version="1.0" encoding="UTF-8"?> <Error><Code>AccessControlListNotSupported</Code><Message>The bucket does not allow ACLs</Message><RequestId>HYC4E3ZWN7X4JMJ5</RequestId><HostId>TqhxfWxKiliOEGYh5lr/gM27uQXfyS8ZgYc5E11Lp6uig72kw/alhA+xZyFkeqegtSHcYXEEuOg=</HostId></Error>

該当のソースコード

.env(実際には入力されています)

AWS_ACCESS_KEY_ID= csvの認証情報に記載されているAccess key ID AWS_SECRET_ACCESS_KEY= csvの認証情報に記載されているSecret access key AWS_DEFAULT_REGION=ap-northeast-1 (リージョンをアジアパシフィック東京で作成したため) AWS_BUCKET= 作成したバケット名

app/Http/Controllers/UserController.php

PHP

1<?php 2 3namespace App\Http\Controllers; 4 5// use App\Http\Requests\UserRequest; 6use App\User; 7use Illuminate\Http\Request; 8use Illuminate\Support\Facades\Hash; 9use Illuminate\Support\Facades\Storage; 10use Illuminate\Support\Facades\Validator; 11 12class UserController extends Controller 13{ 14 //略 15 16        //プロフィール編集画面 17 public function edit(string $name) 18 { 19 $user = User::where('name', $name)->first(); 20 21 return view('users.edit', ['user' => $user]); 22 } 23 24 //プロフィール編集処理 25 public function update(Request $request, string $name) 26 { 27 28 $user = User::where('name', $name)->first(); 29 $allRequest = $request->all(); 30 31 // $profileImage = $request->file('image'); 32 // dd($profileImage); 33 // if ($profileImage) { 34 // $allRequest['image'] = $this->saveProfileImage($profileImage, $user->id); 35 // } 36 37 //s3アップロード開始 38 $image = $request->file('image'); 39 // バケットの`myprefix`フォルダへアップロード 40 $path = Storage::disk('s3')->putFile('image', $image, 'public'); 41 // アップロードした画像のフルパスを取得 42 $user->image = Storage::disk('s3')->url($path); 43 44 $user->fill($allRequest)->save(); 45 return redirect()->route('users.show', ["name" => $user->name]); 46 } 47 48 //略 49} 50

database/migrations/2014_10_12_000000_create_users_table.php

PHP

1public function up() 2{ 3 Schema::create('users', function (Blueprint $table) { 4 $table->bigIncrements('id'); 5 $table->string('name')->unique(); 6 $table->string('email')->unique(); 7 $table->timestamp('email_verified_at')->nullable(); 8 $table->string('twitter_id')->nullable(); 9 $table->string('password')->nullable(); 10 $table->string('image')->nullable(); 11 $table->rememberToken(); 12 $table->timestamps(); 13 }); 14}

resources/views/users/edit.blade.php

PHP

1<form action="{{ route('users.update', ['name' => $user->name]) }}" method="POST" enctype="multipart/form-data"> 2 @method('PATCH') 3 @csrf 4 {{-- 編集フォーム --}} 5 <label for="image"> 6 <img src="{{ asset('storage/'.$user->image) }}" id="img" class="img-fuild rounded-circle" width="80" height="80"> 7 <input type="file" id="image" name="image" onchange="previewImage(this);" class="d-none"> 8 </label> 9 <div class="md-form col-lg-6 col-md-7 col-sm-8 col-xs-10 mx-auto"> 10 <label for="name">ユーザー名</label> 11 <input type="text" class="form-control" id="name" name="name" required value="{{ $user->name }}"> 12 <small>315文字で入力してください</small> 13 </div> 14 <div class="md-form col-lg-6 col-md-7 col-sm-8 col-xs-10 mx-auto"> 15 <label for="email">メールアドレス</label> 16 <input type="text" class="form-control" id="email" name="email" required value="{{ $user->email }}"> 17 </div> 18 <button type="submit" class="btn btn-block cyan darken-3 text-white col-lg-8 col-md-9 col-sm-10 col-xs-12 mx-auto mt-5 mb-5 waves-effect"> 19 更新する 20 </button> 21</form>

S3 バケットポリシー

{ "Version": "2012-10-17", "Id": "Policy1640118455749", "Statement": [ { "Sid": "Stmt1640118449406", "Effect": "Allow", "Principal": { "AWS": "arn:aws:iam::580365198874:user/laravel-vue-app-to-do-sengen" }, "Action": [ "s3:ListBucket", "s3:GetObject", "s3:GetObjectAcl", "s3:PutObject", "s3:PutObjectAcl", "s3:ReplicateObject", "s3:DeleteObject" ], "Resource": [ "arn:aws:s3:::laravel-vue-app-to-do-sengen-backet", "arn:aws:s3:::laravel-vue-app-to-do-sengen-backet/*" ] } ] }

routes/web.php

PHP

1//ユーザーページ表示 2Route::prefix('users')->name('users.')->group(function () { 3 Route::get('/{name}', 'UserController@show')->name('show'); 4 //プロフィール編集画面 5 Route::get('/{name}/edit', 'UserController@edit')->name('edit'); 6 //プロフィール編集処理 7 Route::patch('/{name}/update', 'UserController@update')->name('update'); 8 Route::get('/{name}/likes', 'UserController@likes')->name('likes'); 9 Route::get('/{name}/followings', 'UserController@followings')->name('followings'); 10 Route::get('/{name}/followers', 'UserController@followers')->name('followers'); 11 Route::middleware('auth')->group(function () { 12 Route::put('/{name}/follow', 'UserController@follow')->name('follow'); 13 Route::delete('/{name}/follow', 'UserController@unfollow')->name('unfollow'); 14 }); 15});

app/User.php

PHP

1 protected $fillable = [ 2 'name', 'email', 'password', 'twitter_id', 'image', 3 ]; 4

試したこと

  • 環境変数の見直し
  • バケットポリシーの見直し

補足情報(FW/ツールのバージョンなど)

Laravel 6.2
PHP 7.4.25
composer 2.1.12
node 16.13

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

解決しました。
【S3 bucket】の【オブジェクト所有者】の【ACL】の設定を【無効】から【有効】に変更するとエラーが解決しました。

投稿2021/12/25 14:43

NULL_000000

総合スコア3

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ベストアンサー

Access Deniedなので権限周りのエラーなのは間違いないでしょう。

気になるのはエラーの中の
The bucket does not allow ACL
という文言ですね。

もしかするとこちらと同じ事象かもしれません。
For an Amazon S3 bucket deplolyent from Guithub how do I fix the error AccessControlListNotSupported: The bucket does not allow ACLs?

S3のアクセスコントロールは色々あって複雑ですが、それが同IAMのほうで許可しているならバケットポリシーは設定しなくてもいいはずです。
S3のバケットポリシーでハマったので、S3へのアクセスを許可するPrincipalの設定を整理する

あと、質問の前にエラーの文章を読んでそれについて調べる癖をつけるといいです。

投稿2021/12/23 06:58

yu_1985

総合スコア7447

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

NULL_000000

2021/12/25 14:40

ご回答いただきありがとうございます! 紹介していただいたサイトを参考にIAMとS3のバケットポリシーを見直した結果、無事解決いたしました。 また、EC2にデプロイした際に発生したエラーも全て解決したため、開発環境、本番環境ともにAWS S3画像アップロード機能を実装することができました。 本当に感謝しています。また機会がありましたらよろしくお願いいたします。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問