2013-10-10 5 views
10

У меня есть файлы, которые загружаются на S3 и обрабатываются для какой-то задачи Redshift. После завершения этой задачи эти файлы необходимо объединить. В настоящее время я удаляю эти файлы и снова загружаю объединенные файлы. Они съедают много полосы пропускания. Есть ли способ, которым файлы могут быть объединены непосредственно на S3?Слияние файлов на AWS S3 (с использованием Apache Camel)

Я использую Apache Camel для маршрутизации.

ответ

20

S3 позволяет использовать URI файла S3 в качестве источника для операции копирования. В сочетании с API загрузки Multi-Part S3 вы можете предоставить несколько URI объектов S3 as the sources keys для многопользовательской загрузки.

Однако дьявол находится в деталях. Многопользовательский API загрузки S3 имеет минимальный размер файловой части 5 МБ. Таким образом, если какой-либо файл в серии файлов при конкатенации < 5MB, он не удастся.

Тем не менее, вы можете обойти это, используя отверстие в петле, которое позволяет загружать конечный кусок < 5MB (разрешено, потому что это происходит в реальном мире при загрузке остатков).

Мой код продукции делает это:

  1. Допрос манифест файлов, которые будут загружены
  2. Если первая часть под 5МБ, загружать части * и буфер на диск до 5 МБ не буферизацией.
  3. Прилагайте части последовательно до завершения конкатенации файлов
  4. Если файл с неограниченным сроком действия - < 5 МБ, добавьте его, затем завершите загрузку и создайте новую загрузку и продолжите.

И, наконец, в S3 API есть ошибка. ETag (на самом деле любая контрольная сумма MD5-файла на S3 неправильно пересчитана по завершении многочастной загрузки.Чтобы исправить это, скопируйте штраф по завершении. Если вы используете временное местоположение во время конкатенации, это будет разрешено на последнюю операцию копирования.

* Обратите внимание, что вы можете скачать byte range of a file. Таким образом, если часть 1 является 10K, а часть 2 является 5Гбом, вам нужно только читать в 5110K, чтобы удовлетворить размер 5MB, необходимый для продолжения .

** Вы также могли бы иметь 5MB блок нулей на S3 и использовать его в качестве используемого по умолчанию, начиная часть. Затем, когда загрузка будет завершена, сделайте копию файла, используя диапазон байтов 5MB+1 to EOF-1

P.S. Когда у меня будет время сделать суть этого кода, я отправлю ссылку здесь.

+1

Это действительно отличный ответ! Я собираюсь внедрить его для динамического создания zip-файлов, как упоминается в [этом сообщении в блоге] (http://www.w2lessons.com/2012/01/fast-zipping-in-amazon-s3.html). Я также рассматриваю возможность создания рабочего пула с помощью AWS Lambda для более быстрой обработки запроса, избегая ограничения скорости S3. – MadMod

+0

@MadMod Я не уверен, что формат Zip позволяет это посредством прямой конкатенации zip-файлов. По крайней мере вам нужно будет обновить размер и заголовки CRC существующего zip после конкатенации. –

+0

@JosephLust, любой шанс вы можете поделиться Gist? – Blexy

-6

S3 - это хранилище объектов, а не хранилище блоков. Вы должны получить объект (ы), прежде чем сможете манипулировать им/им.

Итак, ответ: Нет. Вы не можете напрямую объединять файлы на S3.

+2

Это не всегда точно.Если все, кроме одного файла, не менее 5 МБ, вы можете использовать multipart с копией, как указано ниже. – bridiver

+0

Должно ли это быть 5 ГБ (не 5 МБ)? –

+0

Нет, его 5 МБ для минимального размера детали (за исключением последней части, которая может быть меньше). –

14

Вы можете использовать Multipart Upload with Copy, чтобы объединить объекты на S3, не загружая и не загружая их снова.

Вы можете найти несколько примеров в Java, .NET или с помощью REST API here.

Смежные вопросы