AWS S3 คัดลอกไฟล์และโฟลเดอร์ระหว่างสองที่เก็บข้อมูล


112

ฉันมองหาเครื่องมือที่จะช่วยฉันคัดลอกเนื้อหาของที่เก็บข้อมูล AWS S3 ไปยังที่เก็บข้อมูล AWS S3 ที่สองโดยไม่ต้องดาวน์โหลดเนื้อหาไปยังระบบไฟล์ภายในเครื่องก่อน

ฉันได้พยายามใช้ตัวเลือกการคัดลอกคอนโซล AWS S3 แต่ส่งผลให้ไฟล์ที่ซ้อนกันบางไฟล์หายไป

ฉันได้ลองใช้แอป Transmit (โดย Panic) คำสั่งที่ซ้ำกันจะดาวน์โหลดไฟล์ไปยังระบบโลคัลก่อนจากนั้นอัปโหลดกลับไปที่ที่เก็บข้อมูลที่สองซึ่งค่อนข้างไม่มีประสิทธิภาพ


พิจารณาเพิ่มจำนวนคำขอพร้อมกันaws configure set default.s3.max_concurrent_requests 200 ดูโพสต์นี้สำหรับรายละเอียดและตัวเลือกเพิ่มเติมstackoverflow.com/questions/4663016/…
Balmipour

คำตอบ:


176

คัดลอกระหว่าง S3 Buckets

AWS (เพิ่งเปิดตัวเมื่อเร็ว ๆ นี้) อินเตอร์เฟสบรรทัดคำสั่งสำหรับการคัดลอกระหว่างที่เก็บข้อมูล

http://aws.amazon.com/cli/

$ aws s3 sync s3://mybucket-src s3://mybucket-target --exclude *.tmp
..

สิ่งนี้จะคัดลอกจากที่เก็บข้อมูลเป้าหมายหนึ่งไปยังที่เก็บข้อมูลอื่น

ดูเอกสารที่นี่: เอกสาร S3 CLI


เรียกใช้จาก EC2 และคัดลอก 80MB ในเวลาประมาณ 5 วินาที
Stew-au

1
สิ่งที่ฉันต้องการเนื่องจากอัญมณี aws-sdk ไม่มีคุณสมบัติในการคัดลอกหรือซิงค์ที่เก็บข้อมูลทั้งหมดในครั้งเดียว ขอบคุณ!
แปลกประหลาด

มันแสดงข้อผิดพลาดต่อไปนี้A client error (PermanentRedirect) occurred when calling the ListObjects operation: The bucket you are attempting to access must be addressed using the specified endpoint. Please send all future requests to this endpoint.
Giovanni Bitliner

@GiovanniBitliner ชื่อที่เก็บข้อมูลที่คุณใช้ไม่ถูกต้อง คุณกำลังใช้คำนำหน้าผิดหรือใช้วิธีการอ้างถึงที่เก็บข้อมูลแบบเก่า ตรวจสอบชื่อที่เก็บข้อมูลของคุณในคอนโซลผู้ดูแลระบบ
Layke

8
สังเกตว่านี่เป็นครั้งแรกที่คุณใช้เครื่องมือ cli หรือไม่คุณต้องเรียกใช้ 'aws configure' และป้อนเครดิตของคุณ
S ..

41

ตัวอย่างที่เรียบง่ายโดยใช้อัญมณี aws-sdk:

AWS.config(:access_key_id => '...', :secret_access_key => '...')
s3 = AWS::S3.new
s3.buckets['bucket-name'].objects['source-key'].copy_to('target-key')

หากคุณต้องการคัดลอกระหว่างที่เก็บข้อมูลต่างๆให้ระบุชื่อที่เก็บข้อมูลเป้าหมาย:

s3.buckets['bucket-name'].objects['source-key'].copy_to('target-key', :bucket_name => 'target-bucket')

41

ตอนนี้คุณสามารถทำได้จากอินเทอร์เฟซผู้ดูแลระบบ S3 actions->copyเพียงแค่เข้าไปในถังหนึ่งเลือกโฟลเดอร์ของคุณทั้งหมด actions->pasteแล้วย้ายลงไปในถังใหม่ของคุณ


4
! น่ากลัว เขากำลังอ้างถึงเว็บอินเตอร์เฟส ซึ่งแตกต่างจากคนอื่น ๆ ส่วนใหญ่ฉันสามารถทำได้จาก iPad
Jacob Foshee

2
สิ่งนี้สุ่มทิ้งวัตถุที่ซ้อนกันในโฟลเดอร์ย่อย - 3 ปีต่อมาและ AWS ยังไม่สามารถแก้ไขข้อบกพร่องพื้นฐานดังกล่าวได้!
RunLoop

สำหรับภูมิภาคเดียวกันหรือทั้งหมด?
hakiko

1
ปัญหาเหล่านี้ได้รับการบันทึกโดย Amazon หรือไม่ @RunLoop
davetapley

1
@dukedave ฉันไม่รู้และไม่ได้ทดสอบอีกสักพักเพราะฉันใช้การคัดลอกผ่านทางบรรทัดคำสั่งเพราะมันทำงานได้อย่างสมบูรณ์
RunLoop

8

เป็นไปได้ด้วยอัญมณีaws-sdkล่าสุดดูตัวอย่างโค้ด:

require 'aws-sdk'

AWS.config(
  :access_key_id     => '***',
  :secret_access_key => '***',
  :max_retries       => 10
)

file     = 'test_file.rb'
bucket_0 = {:name => 'bucket_from', :endpoint => 's3-eu-west-1.amazonaws.com'}
bucket_1 = {:name => 'bucket_to',   :endpoint => 's3.amazonaws.com'}

s3_interface_from = AWS::S3.new(:s3_endpoint => bucket_0[:endpoint])
bucket_from       = s3_interface_from.buckets[bucket_0[:name]]
bucket_from.objects[file].write(open(file))

s3_interface_to   = AWS::S3.new(:s3_endpoint => bucket_1[:endpoint])
bucket_to         = s3_interface_to.buckets[bucket_1[:name]]
bucket_to.objects[file].copy_from(file, {:bucket => bucket_from})

รายละเอียดเพิ่มเติม: วิธีคัดลอกไฟล์ข้ามที่เก็บข้อมูลโดยใช้อัญมณี aws-s3


ขอขอบคุณที่แสดงวิธีคัดลอกข้ามเซิร์ฟเวอร์ ฉันพยายามคัดลอกจากเซิร์ฟเวอร์ของเราไปยังเซิร์ฟเวอร์สิงคโปร์
Arcolye

@ Arcolye เวลาแฝงใน AWS Singapore ตอนนี้เป็นอย่างไร ปีที่แล้วมันช้าและไม่สอดคล้องกัน
Anatoly

7

คัดลอกระหว่างที่เก็บข้อมูลในภูมิภาคต่างๆ

$ aws s3 cp s3://src_bucket/file  s3://dst_bucket/file --source-region eu-west-1 --region ap-northeast-1

คำสั่งข้างต้นคัดลอกไฟล์จากที่เก็บข้อมูลในยุโรป (eu-west-1) ไปยังญี่ปุ่น (ap-Northeast-1) คุณสามารถรับชื่อรหัสสำหรับภูมิภาคที่เก็บข้อมูลของคุณได้ด้วยคำสั่งนี้:

$ aws s3api get-bucket-location --bucket my_bucket

อย่างไรก็ตามการใช้ Copy and Paste ในเว็บคอนโซล S3 นั้นง่าย แต่ดูเหมือนว่าจะดาวน์โหลดจากที่เก็บข้อมูลต้นทางลงในเบราว์เซอร์จากนั้นอัปโหลดไปยังที่เก็บข้อมูลปลายทาง การใช้ "aws s3" เร็วกว่ามากสำหรับฉัน


6

ฉันได้สร้างDocker ที่ปฏิบัติการได้ของเครื่องมือs3s3mirror ยูทิลิตี้ในการคัดลอกและจำลองจากที่เก็บข้อมูล AWS S3 ไปยังที่เก็บข้อมูลอื่น

เป็นเธรดที่อนุญาตให้ทำสำเนาแบบขนานและหน่วยความจำมีประสิทธิภาพมากมันประสบความสำเร็จโดยที่ s3cmd ล้มเหลวอย่างสมบูรณ์

การใช้งาน:

docker run -e AWS_ACCESS_KEY_ID=FOO -e AWS_SECRET_ACCESS_KEY=BAR pmoust/s3s3mirror [OPTIONS] source_bucket[/prefix] dest_bucket[/prefix]

สำหรับรายการตัวเลือกทั้งหมดให้ลอง:

docker run pmoust/s3s3mirror 

5

ตรวจสอบเอกสารด้านล่าง ฉันเดาว่านั่นคือสิ่งที่คุณกำลังมองหา http://docs.amazonwebservices.com/AmazonS3/latest/API/RESTObjectCOPY.html

S3Interface ของอัญมณี RightAws มีฟังก์ชั่นการคัดลอกที่ทำตามข้างต้น

http://rubydoc.info/gems/right_aws/3.0.0/RightAws/S3Interface#copy-instance_method


5

ฉันคิดว่าตอนนี้คุณอาจพบวิธีแก้ปัญหาที่ดี แต่สำหรับคนอื่น ๆ ที่กำลังประสบปัญหานี้ (อย่างที่ฉันเพิ่งเป็นเมื่อไม่นานมานี้) ฉันได้สร้างยูทิลิตี้ง่ายๆโดยเฉพาะเพื่อจุดประสงค์ในการจำลองถัง S3 หนึ่งไปยังอีกถังหนึ่งใน เป็นลักษณะที่มีประสิทธิภาพสูงพร้อมกัน แต่ CPU และหน่วยความจำ

อยู่บน github ภายใต้ Apache License ที่นี่: https://github.com/cobbzilla/s3s3mirror

เมื่อคุณมีที่เก็บข้อมูลขนาดใหญ่มากและกำลังมองหาประสิทธิภาพสูงสุดก็อาจคุ้มค่าที่จะลอง

หากคุณตัดสินใจที่จะลองโปรดแจ้งให้เราทราบหากคุณมีข้อเสนอแนะใด ๆ


ฉันมีประสบการณ์ที่ยอดเยี่ยมกับ s3s3mirror ฉันสามารถตั้งค่าบนโหนด EC2 ขนาดเล็ก m1 และคัดลอกวัตถุ 1.5 ล้านชิ้นในเวลาประมาณ 2 ชั่วโมง การติดตั้งค่อนข้างยากเนื่องจากฉันไม่คุ้นเคยกับ Maven และ Java แต่ใช้คำสั่ง apt-get เพียงไม่กี่คำบน Ubuntu เพื่อติดตั้งทุกอย่าง หมายเหตุสุดท้าย: หาก (เช่นฉัน) คุณกังวลเกี่ยวกับการเรียกใช้สคริปต์ที่ไม่รู้จักในที่เก็บข้อมูล s3 ขนาดใหญ่ที่สำคัญให้สร้างผู้ใช้พิเศษที่มีสิทธิ์เข้าถึงแบบอ่านอย่างเดียวในที่เก็บสำเนาจากที่เก็บข้อมูลและใช้ข้อมูลรับรองเหล่านั้น โอกาสลบโดยไม่ได้ตั้งใจเป็นศูนย์
คาห์

4

หากคุณอยู่ในเชลล์และต้องการคัดลอกไฟล์หลายไฟล์ แต่ไม่ใช่ทุกไฟล์: s3cmd cp --recursive s3: // BUCKET1 / OBJECT1 s3: // BUCKET2 [/ OBJECT2]


3

ฉันเขียนสคริปต์ที่สำรองถัง S3: https://github.com/roseperrone/aws-backup-rake-task

#!/usr/bin/env python
from boto.s3.connection import S3Connection
import re
import datetime
import sys
import time

def main():
    s3_ID = sys.argv[1]
    s3_key = sys.argv[2]
    src_bucket_name = sys.argv[3]
    num_backup_buckets = sys.argv[4]
    connection = S3Connection(s3_ID, s3_key)
    delete_oldest_backup_buckets(connection, num_backup_buckets)
    backup(connection, src_bucket_name)

def delete_oldest_backup_buckets(connection, num_backup_buckets):
    """Deletes the oldest backup buckets such that only the newest NUM_BACKUP_BUCKETS - 1 buckets remain."""
    buckets = connection.get_all_buckets() # returns a list of bucket objects
    num_buckets = len(buckets)

    backup_bucket_names = []
    for bucket in buckets:
        if (re.search('backup-' + r'\d{4}-\d{2}-\d{2}' , bucket.name)):
            backup_bucket_names.append(bucket.name)

    backup_bucket_names.sort(key=lambda x: datetime.datetime.strptime(x[len('backup-'):17], '%Y-%m-%d').date())

    # The buckets are sorted latest to earliest, so we want to keep the last NUM_BACKUP_BUCKETS - 1
    delete = len(backup_bucket_names) - (int(num_backup_buckets) - 1)
    if delete <= 0:
        return

    for i in range(0, delete):
        print 'Deleting the backup bucket, ' + backup_bucket_names[i]
        connection.delete_bucket(backup_bucket_names[i])

def backup(connection, src_bucket_name):
    now = datetime.datetime.now()
    # the month and day must be zero-filled
    new_backup_bucket_name = 'backup-' + str('%02d' % now.year) + '-' + str('%02d' % now.month) + '-' + str(now.day);
    print "Creating new bucket " + new_backup_bucket_name
    new_backup_bucket = connection.create_bucket(new_backup_bucket_name)
    copy_bucket(src_bucket_name, new_backup_bucket_name, connection)


def copy_bucket(src_bucket_name, dst_bucket_name, connection, maximum_keys = 100):
    src_bucket = connection.get_bucket(src_bucket_name);
    dst_bucket = connection.get_bucket(dst_bucket_name);

    result_marker = ''
    while True:
        keys = src_bucket.get_all_keys(max_keys = maximum_keys, marker = result_marker)

        for k in keys:
            print 'Copying ' + k.key + ' from ' + src_bucket_name + ' to ' + dst_bucket_name

            t0 = time.clock()
            dst_bucket.copy_key(k.key, src_bucket_name, k.key)
            print time.clock() - t0, ' seconds'

        if len(keys) < maximum_keys:
            print 'Done backing up.'
            break

        result_marker = keys[maximum_keys - 1].key

if  __name__ =='__main__':main()

ฉันใช้สิ่งนี้ในงานคราด (สำหรับแอพ Rails):

desc "Back up a file onto S3"
task :backup do
     S3ID = "AKIAJM3NRWC7STXWUWVQ"
     S3KEY = "0A5kuzV+E1dkaPjZxHQAezz1GlSddJd0iS5sNpry"
     SRCBUCKET = "primary-mzgd"
     NUM_BACKUP_BUCKETS = 2

     Dir.chdir("#{Rails.root}/lib/tasks")
     system "./do_backup.py #{S3ID} #{S3KEY} #{SRCBUCKET} #{NUM_BACKUP_BUCKETS}"
end

1

ฉันได้ยินมาว่ามีโมดูลโหนดสำหรับสิ่งนั้นหากคุณใช้ javascript: p

จากเอกสารKnox-copy :

knoxCopy = require 'knox-copy'

client = knoxCopy.createClient
  key: '<api-key-here>'
  secret: '<secret-here>'
  bucket: 'backups'

client.copyBucket
  fromBucket: 'uploads'
  fromPrefix: '/nom-nom'
  toPrefix: "/upload_backups/#{new Date().toISOString()}"
  (err, count) ->
     console.log "Copied #{count} files"

นี่ไม่ใช่จาวาสคริปต์ขออภัย ... (ใช่ฉันรู้เรื่องกาแฟและคุณสามารถใช้มันได้ แต่ยังไม่ใช่จาวาสคริปต์)
Victor Schröder

1

ฉันได้รับแจ้งว่าคุณสามารถทำได้โดยใช้ s3distcp บนคลัสเตอร์ EMR ควรจะเร็วกว่าสำหรับข้อมูลที่มีไฟล์ขนาดใหญ่ มันทำงานได้ดีเพียงพอกับชุดข้อมูลขนาดเล็ก - แต่ฉันต้องการวิธีแก้ปัญหาอื่นเนื่องจากช่วงการเรียนรู้ที่ใช้ในการตั้งค่าสำหรับข้อมูลเพียงเล็กน้อย (ฉันไม่เคยทำงานกับ EMR มาก่อน)

นี่คือลิงค์จากเอกสาร AWS: http://docs.aws.amazon.com/ElasticMapReduce/latest/DeveloperGuide/UsingEMR_s3distcp.html

อัปเดต: สำหรับชุดข้อมูลเดียวกัน s3s3mirror เร็วกว่า s3distcp หรือ AWS cli มาก ติดตั้งง่ายกว่ามากด้วย


1

หากต้องการคัดลอกจากที่เก็บ S3 หนึ่งไปยังที่เก็บข้อมูล S3 เดียวกันหรืออีกชุดหนึ่งโดยไม่ต้องดาวน์โหลดลงในเครื่องนั้นค่อนข้างง่าย ใช้คำสั่งเชลล์ด้านล่าง

hdfs dfs -cp -f "s3://AccessKey:SecurityKey@ExternalBucket/SourceFoldername/*.*" "s3://AccessKey:SecurityKey@ExternalBucket/TargetFoldername"

นี้จะคัดลอกไฟล์ทั้งหมดจากถังแหล่งที่มาของSourceFoldernameโฟลเดอร์ถังเป้าหมายTargetFoldernameโฟลเดอร์ ในโค้ดข้างต้นโปรดแทนที่AccessKey, SecurityKeyและExternalBucketมีค่าที่สอดคล้องกันของคุณ


คืออะไรhdfs?
Anthony Kong

1

จาก AWS cli https://aws.amazon.com/cli/คุณสามารถทำได้

aws s3 ls - นี่จะแสดงรายการที่เก็บข้อมูล S3 ทั้งหมด

aws cp --recursive s3://<source bucket> s3://<destination bucket> - การดำเนินการนี้จะคัดลอกไฟล์จากที่เก็บข้อมูลหนึ่งไปยังอีกที่หนึ่ง

หมายเหตุ * มีประโยชน์มากเมื่อสร้างที่เก็บข้อมูลการจำลองแบบข้ามภูมิภาคโดยการทำข้างต้นไฟล์ของคุณจะถูกติดตามทั้งหมดและการอัปเดตไปยังไฟล์ภูมิภาคต้นทางจะถูกเผยแพร่ไปยังที่เก็บข้อมูลที่จำลองแบบ ทุกอย่างยกเว้นการลบไฟล์จะถูกซิงค์

สำหรับ CRR ตรวจสอบให้แน่ใจว่าคุณได้เปิดใช้งานการกำหนดเวอร์ชันบนที่เก็บข้อมูล


0

วิธีการเกี่ยวกับaws s3 syncคำสั่ง cli aws s3 ซิงค์ s3: // bucket1 / s3: // bucket2 /


0

ดังที่ Neel Bhaat ได้อธิบายไว้ในบล็อกนี้มีเครื่องมือต่างๆมากมายที่สามารถใช้เพื่อจุดประสงค์นี้ บางส่วนมีให้โดย AWS ซึ่งส่วนใหญ่เป็นเครื่องมือของบุคคลที่สาม เครื่องมือทั้งหมดนี้กำหนดให้คุณต้องบันทึกรหัสบัญชี AWS และความลับในเครื่องมือเอง ระมัดระวังอย่างมากเมื่อใช้เครื่องมือของบุคคลที่สามเนื่องจากข้อมูลรับรองที่คุณบันทึกไว้อาจทำให้คุณเสียค่าใช้จ่ายทั้งหมดและทำให้คุณเสียชีวิต

ดังนั้นฉันจึงแนะนำให้ใช้AWS CLIเพื่อจุดประสงค์นี้เสมอ คุณสามารถติดตั้งได้จากลิงค์นี้ จากนั้นเรียกใช้คำสั่งต่อไปนี้และบันทึกคีย์ค่าลับของคุณใน AWS CLI

aws configure

และใช้คำสั่งต่อไปนี้เพื่อซิงค์ AWS S3 Bucket กับเครื่องภายในของคุณ (เครื่องท้องถิ่นควรติดตั้ง AWS CLI)

aws s3 sync <source> <destination>

ตัวอย่าง:

1) สำหรับ AWS S3 เป็น Local Storage

aws s3 sync <S3Uri> <LocalPath>

2) จาก Local Storage ไปยัง AWS S3

aws s3 sync <LocalPath> <S3Uri>

3) จากที่เก็บข้อมูล AWS s3 ไปยังที่เก็บข้อมูลอื่น

aws s3 sync <S3Uri> <S3Uri> 

0

วิธีที่ดีที่สุดที่จะคัดลอกถัง S3 คือการใช้AWS CLI

มันเกี่ยวข้องกับ 3 ขั้นตอนเหล่านี้:

  1. การติดตั้ง AWS CLI บนเซิร์ฟเวอร์ของคุณ
**https://docs.aws.amazon.com/cli/latest/userguide/cli-chap-install.html**
  1. หากคุณกำลังคัดลอกที่เก็บข้อมูลระหว่างบัญชี AWS สองบัญชีคุณต้องแนบนโยบายที่ถูกต้องกับที่เก็บข้อมูลแต่ละบัญชี

  2. หลังจากนี้ให้ใช้คำสั่งนี้เพื่อคัดลอกจากที่เก็บข้อมูลหนึ่งไปยังอีกที่หนึ่ง

aws s3 sync s3://sourcebucket s3://destinationbucket

รายละเอียดของขั้นตอนที่ 2และขั้นตอนที่ 3มีให้ในลิงค์นี้:

https://aws.amazon.com/premiumsupport/knowledge-center/account-transfer-s3/


โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.