S3バケット間でファイルを移動する最良の方法?


89

一部のファイルを本番バケットから開発バケットに毎日コピーしたいと思います。

例:productionbucket / feed / feedname / dateをdevelopmentbucket / feed / feedname / dateにコピーします

必要なファイルはフォルダ構造の奥深くにあるため、各フォルダに移動してコピー/貼り付けするのに時間がかかりすぎます。

ドライブを各バケットにマウントしてWindowsバッチスクリプトを記述してみましたが、それは非常に遅く、すべてのファイル/フォルダーをローカルサーバーに不必要にダウンロードして、再度バックアップします。

回答:


109

更新

以下のようalbergeによって指摘(1)、最近で優れたAWSコマンドラインインタフェース(ほぼ)すべてのもののAWSと対話するための最も汎用的なアプローチを提供します-それは一方で、ほとんどのサービスのAPIをカバーし、また、特徴、より高いレベルのS3のコマンドを扱うためのあなた具体的な使用例については、S3のAWS CLIリファレンスをご覧ください。

  • 同期 - 同期ディレクトリとS3の接頭辞。あなたのユースケースがで覆われている例2(より細かいと使用状況をきめ--exclude--includeおよびなどを扱う接頭辞でも入手可能です):

    次のsyncコマンドは、s3オブジェクトをコピーして、指定されたプレフィックスとバケットの下のオブジェクトを、別の指定されたプレフィックスとバケットの下のオブジェクトに同期します。[...]

    aws s3 sync s3://from_my_bucket s3://to_my_other_bucket
    

完全を期すために、下位レベルのS3コマンドも引き続きs3apiサブコマンドを介して利用できることを述べます。これにより、最終的に上位レベルの機能を採用する前に、SDKベースのソリューションをAWS CLIに直接変換できます。


最初の回答

S3バケット間でのファイルの移動は、PUT Object-Copy API(その後にDELETE Object)を使用して実行できます

このPUT操作の実装は、Amazon S3にすでに格納されているオブジェクトのコピーを作成します。PUTコピー操作は、GETを実行してからPUTを実行するのと同じです。リクエストヘッダーx-amz-copy-sourceを追加すると、PUT操作でソースオブジェクトが宛先バケットにコピーされます。ソース

利用可能な既存のすべてのAWS SDKのそれぞれのサンプルがあります。単一のオペレーションでのオブジェクトのコピーを参照してください。当然のことながら、ここではスクリプトベースのソリューションが明らかに最初の選択肢となるため、AWS SDK for Rubyを使用してオブジェクトをコピーすることから始めるとよいでしょう。代わりにPythonを使用する場合は、もちろんboto使用しても同じことができcopy_key()ます。botoのS3 APIドキュメントのmethodを参照してください。

PUT ObjectファイルをコピーするだけなのでDELETE Object、コピー操作が成功した後でも、ファイルを明示的に削除する必要がありますが、バケットとファイル名を処理する全体的なスクリプトが適切になったら、数行だけです(それぞれの例もあります) 、たとえば、リクエストごとに1つのオブジェクトを削除するをご覧ください)。


最終的に、.NETのAWS SDKを使用して操作のスクリプトを作成しました
Matt Dell

1
@MattDellあなたはこの質問に.NET回答を追加できますか?
balexandre 2013年

1
これについて困るのは、Amazonがコピーコマンドが成功したかどうかについてあまり明確ではないため、操作後の削除が危険に思われることです。
James McMahon

明確にするために、私は特にJava APIに言及していました。別の質問stackoverflow.com/questions/17581582
James McMahon

単一のIDとキーを作成して、一方のバケットから読み取り、もう一方のバケットに書き込むことができる簡単な方法が必要です。特に、バケットがアカウント全体にある場合。
CMCDragonkai 2016年

65

新しい公式AWS CLIは、のほとんどの機能をネイティブでサポートしていますs3cmd。私は以前、s3cmdまたはruby AWS SDKを使用してこのようなことをしていましたが、公式のCLIはこれに適しています。

http://docs.aws.amazon.com/cli/latest/reference/s3/sync.html

aws s3 sync s3://oldbucket s3://newbucket

4
これは、リストのトップに投票する必要があります。これはバケットを同期する適切な方法であり、これらすべての回答の中で最新のものです。
dft 2014

403アクセス拒否エラーで問題が発生した場合は、このブログ投稿を参照してください。それは役に立ちました。alfielapeter.com/posts/…– crlane 14
12

3
クロスリージョンコピーaws s3 sync s3://my-bucket-in-eu-west1 s3://my-bucket-in-eu-central1 --source-region=eu-west-1 --region=eu-central-1
同等のもの8

あなたは、サーバー用途にこのower夜に実行する必要がある場合nohup aws s3 sync s3://my-bucket-in-eu-west1 s3://my-bucket-in-eu-central1 --source-region=eu-west-1 --region=eu-central-1 & thegeekstuff.com/2010/12/5-ways-to-execute-linux-command
equivalent8

@albergeコマンドライン引数を使用してアクセスキーとシークレットを提供する方法はありますか?
EmptyData

28

バケット間を移動またはコピーするには、s3cmdツールを使用して問題なく動作します。例えば:

s3cmd cp --recursive s3://bucket1/directory1 s3://bucket2/directory1
s3cmd mv --recursive s3://bucket1/directory1 s3://bucket2/directory1

28

これに必要なコピーを並列化するために独自のカスタムツールを作成するのに何日も費やしましたが、AWS S3 CLIの同期コマンドを使用してバケットを大規模な並列化と同期する方法に関するドキュメントに出くわしました。次のコマンドは、1,000個のスレッドを使用してジョブ(それぞれ小さなファイルまたはマルチパートコピーの一部)を実行し、100,000個のジョブを先読みするようAWS CLIに指示します。

aws configure set default.s3.max_concurrent_requests 1000
aws configure set default.s3.max_queue_size 100000

これらを実行した後、次のように単純なsyncコマンドを使用できます。

aws s3 sync s3://source-bucket/source-path s3://destination-bucket/destination-path

m4.xlargeマシン(AWS--4コア、16GB RAM)では、私の場合(3-50GBファイル)、同期/コピー速度は約9.5MiB / sから700 + MiB / sになり、速度はデフォルト構成の70倍。

更新:S3CMDは長年にわたって更新されており、これらの変更は多数の小さなファイルで作業している場合にのみ有効になることに注意してください。また、Windows上のS3CMD(Windowsのみ)は、全体的なスループットに深刻な制限があり、使用するインスタンスのサイズや設定に関係なく、プロセスあたり約3Gbpsしか達成できないことにも注意してください。S5CMDのような他のシステムにも同じ問題があります。私はこれについてS3チームに話しました、そして彼らはそれを調査しています。


おかげで、あなたの設定で900 + MiB /秒以上を取得することができ、デフォルトよりも大幅にスピードアップしました。
kozyr 2017年

@ジェームズ:APIはこのような高速転送を達成する上で私たちを制限していますか?T2 EC2マシンからAWS Java SDKとCLIで提供されるtransfermanager apiを使用して、2 GBのファイルを転送しています。時間の差は、5.5倍(CLI-14秒)対(SDK-80秒)です。また、SDKでs3.max_queue_sizeのオプションが表示されません。コメントは?
ドワーリア

@Dwarrior、これらの設定はどちらもCLI用です。SDKを使用する場合は、すべてのリクエストキューイングを自分で管理する必要があります。AWSサポートは、Linuxを使用したEC2とS3の間の可能な最大スループット(つまり、アドバタイズされたEC2インスタンスのネットワークスループット)の約80%に達したと主張しています。WindowsはAWSで二流の市民であり、Amazonが提供するツールではその半分も手に入れることができず、彼らはそれを修正する予定がないようです。:-( T2マシンでは、AWSは取得する帯域幅を正確に指定しませんが、S3 VPCエンドポイントを設定すると多少改善されます
James

@ジェームス私はスパークでクラスター上でファイルのリストを並列化し、各パーティション内の並列化と組み合わせてから、任意のファイルの並列アップロードにtransfermanagerを使用するまで行きました。それを実行してから80秒から45秒に改善が見られますが、EC2からのCLIの処理方法がまだありません。このセットアップをありがとう。Windowsでのパフォーマンスも大幅に向上しました。SDKでは、最大接続数を設定できますが、キューサイズは設定できないため、そのままにする必要があるかもしれません。:)キューイングの管理方法に関する任意のポインタ、ベースラインとして取り上げることができるサンプルコード。
Dwarrior

2
S5Cmd(github.com/peakgames/s5cmd)は、AWSサポート担当者が最大のスループットを得るために使用したユーティリティです。インスタンスのサイズは大きな違いを生みます。新しいc5nシリーズは、ネットワーキングに非常に費用対効果が高く、驚異的な100Gbpsまで対応します。
ジェームズ

13

要求された.NETの例:

using (client)
{
    var existingObject = client.ListObjects(requestForExisingFile).S3Objects; 
    if (existingObject.Count == 1)
    {
        var requestCopyObject = new CopyObjectRequest()
        {
            SourceBucket = BucketNameProd,
            SourceKey = objectToMerge.Key,
            DestinationBucket = BucketNameDev,
            DestinationKey = newKey
        };
        client.CopyObject(requestCopyObject);
    }
}

クライアントは次のようなものです

var config = new AmazonS3Config { CommunicationProtocol = Protocol.HTTP, ServiceURL = "s3-eu-west-1.amazonaws.com" };
var client = AWSClientFactory.CreateAmazonS3Client(AWSAccessKey, AWSSecretAccessKey, config);

より良い方法があるかもしれませんが、それは私がいくつかのファイルを転送させるために書いたいくつかの簡単なコードです。


1
それは良い解決策のようです。2つのバケットに異なる認証情報がある場合はどうなりますか?
Roee Gavirel 2014

2
資格情報は、copyコマンドを実行するためのものです。これらの単一の認証情報には、ソース/ターゲットバケットでの適切な読み取り/書き込み権限が必要です。アカウント間でコピーするには、バケットポリシーを使用して、他のアカウントの認証情報からバケットへのアクセスを許可する必要があります。
Matt Houser

9

AWS内にUNIXホストがある場合は、s3tools.orgのs3cmdを使用します。キーが開発バケットへの読み取りアクセスとなるように権限を設定します。次に実行します:

s3cmd cp -r s3://productionbucket/feed/feedname/date s3://developmentbucket/feed/feedname

サーバ側?s3にはサーバー側はありません。すべてのコマンドはリモートクライアントから実行されます。
DK。

ちなみに、このコマンドはインターネット経由でうまく機能するようです!
Gabe Kopley 2013

3
「サーバー側」の質問は有効です。s3cmd転送はすべてのデータをクライアントに転送しますか、それともS3からS3への直接転送ですか?前者の場合、これをAWSクラウドで実行して、外部WAN転送を回避することをお勧めします。
Bruce Edge

1
コピーはすべてS3でリモートで行われます。
DK。

また、このプロセスを誤って中断した場合s3cmd cp--skip-existingオプションを受け入れないことに注意してください。s3cmd sync代わりに、既存のものをスキップして実行できます
ianstarz

9

私にとっては、次のコマンドがうまくいきました:

aws s3 mv s3://bucket/data s3://bucket/old_data --recursive

2
シンプルで簡単な解決策... aws cliでこれを行うことができるのに、なぜこのような単純なタスクにサードパーティのツールや回避策を使用するのですか?
Fr0zenFyr 2016年

7

これを実行するためのRubyクラスは次のとおりです。https//gist.github.com/4080793

使用例:

$ gem install aws-sdk
$ irb -r ./bucket_sync_service.rb
> from_creds = {aws_access_key_id:"XXX",
                aws_secret_access_key:"YYY",
                bucket:"first-bucket"}
> to_creds = {aws_access_key_id:"ZZZ",
              aws_secret_access_key:"AAA",
              bucket:"first-bucket"}
> syncer = BucketSyncService.new(from_creds, to_creds)
> syncer.debug = true # log each object
> syncer.perform

5

実際、最近では、AWS s3インターフェースでcopy + pasteアクションを使用するだけです。コピーするファイルに移動し、[アクション]-> [コピー]をクリックして、宛先バケットに移動し、[アクション]-> [貼り付け]をクリックします。

それは非常に迅速にファイルを転送し、プログラミングを必要としない複雑なソリューションのように見えるか、そのようなトップソリューションよりも優れています。


はい。同じことを数分前に発見しました。私は賛成したので、より多くの人々が時間を節約できます:)
JCarlosR

134,364個のオブジェクトを含むバケット間コピーでそれを試しました。何時間もかかりました。そして、宛先は134,333ファイルしかありませんでした-コピーはそれが「成功した」と述べましたが、欠けているファイルの説明はありませんでした。
ウォーレン、

ここの他の投稿で説明されている「aws s3 sync」タイプのコマンドを使用すると、134,364のオブジェクトすべてが約20分でコピーされました。
ウォーレン

4

SnowplowでのETLジョブでこの問題が発生したため、並列ファイルコピーコード(Ruby、Fogの上に構築)をSluiceという独自のRuby gemに抽出しました。

https://github.com/snowplow/sluice

Sluiceは、S3ファイルの削除、移動、ダウンロードも処理します。すべてが並列化され、操作が失敗した場合は自動的に再試行されます(これは驚くほど頻繁に行われます)。お役に立てれば幸いです。



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