Laravel 5:如何将本地文件复制到 Amazon S3?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/29527611/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 11:19:40  来源:igfitidea点击:

Laravel 5: How do you copy a local file to Amazon S3?

laravelamazon-s3uploadlaravel-5laravel-filesystem

提问by clone45

I'm writing code in Laravel 5 to periodically backup a MySQL database. My code thus far looks like this:

我正在 Laravel 5 中编写代码来定期备份 MySQL 数据库。到目前为止,我的代码如下所示:

    $filename = 'database_backup_'.date('G_a_m_d_y').'.sql';
    $destination = storage_path() . '/backups/';

    $database = \Config::get('database.connections.mysql.database');
    $username = \Config::get('database.connections.mysql.username');
    $password = \Config::get('database.connections.mysql.password');

    $sql = "mysqldump $database --password=$password --user=$username --single-transaction >$destination" . $filename;

    $result = exec($sql, $output); // TODO: check $result

    // Copy database dump to S3

    $disk = \Storage::disk('s3');

    // ????????????????????????????????
    //  What goes here?
    // ????????????????????????????????

I've seen solutions online that would suggest I do something like:

我在网上看过一些解决方案,建议我做一些类似的事情:

$disk->put('my/bucket/' . $filename, file_get_contents($destination . $filename));

However, for large files, isn't it wasteful to use file_get_contents()? Are there any better solutions?

但是,对于大文件,使用file_get_contents()是不是很浪费?有没有更好的解决方案?

采纳答案by itod

Laravel has now putFile?and putFileAsmethod to allow stream of file.

Laravel 现在有putFile?andputFileAs方法来允许文件流。

Automatic Streaming

If you would like Laravel to automatically manage streaming a given file to your storage location, you may use the putFile or putFileAs method. This method accepts either a Illuminate\Http\File or Illuminate\Http\UploadedFile instance and will automatically stream the file to your desired location:

自动流媒体

如果您希望 Laravel 自动管理将给定文件流式传输到您的存储位置,您可以使用 putFile 或 putFileAs 方法。此方法接受 Illuminate\Http\File 或 Illuminate\Http\UploadedFile 实例,并将自动将文件流式传输到您想要的位置:

use Illuminate\Http\File;
use Illuminate\Support\Facades\Storage;

// Automatically generate a unique ID for file name...
Storage::putFile('photos', new File('/path/to/photo'));

// Manually specify a file name...
Storage::putFileAs('photos', new File('/path/to/photo'), 'photo.jpg');

Link to doc: https://laravel.com/docs/5.8/filesystem(Automatic Streaming)

链接到文档:https: //laravel.com/docs/5.8/filesystem(自动流媒体)

Hope it helps

希望能帮助到你

回答by theHarvester

There is a way to copy files without needing to load the file contents into memory.

有一种方法可以复制文件而无需将文件内容加载到内存中。

You will also need to import the following:

您还需要导入以下内容:

use League\Flysystem\MountManager;

Now you can copy the file like so:

现在您可以像这样复制文件:

$mountManager = new MountManager([
    's3' => \Storage::disk('s3')->getDriver(),
    'local' => \Storage::disk('local')->getDriver(),
]);
$mountManager->copy('s3://path/to/file.txt', 'local://path/to/output/file.txt');

回答by user4603841

You can always use a file resource to stream the file (advisable for large files) by doing something like this:

您始终可以通过执行以下操作来使用文件资源来流式传输文件(建议用于大文件):

Storage::disk('s3')->put('my/bucket/' . $filename, fopen('path/to/local/file', 'r+'));

An alternative suggestion is proposed here. It uses Laravel's Storage facade to read the stream. The basic idea is something like this:

这里提出了一个替代建议。它使用 Laravel 的 Storage 门面来读取流。基本思想是这样的:

    $inputStream = Storage::disk('local')->getDriver()->readStream('/path/to/file');
    $destination = Storage::disk('s3')->getDriver()->getAdapter()->getPathPrefix().'/my/bucket/';
    Storage::disk('s3')->getDriver()->putStream($destination, $inputStream);

回答by vipmaa

You can try this code

你可以试试这个代码

$contents = Storage::get($file);
Storage::disk('s3')->put($newfile,$contents);

As Laravel document this is the easy way I found to copy data between two disks

作为 Laravel 文档,这是我发现在两个磁盘之间复制数据的简单方法

回答by Marcin Nabia?ek

Looking at the documentation the only way is using method putwhich needs file content. There is no method to copy file between 2 file systems so probably the solution you gave is at the moment the only one.

查看文档的唯一方法是使用put需要文件内容的方法。没有方法可以在 2 个文件系统之间复制文件,因此您提供的解决方案可能是目前唯一的解决方案。

If you think about it, finally when copying file from local file system to s3, you need to have file content to put it in S3, so indeed it's not so wasteful in my opinion.

仔细想想,最后从本地文件系统复制文件到s3时,需要有文件内容才能放到S3中,所以在我看来确实没有那么浪费。

回答by Rajkumar R

I solved it in the following way:

我通过以下方式解决了它:

$contents = \File::get($destination);
\Storage::disk('s3')
    ->put($s3Destination,$contents);

Sometimes we don't get the data using $contents = Storage::get($file);- storage function so we have to give root path of the data using Laravel Fileinstead of storage path using Storage.

有时我们没有使用$contents = Storage::get($file);- storage 函数获取数据,因此我们必须使用 Laravel File 提供数据的根路径,而不是使用Storage的存储路径。