Cara menghapus file secara rekursif dari bucket S3


90

Saya memiliki struktur folder berikut di S3. Apakah ada cara untuk menghapus semua file secara rekursif di bawah folder tertentu (katakanlah foo/bar1 or foo or foo/bar2/1..)

foo/bar1/1/..
foo/bar1/2/..
foo/bar1/3/..

foo/bar2/1/..
foo/bar2/2/..
foo/bar2/3/..

Jawaban:


169

Dengan alat baris perintah aws-cli python terbaru , untuk secara rekursif menghapus semua file di bawah folder dalam keranjang hanya:

aws s3 rm --recursive s3://your_bucket_name/foo/

Atau hapus semua yang ada di bawah keranjang:

aws s3 rm --recursive s3://your_bucket_name

Jika yang Anda inginkan adalah benar-benar menghapus bucket, ada pintasan satu langkah:

aws s3 rb --force s3://your_bucket_name

yang akan menghapus konten di keranjang itu secara rekursif, lalu menghapusnya.

Catatan: s3://awalan protokol diperlukan agar perintah ini berfungsi


2
inilah jawabannya. Ini adalah standar (baru-baru), alat canggih, dirancang untuk hal-hal seperti pertanyaan ini
Don Cheadle

Ini hanya menghapus file tetapi juga menghapus bucket setelah menghapus file. Apakah saya melewatkan sesuatu?
Naveen

1
@Naveen seperti yang saya katakan di atas, rmhanya akan menghapus file tetapi rb --forceakan menghapus file dan bucket.
nomor 5

5
menggunakan --recursivemenghapus folder juga.
ryantuck

2
@Moseleyi saya percaya bahwa Anda tidak dapat benar-benar memiliki folder kosong di ember s3
ryantuck

58

Ini biasanya memerlukan panggilan API khusus per kunci (file), tetapi telah sangat disederhanakan karena diperkenalkannya Amazon S3 - Multi-Object Delete pada Desember 2011:

Multi-Object Delete baru dari Amazon S3 memberi Anda kemampuan untuk menghapus hingga 1000 objek dari bucket S3 dengan satu permintaan.

Lihat jawaban saya untuk pertanyaan terkait hapus dari S3 menggunakan api php menggunakan wildcard untuk informasi lebih lanjut tentang ini dan masing-masing contoh di PHP ( AWS SDK untuk PHP mendukung ini sejak versi 1.4.8 ).

Sementara itu, sebagian besar perpustakaan klien AWS telah memperkenalkan dukungan khusus untuk fungsionalitas ini, misalnya:

Python

Anda dapat mencapai ini dengan antarmuka boto Python yang sangat baik ke AWS kira-kira sebagai berikut (belum teruji, dari atas kepala saya):

import boto
s3 = boto.connect_s3()
bucket = s3.get_bucket("bucketname")
bucketListResultSet = bucket.list(prefix="foo/bar")
result = bucket.delete_keys([key.name for key in bucketListResultSet])

Rubi

Ini tersedia sejak versi 1.24 dari AWS SDK untuk Ruby dan catatan rilis juga menyediakan contoh:

bucket = AWS::S3.new.buckets['mybucket']

# delete a list of objects by keys, objects are deleted in batches of 1k per
# request.  Accepts strings, AWS::S3::S3Object, AWS::S3::ObectVersion and 
# hashes with :key and :version_id
bucket.objects.delete('key1', 'key2', 'key3', ...)

# delete all of the objects in a bucket (optionally with a common prefix as shown)
bucket.objects.with_prefix('2009/').delete_all

# conditional delete, loads and deletes objects in batches of 1k, only
# deleting those that return true from the block
bucket.objects.delete_if{|object| object.key =~ /\.pdf$/ }

# empty the bucket and then delete the bucket, objects are deleted in batches of 1k
bucket.delete!

Atau:

AWS::S3::Bucket.delete('your_bucket', :force => true)

harus menggunakan jawaban baru aws cliseperti @ number5 di bawah docs.aws.amazon.com/cli/latest/reference/s3/rm.html
Don Cheadle

43

Anda juga dapat mempertimbangkan untuk menggunakan Amazon S3 Lifecycle untuk membuat kedaluwarsa untuk file dengan awalan foo/bar1.

Buka konsol browser S3 dan klik sebuah ember. Kemudian klik Properties dan kemudian LifeCycle.

Buat aturan kedaluwarsa untuk semua file dengan awalan foo/bar1dan setel tanggal ke 1 hari sejak file dibuat.

Simpan dan semua file yang cocok akan hilang dalam waktu 24 jam.

Jangan lupa untuk menghapus aturan tersebut setelah Anda selesai!

Tidak ada panggilan API, tidak ada pustaka, aplikasi, atau skrip pihak ketiga.

Saya baru saja menghapus beberapa juta file dengan cara ini.

Tangkapan layar yang menunjukkan jendela Aturan Siklus Hidup (catatan dalam gambar ini, Awalan telah dikosongkan, memengaruhi semua kunci dalam keranjang):

masukkan deskripsi gambar di sini


4
Ide bagus untuk menggunakan Lifecycle alih-alih beberapa perintah hapus.
xis

Tepatnya, biarkan S3 melakukannya untuk Anda.
Ryan

Anda juga dapat menerapkan ini ke seluruh keranjang, memungkinkan Anda untuk menghapus keranjang.
Memanjakan diri

8

Dengan s3cmdpaket yang diinstal pada mesin Linux, Anda dapat melakukan ini

s3cmd rm s3://foo/bar --recursive


1
Menurut bantuannya, itu bisa berupa penghapusan objek tunggal s3cmd del s3://BUCKET/OBJECTatau penghapusan seluruh keranjang s3cmd rb s3://BUCKET. Tidak ada s3cmd rm, setidaknya menurut s3cmd --help.
Paul McMurdie

s3cmd rmsedang dalam bantuan pada 2019 (sebagai alias untuk del), ini adalah jawaban yang sangat bagus. Alat awscli hanya bekerja pada /prefiks pengakhiran, tetapi tidak pada folder dan prefiks nama file parsial, sedangkan s3cmd bekerja pada kedua kasus. Jawaban ini membutuhkan lebih banyak suara positif, saya harus menggulir terlalu jauh untuk menemukan solusi yang tepat.
David Parks

8

Jika Anda ingin menghapus semua objek dengan awalan "foo /" menggunakan Java AWS SDK 2.0

import java.util.ArrayList;
import java.util.Iterator;
import software.amazon.awssdk.services.s3.S3Client;
import software.amazon.awssdk.services.s3.model.*;

//...

ListObjectsRequest listObjectsRequest = ListObjectsRequest.builder()
    .bucket(bucketName)
    .prefix("foo/")
    .build()
;
ListObjectsResponse objectsResponse = s3Client.listObjects(listObjectsRequest);

while (true) {
    ArrayList<ObjectIdentifier> objects = new ArrayList<>();

    for (Iterator<?> iterator = objectsResponse.contents().iterator(); iterator.hasNext(); ) {
        S3Object s3Object = (S3Object)iterator.next();
        objects.add(
            ObjectIdentifier.builder()
                .key(s3Object.key())
                .build()
        );
    }

    s3Client.deleteObjects(
        DeleteObjectsRequest.builder()
            .bucket(bucketName)
            .delete(
                Delete.builder()
                    .objects(objects)
                    .build()
            )
            .build()
    );

    if (objectsResponse.isTruncated()) {
        objectsResponse = s3Client.listObjects(listObjectsRequest);
        continue;
    }

    break;
};

1
Saya tidak dapat menemukan demonstrasi yang lebih jitu tentang apa yang orang tidak suka tentang Jawa daripada jawaban ini ...
Jivan

3

Jika menggunakan AWS-SKD untuk ruby ​​V2.

s3.list_objects(bucket: bucket_name, prefix: "foo/").contents.each do |obj|
  next if obj.key == "foo/" 
  resp = s3.delete_object({
    bucket: bucket_name,
    key: obj.key,
  })
end

mohon perhatiannya, semua "foo / *" di bawah keranjang akan dihapus.


2

Saya baru saja menghapus semua file dari bucket saya dengan menggunakan PowerShell:

Get-S3Object -BucketName YOUR_BUCKET | % { Remove-S3Object -BucketName YOUR_BUCKET -Key $_.Key -Force:$true }

Terima kasih telah memposting jawaban ini, saya mencoba melakukan hal ini dengan tepat dan menempatkan -Key "% _. Key" yang tidak berfungsi.
Scott Gartner


2

Jawaban yang dipilih kehilangan satu langkah.

Bantuan per aws s3:

Saat ini, tidak ada dukungan untuk penggunaan karakter pengganti gaya UNIX dalam argumen jalur perintah. Namun, sebagian besar perintah memiliki --exclude "<value>"dan --include "<value>" parameter yang dapat mencapai hasil yang diinginkan ......... Jika ada beberapa filter, aturannya adalah filter yang muncul kemudian di perintah akan diutamakan daripada filter yang muncul sebelumnya pada perintah. Misalnya, jika parameter filter yang diteruskan ke perintah adalah --exclude "*" --include "*.txt"Semua file akan dikecualikan dari perintah kecuali untuk file yang diakhiri dengan .txt

aws s3 rm --recursive s3://bucket/ --exclude="*" --include="/folder_path/*" 

0

Cara terbaik adalah menggunakan aturan siklus hidup untuk menghapus seluruh konten bucket. Secara terprogram Anda dapat menggunakan kode berikut (PHP) untuk aturan siklus hidup PUT.

$expiration = array('Date' => date('U', strtotime('GMT midnight')));
$result = $s3->putBucketLifecycle(array(
            'Bucket' => 'bucket-name',
            'Rules' => array(
                array(
                    'Expiration' => $expiration,
                    'ID' => 'rule-name',
                    'Prefix' => '',
                    'Status' => 'Enabled',
                ),
            ),
        ));

Dalam kasus di atas semua objek akan dihapus Tanggal mulai - "Hari ini GMT tengah malam".

Anda juga dapat menentukan Hari sebagai berikut. Tetapi dengan Hari itu akan menunggu setidaknya 24 jam (minimal 1 hari) untuk mulai menghapus isi ember.

$expiration = array('Days' => 1);

0

Saya perlu melakukan hal berikut ...

def delete_bucket
  s3 = init_amazon_s3
  s3.buckets['BUCKET-NAME'].objects.each do |obj|
    obj.delete
  end
end

def init_amazon_s3
  config = YAML.load_file("#{Rails.root}/config/s3.yml")
  AWS.config(:access_key_id => config['access_key_id'],:secret_access_key => config['secret_access_key'])
  s3 = AWS::S3.new
end

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.