Laravel 5のストレージファサードを使用してファイルURLを取得するにはどうすればよいですか?


83

私はLaravel5との新しいFlysystem統合を使用して実験してきました。DBへの「ローカライズされた」パスを保存し、ストレージファサードにパスを完成させています。たとえば、私は保存screenshots/1.jpgして使用しています

Storage::disk('local')->get('screenshots/1.jpg')

または

Storage::disk('s3')->get('screenshots/1.jpg') 

異なるディスクで同じファイルを取得できます。

get ファイルの内容を取得しますが、次のようにビューで使用したいと考えています。

<img src="{{ Storage::path('screenshots/1.jpg') }}" />

しかし、パス、またはフルパスを取得できるものは利用できません(私が見る限り)。では、どうすればフルパスを返すことができますか?または、これは仕様によるものかどうか疑問に思いますか?もしそうなら、なぜ私はフルパスを取得できないはずですか?それとも、私はこれを完全に間違った方法で行っていますか?


1
パスではなくURLを要求しています。
アダム

回答:


54

編集:L5.2 +のソリューション

より良く、より簡単な解決策があります。

Storage::url($filename)特定のファイルのフルパス/ URLを取得するために使用します。次のS3場所でストレージファイルシステムとして設定する必要があることに注意してくださいconfig/filesystems.php'default' => 's3'

もちろん、Storage::disk('s3')->url($filename)同じようにすることもできます。

ご覧のとおり、クラウドファイルシステムを参照config/filesystems.phpするパラメーターも'cloud' => 's3'定義されています。ローカルサーバーのストレージフォルダーを管理したいが、クラウドでいくつかのファイルを取得/保存したい場合Storage::cloud()は、同じファイルシステムメソッドを使用しますStorage::cloud()->url($filename)

Laravelのドキュメントにはこのメソッドについては記載されていませんが、詳細を知りたい場合は、ここでソースコードを確認できます


いいね!これは新しい方法ですが、今ここにあるのはうれしいです!Storageクラスはデフォルトでビューで機能しますか?もしそうなら、これを正解としてマークします。
daviestar 2016

はい!デフォルトでビューで機能するため、心配する必要はありません。
Pere Joan Martorell 2016

5
これはL5.2 +用です
daviestar 2016

154

ストレージディスクへのパスは次のようになります。

$storagePath  = Storage::disk('local')->getDriver()->getAdapter()->getPathPrefix()

私はそれに対するより短い解決策を知りません...

$ storagePathをビューと共有してから、

$storagePath."/myImg.jpg";

これは、パブリックストレージフォルダのパスを取得するのに最適なソリューションです。ありがとう!
デビッド

14
もう一つの方法は、使用することですapplyPathPrefix。このように:Storage::disk('local')->getDriver()->getAdapter()->applyPathPrefix('myImg.jpg');
マキシムラニン

3
@maximLanin:どういうわけか、例をコピーすると、最後の(applyPathPrefix)のhとP(path * Prefix)の間に奇妙な文字が含まれます。それをコピーして貼り付けると、エラーが発生します。最初にapplyPathPrefixコピーできます。非常に奇妙な。(あなたの例では、ダブルクリックして、最後のメソッド名を、それをテストすることができます。
モーリス・

3
getDriver()必要ありません。単にStorage::disk('local')->getAdapter()->getPathPrefix()同様に機能します。
RA。

6
Laravel 5.4以降、新しい簡単な方法があることを知っておくとよいでしょう。Bilalの回答をStorage::path参照してください
Marten Koetsier 2018

69

このメソッドはLaravel5.4以降に存在し、次の方法で取得できます。

$path = Storage::disk('public')->path($filename);

1
Laravel5.6のチャームのように機能します。誰かがAPIでこれについて疑問に思っているなら、ここにあります:laravel.com/api/5.6/Illuminate/Filesystem/…–
Angel Santiago Jaime Zavala

1
私が見る限り、このメソッドはLaravel 5.4(laravel.com/api/5.4/Illuminate/Filesystem/…)以降に存在します
Marten Koetsier

上記の2つのコメントのリンクは両方とも無効です。
DOTNET

9

これが私がそれを機能させる方法です-環境変数を使用してs3とローカルディレクトリパスを切り替え、パスをすべてのビューに渡します。

.envの場合:

APP_FILESYSTEM=local or s3
S3_BUCKET=BucketID

config / filesystems.php:

'default' => env('APP_FILESYSTEM'),

app/Providers/AppServiceProvider

public function boot()
{
    view()->share('dynamic_storage', $this->storagePath());
}

protected function storagePath()
{
    if (Storage::getDefaultDriver() == 's3') {
        return Storage::getDriver()
                ->getAdapter()
                ->getClient()
                ->getObjectUrl(env('S3_BUCKET'), '');
    }

    return URL::to('/');
}

1
説明どおりにs3ストレージを使用すると、エラーが発生しました。だから私はこれに例を修正しました return Storage::disk('s3')->getDriver()->getAdapter()->getClient()->getObjectUrl(env('S3_BUCKET'), '').'/';
ライオネルモリソン

5

以下のように、最初にファイルのURL /リンクを取得し、次にパスを取得します。

$url = Storage::disk('public')->url($filename);
$path = public_path($url);

5

ストレージ(ディスク)パスを表示するだけの場合は、次を使用します。

Storage::disk('local')->url('screenshots/1.jpg'); // storage/screenshots/1.jpg
Storage::disk('local')->url(''): // storage

また、興味があれば、Laravel専用のパッケージ(https://github.com/fsasvari/laravel-uploadify)を作成したので、Eloquentモデルフィールドでこれらすべてのフィールドを使用できます。

$car = Car::first();

$car->upload_cover_image->url();
$car->upload_cover_image->name();
$car->upload_cover_image->basename();
$car->upload_cover_image->extension();
$car->upload_cover_image->filesize();

4

さて、数週間前、私は非常によく似た質問をしました(ストレージを介してアップロードされたファイルからCDN URLを取得します):CDN URLが私のビューに画像を表示するようにしました(必要に応じて)。

ただし、パッケージAPIを確認した後、このタスクを実行する方法がないことを確認しました。したがって、私の解決策は、の使用を避けることflysystemでした。私の場合、RackSpaceで遊ぶ必要がありました。それで、最終的に、自分のuseパッケージを作成し、PHP SDK forOpenStackを使用して独自のストレージパッケージを作成することにしました。

このようにgetPublicUrl()して、cdnコンテナからパブリックURLを取得するために必要な関数へのフルアクセスが可能になります。

/** @var DataObject $file */
$file = \OpenCloud::container('cdn')->getObject('screenshots/1.jpg');

// $url:  https://d224d291-8316ade.ssl.cf1.rackcdn.com/screenshots/1.jpg
$url = (string) $file->getPublicUrl(UrlType::SSL);

結論として、ストレージサービスを別のレベルに引き上げる必要がある場合flysystemは、それだけでは不十分です。local目的、あなたはnXuのソリューション@試すことができます


3

ファイルの絶対URLが必要な場合は、以下のコードを使用してください。

$file_path = \Storage::url($filename);
$url = asset($file_path);
// Output: http://example.com/storage/filename.jpg

2

保存方法:

public function upload($img){
   $filename = Carbon::now() . '-' .  $img->getClientOriginalName();
   return Storage::put($filename, File::get($img)) ? $filename : '';
}

ルート:

 Route::get('image/{filename}', [
        'as'   => 'product.image',
        'uses' => 'ProductController@getImage',
    ]);

コントローラ:

 public function getImage($filename)
    {
        $file = Storage::get($filename);

        return new Response($file, 200);
    }

見る:

 <img src="{{ route('product.image', ['filename' => $yourImageName]) }}" alt="your image"/>

なぜ誰かがそれをするのか、なぜs3を使用してWebサーバーでそれをbroxyするのか!!
Shady Keshk 2016年

2

私が見つけた別の解決策はこれです:

Storage::disk('documents')->getDriver()->getConfig()->get('url')

ドキュメントストレージのベースパスを含むURLを返します


1

これを見てください:storage_path()を使用してlaravel4で画像を表示する方法。同じことがLaravel5にも当てはまります。

ストレージはファイルシステム用であり、その大部分はWebサーバーからアクセスできません。推奨される解決策はpublic/screenshots/、たとえば、パブリックフォルダ(ドキュメントルート)のどこかに画像を保存することです。次に、それらを表示する場合は、を使用しますasset('screenshots/1.jpg')


開発中はパブリックフォルダ、ライブ時にはs3になるように「ディスク」を設定しようとしています
daviestar 2015年

それは実際には重要ではなくStorage::path()、サーバー上のファイルのパスを返しますが、それにURLが必要であり、Webサーバーはドキュメントルートからのファイルのみを提供できます<project>/public。その中にディレクトリを作成し、ブレードテンプレートでurl()またはを使用しますasset()
nXu 2015年

2
Storage::path()存在しませんが、私はそれを
望んで

わかりました、誤解しました、ごめんなさい。私がすることは同じです。ローカルであろうとs3であろうと、DBへのフルパスを保存します。画像をアップロード/作成するときはgetenv('debug')、どちらを使用するかを確認して決定するだけです。
nXu 2015年

フルパスを保存しないようにしようとしていましたが、おそらくそれが最も賢明な方法です。
daviestar 2015年

1

私の場合、このファイルでローカルファイル用に別のメソッドを作成しました:src / Illuminate / Filesystem / FilesystemAdapter.php

    /**
 * Get the local path for the given filename.
 * @param $path
 * @return string
 */
public function localPath($path)
{
    $adapter = $this->driver->getAdapter();
    if ($adapter instanceof LocalAdapter) {
        return $adapter->getPathPrefix().$path;
    } else {
        throw new RuntimeException('This driver does not support retrieving local path');
    }
}

次に、フレームワークへのプルリクエストを作成しますが、まだメインコアにマージされていません:https//github.com/laravel/framework/pull/13605 誰かがこれをマージする可能性があります))


0

この作品は2020年にlaravel7で私のために

        $image_resize = Image::make($image->getRealPath());
        $image_resize->resize(800,600);
        $image_resize->save(Storage::disk('episodes')->path('') . $imgname);

こんな感じで使えます

echo Storage::disk('public')->path('');
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.