20

Załóżmy, że mam komputer, który chcę mieć możliwość zapisu do określonego pliku dziennika przechowywanego w wiadrze S3.Dołącz dane do obiektu S3

Tak więc, maszyna musi mieć zdolności do pisania tego wiadra, ale nie chcę, aby miała możliwość nadpisywania lub usuwania jakichkolwiek plików w tym segmencie (w tym w tym, do którego ma pisać).

W zasadzie chcę, aby moja maszyna mogła dołączać dane tylko do tego pliku dziennika, bez nadpisywania i pobierania.

Czy istnieje sposób skonfigurowania mojego S3 do pracy w ten sposób? Może są jakieś zasady IAM, które mogę do niego dołączyć, żeby działały tak, jak chcę?

+0

Nie można modyfikować obiektów w S3. Czy możesz po prostu dołączyć nowy plik dziennika? Byłby to lepszy model i obsługiwałby wielu klientów jednocześnie. – jarmod

+0

@jarmod Tak, myślałem o tym, ale problem polega na tym, że jeśli atakujący uda się uzyskać dostęp do mojego serwera, będzie miał możliwość usunięcia lokalnego pliku przechowywanego na nim, zanim zostanie wysłany do wiadra S3 (co mówi się, że dzieje się pod koniec dnia). – Theodore

+0

Możesz również chcieć rzucić okiem na dzienniki CloudWatch. Pozwól mu zarządzać złożonością zbierania i przechowywania twoich dzienników, udostępniaj opcje wyszukiwania, zasady przechowywania i pozwalaj na generowanie alertów na podstawie danych, które możesz dostosować do swoich dzienników. – jarmod

Odpowiedz

37

Niestety, nie możesz.

S3 doesn't have an "append" operation.* Po przesłaniu obiektu nie można go zmodyfikować; Twoją jedyną opcją jest załadowanie nowego obiektu, który go zastąpi, który nie spełnia Twoich wymagań.

*: Tak, wiem, że ten post ma kilka lat. Wciąż jest dokładny.

+0

Widzę ... Dzięki. – Theodore

+0

Czy mogę wiedzieć, używając Multipart Upload, czy możemy to osiągnąć? – Anjali

+0

Przesyłanie wielu stron pozwoli ci pobrać dane do S3 bez pobierania oryginalnego obiektu, ale nie pozwoli ci na bezpośrednie zastąpienie oryginalnego obiektu. Zobacz np. https://docs.aws.amazon.com/AmazonS3/latest/API/mpUploadUploadPartCopy.html Można wtedy usunąć stary obiekt/zmienić nazwę nowego. To jednak nie jest pytanie. – MikeGM

3

Najlepszym rozwiązaniem Jestem świadomy jest użycie AWS Kinesis Firehose:

https://aws.amazon.com/kinesis/firehose/

Ich code sample wygląda skomplikowanie, lecz Twoja może być naprawdę proste. Kontynuujesz wykonywanie operacji PUT (lub BATCH PUT) w strumieniu dostarczania Kinesis Firehose w aplikacji (przy użyciu pakietu SDK AWS), a także konfigurujesz strumień dostarczania kinesis Firehose, aby przesłać strumieniowo dane do wybranego kubka AWS S3 (w AWS Kinesis Firehose).

enter image description here

To nie jest jeszcze tak wygodne, jak >> z linii poleceń Linuksa, ponieważ po utworzeniu pliku na S3 ponownie mamy do czynienia z pobieraniem, dołączając i przesyłając nowy plik, ale ci tylko trzeba to zrobić raz na partię linii, a nie na każdą linię danych, aby nie trzeba było martwić się ogromnymi opłatami z powodu wielkości operacji dołączania. Może to zrobić, ale nie widzę, jak to zrobić z konsoli.

+2

Należy zauważyć, że istnieje maksymalny czas (900 sekund od utworzenia pliku) lub maksymalny rozmiar (rozmiar pliku 128 MB) w tym celu - co oznacza, że ​​kinesis firehose będzie dołączał do tego samego pliku S3, dopóki nie osiągnie jednego z tych limitów: https : //docs.aws.amazon.com/firehose/latest/dev/create-configure.html –

0

miałem podobny problem i to poprosiłem

how to Append data in file using AWS Lambda

Oto co wymyślić rozwiązania powyższego problemu:

Zastosowanie getObject przy sprowadzaniu z istniejącego pliku

s3.getObject(getParams, function(err, data) { 
    if (err) console.log(err, err.stack); // an error occurred 
    else{ 
     console.log(data);   // successful response 
     var s3Projects = JSON.parse(data.Body); 
     console.log('s3 data==>', s3Projects); 
     if(s3Projects.length > 0) { 
      projects = s3Projects; 
     } 
    } 
    projects.push(event); 
    writeToS3(); // Calling function to append the data 
}); 

zapis w funkcji dołączania plik

function writeToS3() { 
    var putParams = { 
     Body: JSON.stringify(projects), 
     Bucket: bucketPath, 
     Key: "projects.json", 
     ACL: "public-read" 
    }; 

    s3.putObject(putParams, function(err, data) { 
     if (err) console.log(err, err.stack); // an error occurred 
     else  console.log(data);   // successful response 
     callback(null, 'Hello from Lambda'); 
    }); 
} 

Nadzieja ta pomoc !!

+0

Twoja funkcja 'writeToS3' nadpisze plik, nie dołączając do niego. – duskwuff