Стоит ли использовать обратный прокси nginx для хранения облачных объектов?
В настоящее время я реализую архитектуру хранения изображений для своей службы.
Как я прочитал в одной статье, неплохо было бы переместить весь
трафик загрузки и скачивания изображений во внешнее хранилище облачных объектов.
https://medium.com/@jgefroh/software-architecture-image-uploading-67997101a034
Как я заметил, существует множество поставщиков облачных хранилищ объектов:
- Amazon S3
- Google Cloud Storage
- Microsoft Azure Blob Storage
- Alibaba Object Storage
- Oracle Object Storage
- IBM Object Storage
- Backblaze B2 Object
- Exoscale Object Storage
- Aruba Object Storage
- OVH Object Хранилище
- DreamHost DreamObjects
- Файлы Rackspace Cloud
- Цифровые океанические пространства
- Хранилище горячих объектов Wasabi
Мой первый выбор был Amazon S3, потому что
почти вся моя системная инфраструктура расположена на AWS.
Однако я вижу много проблем с этим хранилищем объектов.
(Пожалуйста, поправьте меня, если я ошибаюсь в любом пункте ниже)
1) Дорогая доставка бревен
AWS взимает плату за все операционные запросы. Если мне нужно платить за все запросы, я хотел бы видеть все журналы запросов. и я хотел бы получить эти журналы как можно быстрее. AWS S3 обеспечивает доставку журналов, но с большой задержкой, и каждый журнал предоставляется как отдельный файл в другом сегменте S3, поэтому каждый журнал представляет собой отдельный запрос на запись S3. Запросы на запись более дорогие, они стоят примерно 5 долларов за 1 млн запросов. Существует еще одна возможность запускать AWS Lambda при каждом запросе, однако это также дополнительная плата в размере 0,2 доллара США за 1 миллион вызовов лямбда-выражения. Таким образом, на мой взгляд, доставка журналов запросов S3 обходится слишком дорого.
2) Невозможно настроить максимальную длину содержимого объекта глобально для всего сегмента.
Я не нашел возможности настроить ограничение максимального размера объекта (длины содержимого) для всего ведра. Вкратце - я хочу иметь возможность блокировать загрузку файлов, размер которых превышает указанный лимит для выбранного сегмента. Я знаю, что можно указать длину содержимого загруженного файла в предварительно заданных URL-адресах PUT, однако я думаю, что это должно быть доступно для глобальной настройки для всего сегмента.
3) Невозможно настроить ограничение скорости запросов на IP-адрес в минуту непосредственно в корзине.
Поскольку все запросы S3 являются платными, я хотел бы иметь возможность ограничить лимит запросов, которые будут выполняться в моем сегменте с одного IP-адреса. Я хочу предотвратить массовые загрузки и выгрузки с одного IP-адреса, и я хочу, чтобы его можно было настраивать для всего сегмента. Я знаю, что эту функцию может предоставить AWS WAF, подключенный к Cloudfront, однако такие проверенные WAF запросы обходятся слишком дорого! Вы должны платить 0,60$ за каждый миллион проверенных запросов. Прямые запросы Amazon S3 стоят 0,4 доллара за 1 млн запросов, поэтому в этом нет никакого смысла и совершенно не выгодно использовать AWS WAF в качестве опции ограничения скорости для запросов S3 в качестве "защиты кошелька" от DOS-атак.
4) Невозможно создать предварительно подписанный URL-адрес "одноразовая загрузка".
Сгенерированные предварительно подписанные URL-адреса можно использовать несколько раз, пока не истек срок действия. Это означает, что вы можете загружать один файл много раз, используя один и тот же заранее заданный URL. Было бы замечательно, если бы AWS S3 API предоставлял возможность создавать заранее заданные URL-адреса для "одноразовой загрузки". Я знаю, что могу реализовать такую функцию "разовая загрузка" самостоятельно.
Например, см. Эту ссылку https://serverless.com/blog/s3-one-time-signed-url/
Однако, на мой взгляд, такая функциональность должна предоставляться напрямую через S3 API.
5) Каждый запрос к S3 платный!
Допустим, вы создали частную корзину. Однако никто не может получить доступ к данным в нем.... Кто угодно из Интернета может запускать массовые запросы в вашей корзине... и Amazon будет взимать с вас плату за все запрещенные 403 запроса!!! Не очень удобно, что кто-то может "истощить мой кошелек" в любое время, зная только название моего ведра! Это далеко не безопасно!, особенно если вы дадите кому-то прямой URL-адрес S3 с адресом корзины. Каждый, кто знает название корзины, может выполнить массовые 403 запроса и опустошить мой кошелек!!! Кто-то уже задавал этот вопрос здесь, и я думаю, это все еще проблема
https://forums.aws.amazon.com/message.jspa?messageID=58518
На мой взгляд, запрещенные запросы 403 не должны оплачиваться вообще!
6) Невозможно заблокировать сетевой трафик к S3 через правила NaCL,
потому что каждый запрос к S3 является платным. Я хотел бы иметь возможность полностью блокировать сетевой трафик к моей корзине S3 на нижнем сетевом уровне. Поскольку сегменты S3 не могут быть размещены в частном VPC, я не могу блокировать трафик с определенного IP-адреса с помощью правил NaCl. На мой взгляд, AWS должен предоставлять такие правила NaCl для ведер S3 (я имею в виду правила NaCL, а не правила ACL, которые блокируют только уровень приложения)
Из-за всех этих проблем я рассматриваю возможность использования nginx
в качестве прокси для всех запросов, сделанных в мои частные корзины S3.
Преимущества этого решения:
- Я могу бесплатно оценивать запросы на ограничение до S3, но хочу
- Я могу кэшировать изображения на моем nginx бесплатно - меньше запросов к S3
- Я могу добавить дополнительный уровень безопасности с помощью Lua Resty WAF (https://github.com/p0pr0ck5/lua-resty-waf)
- Могу быстро отсечь запросы с телом запроса больше указанного
- Я могу предоставить дополнительную аутентификацию запроса с использованием openresty
(пользовательский код lua может выполняться по каждому запросу) - Я могу легко и быстро получить все журналы доступа с моей машины EC2 nginx и переслать их в облачное хранилище с помощью cloud-watch-agent.
Недостатки этого решения:
Мне нужно передать весь трафик на S3 через мои машины EC2 и масштабировать мои машины EC2 nginx с использованием группы автомасштабирования.
Прямой трафик в корзину S3 по-прежнему возможен из Интернета для всех, кто знает название моей корзины!
(Нет возможности скрыть ведро S3 в частной сети)
МОИ ВОПРОСЫ
Считаете ли вы, что такой подход с обратным прокси-сервером nginx перед хранилищем объектов хорош?
Или, может быть, лучший способ - просто найти альтернативного поставщика хранилища облачных объектов, а не запросы хранилища прокси-объектов вообще?
Буду очень благодарен за рекомендации поставщиков альтернативных хранилищ.
Такая информация о данной рекомендации была бы предпочтительнее.
Имя поставщика хранилища объектов
A. Сколько стоит трафик INGRESS?
Б. Сколько стоит трафик ЭГРЕСС?
C. Какова цена ЗАПРОСОВ?
D. Какие варианты оплаты доступны?
E. Есть ли долгосрочное соглашение?
F. Где расположены дата-центры?
G. Предоставляет ли он совместимый с S3 API?
H. Обеспечивает ли он полный доступ ко всем журналам запросов?
I. Предоставляет ли он настраиваемый лимит скорости для каждого IP-адреса в минуту для сегмента?
J. Позволяет ли скрыть хранилище объектов в частной сети или разрешить сетевой трафик только с определенного IP-адреса?
На мой взгляд, ИДЕАЛЬНЫЙ поставщик хранилища облачных объектов должен:
1) Предоставлять журналы доступа для всех запросов, сделанных в сегменте (номер IP, код ответа, длина содержимого и т. Д.)
2) Предоставлять возможность ограничивать количество запросов сегментов на IP-номер в минуту.
3) Обеспечьте возможность отсечения трафика от вредоносных IP-адресов на сетевом уровне
4) Обеспечьте возможность скрыть сегменты хранилища объектов в частной сети или предоставить доступ только для определенных IP-номеров
5) Не взимать плату за запрещенные запросы 403
Буду очень благодарен за все ответы, комментарии и рекомендации С
уважением
2 ответа
Использование nginx в качестве обратного прокси для облачного хранилища объектов является хорошей идеей для многих случаев использования, и вы можете найти в Интернете несколько руководств о том, как это сделать (по крайней мере, с s3).
Я не знаком со всеми функциями, доступными у всех поставщиков облачных хранилищ, но сомневаюсь, что какой-либо из них предоставит вам все функции и гибкость, которые есть у nginx.
Что касается ваших недостатков:
Масштабирование всегда является проблемой, но с помощью тестов производительности вы можете увидеть, что nginx может обрабатывать большую пропускную способность даже на небольших машинах.
Для этого есть решение в AWS. Сначала сделайте свою корзину S3 частной, а затем вы сможете:
- Разрешить доступ к вашей корзине только из экземпляров EC2, на которых запущены ваши серверы nginx
- генерировать предварительно подписанные URL-адреса для вашей корзины S3 и предоставлять их своим клиентам с помощью nginx.
Обратите внимание, что оба решения вашей второй проблемы требуют некоторой разработки.
Если у вас есть инфраструктура AWS и вы хотите реализовать локальный S3-совместимый API, вы можете изучить MinIO.
Это эффективное объектное хранилище, которое защищает данные с помощью Erasure Coding.