Перейти до вмісту

Модуль 1.4: Amazon S3 та об'єктне сховище

Складність: [MEDIUM] | Час на виконання: 2.5 год | Передумови: Модуль 1.1

Чому цей модуль важливий

Розділ «Чому цей модуль важливий»

У 2017 році оборонний підрядник випадково розкрив особисту інформацію, дані про допуски до секретності та паролі тисяч державних службовців. Дані не були викрадені через складний мережевий злом. Вони знаходилися в бакеті Amazon S3 під назвою defense-contractor-internal-data. Дозволи бакета були необачно змінені розробником, який намагався виправити скрипт розгортання, ненавмисно надавши доступ READ групі AllUsers — фактично зробивши його публічним для всього інтернету. Будь-хто, хто міг вгадати URL, міг завантажити файли. Дані залишалися відкритими протягом декількох місяців, поки їх не знайшов дослідник з безпеки.

Amazon Simple Storage Service (S3) — це фундаментальний рівень зберігання даних у хмарі. Він безмежно масштабований, надзвичайно надійний і обслуговує трильйони об’єктів по всьому світу. Завдяки своїй доступності та простоті використання, він став стандартним місцем для зберігання ресурсів додатків, бекапів баз даних, величезних озер даних (data lakes) та хостингу статичних веб-сайтів.

Однак ця доступність — палиця з двома кінцями. S3 за замовчуванням знаходиться прямо в публічному інтернеті (з точки зору мережевої маршрутизації, а не прав доступу). Одна неправильно налаштована політика бакета може миттєво перетворити приватне сховище даних на публічний витік. У цьому модулі ви вивчите механіку об’єктного зберігання на відміну від традиційного файлового. Ви опануєте рівні безпеки, що захищають дані в S3, впровадите правила життєвого циклу для автоматизації економних стратегій архівування та навчитеся створювати безпечні тимчасові механізми доступу для обміну об’єктами без відкриття всього бакета.


Об’єктне сховище vs Файлове сховище

Розділ «Об’єктне сховище vs Файлове сховище»

Якщо ви користувалися традиційною операційною системою або мережевим накопичувачем (NAS), ви знайомі з Файловим сховищем. Дані організовані в ієрархічне дерево вкладених директорій та папок. Модифікація великого файлу зазвичай передбачає оновлення лише змінених блоків на диску.

S3 — це Об’єктне сховище. Воно працює за принципово іншою логікою:

  • Плоска структура: В S3 немає справжніх директорій або папок. Усе зберігається у величезному пласкому контейнері, який називається Бакет (Bucket).
  • Ключі та Об’єкти: Дані зберігаються як Об’єкт, що складається з самих даних файлу та його метаданих. Кожен об’єкт ідентифікується унікальним Ключем (Key — фактично шлях/ім’я файлу). Коли ви бачите шлях на кшталт images/2023/photo.jpg в S3, images/2023/ не є папкою; увесь рядок images/2023/photo.jpg — це просто довге ім’я ключа. Консоль візуально імітує папки для вашої зручності.
  • Незмінність (Immutability): Об’єкти в S3 незмінні. Ви не можете відкрити відеофайл на 10 ГБ в S3, відредагувати метадані і зберегти тільки зміни. Якщо ви змінюєте об’єкт, S3 повністю перезаписує існуючий об’єкт новою версією.
ФункціяФайлове сховище (EFS/NFS)Блочне сховище (EBS)Об’єктне сховище (S3)
СтруктураІєрархічна (папки/файли)Сирі блоки на дискуПлоский простір (ключі)
ДоступПротокол NFS/SMBПриєднано до однієї EC2HTTP REST API
Зміна на місціТакТакНі (повне перезаписування)
Макс. розмірОбмежено дискомОбмежено томом5 ТБ на об’єкт
МетаданіБазові (права, час)Немає (сирі блоки)Багаті кастомні пари ключ-значення
Типове використ.Спільні папки, CMSБази даних, диски ОСБекапи, озера даних, статика
НадійністьЗалежить від конфігу99.999% (у межах AZ)99.999999999% (11 дев’яток)

Думайте про це так: EBS — це жорсткий диск, прикручений болтами до одного сервера; EFS — це мережева папка, яку монтують усі; а S3 — це величезний склад, де ви віддаєте пакунки комірнику і отримуєте квитанцію (ключ), щоб забрати їх пізніше.


Безпека S3: Рівні захисту

Розділ «Безпека S3: Рівні захисту»

Оскільки бакети S3 існують у глобальному просторі імен і доступні через HTTP-ендпоінти, їх захист потребує кількох рівнів авторизації, що накладаються один на одного. S3 оцінює дозволи за допомогою комбінації політик IAM та політик ресурсів.

Ось як працює повний потік оцінки доступу, коли запит потрапляє до S3:

┌──────────────────────┐
│ Вхідний запит │
│ (GET /my-bucket/obj)│
└──────────┬───────────┘
┌────────────────────────────────┐
│ S3 Block Public Access (BPA) │
│ Це публічний запит? │
│ Чи ввімкнено BPA? │
└───────────┬───────┬────────────┘
│ │
BPA блокує BPA пропускає
(DENY) (не публіч. або BPA вимкн)
│ │
▼ ▼
ВІДМОВЛЕНО ┌──────────────────────┐
│ Політика бакета │
│ Явна заборона? │
└──┬─────────┬─────────┘
│ │
Явна Немає явної
ЗАБОРОНА заборони
│ │
▼ ▼
ВІДМОВЛЕНО ┌──────────────────────┐
│ Політика бакета │
│ Явний дозвіл? │
└──┬─────────┬─────────┘
│ │
Явний Немає збігу
ДОЗВІЛ в політиці
│ │
▼ ▼
ДОЗВОЛЕНО ┌──────────────────┐
(якщо │ Політика IAM │
той самий │ запитувача │
акаунт) └──┬──────┬────────┘
│ │
IAM Дозвіл Немає IAM
│ Дозволу
▼ ▼
ДОЗВОЛЕНО ВІДМОВЛЕНО
Ключові правила:
- Явна ЗАБОРОНА завжди перемагає, незалежно від місця в ланцюжку.
- Крос-акаунт: і політика бакета, і IAM запитувача ПОВИННІ дозволяти.
- Один акаунт: достатньо АБО політики бакета, АБО IAM дозволу.
- BPA — це головний запобіжник від спроб публічного доступу.

Це ваш головний вимикач. BPA працює на рівні акаунта або бакета, щоб скасувати будь-яку політику, яка намагається зробити дані публічними. Якщо BPA увімкнено (а він увімкнений за замовчуванням для всіх нових бакетів), навіть якщо адміністратор напише політику бакета, яка явно надає s3:GetObject групі * (усім), S3 заблокує такий запит. Ніколи не вимикайте Block Public Access, якщо ви не хостите публічні веб-ресурси навмисно.

BPA має чотири незалежні налаштування:

НалаштуванняЩо воно блокує
BlockPublicAclsВідхиляє запити PUT, що містять публічний ACL
IgnorePublicAclsІгнорує будь-які існуючі публічні ACL на бакеті/об’єктах
BlockPublicPolicyВідхиляє політики бакета, що надають публічний доступ
RestrictPublicBucketsОбмежує доступ до бакетів із публічними політиками тільки сервісами AWS та авторизованими користувачами

Найкраща практика: увімкніть усі чотири на рівні акаунта, щоб жоден бакет у всьому акаунті не міг випадково стати публічним.

Terminal window
# Увімкнення BPA на рівні АКАУНТА (рекомендовано)
aws s3control put-public-access-block \
--account-id $(aws sts get-caller-identity --query Account --output text) \
--public-access-block-configuration \
"BlockPublicAcls=true,IgnorePublicAcls=true,BlockPublicPolicy=true,RestrictPublicBuckets=true"

Як ми розбирали в Модулі 1.1, політики IAM приєднуються до ідентифікатора, який робить запит (користувача або ролі). Якщо екземпляр EC2 має IAM-роль, що дозволяє s3:PutObject у конкретний бакет, він зможе завантажувати файли.

Приклад: дозволити ролі читати тільки з певного префікса:

{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"s3:GetObject",
"s3:ListBucket"
],
"Resource": [
"arn:aws:s3:::my-data-bucket",
"arn:aws:s3:::my-data-bucket/reports/*"
],
"Condition": {
"StringEquals": {
"s3:prefix": "reports/"
}
}
}
]
}

Зверніть увагу на два ARN: один для самого бакета (потрібен для ListBucket) і один для об’єктів всередині (потрібен для GetObject). Забути ARN рівня бакета — одна з найпоширеніших помилок при відлагодженні IAM.

3. Політики бакета (Bucket Policies)

Розділ «3. Політики бакета (Bucket Policies)»

Політика бакета приєднується безпосередньо до ресурсу (самого бакета). Це JSON-документ, який діє як вишибала на вході до бакета.

  • Крос-акаунт доступ: Політики бакета необхідні для того, щоб дозволити користувачам з інших акаунтів AWS читати або писати у ваш бакет.
  • Примусове шифрування: Ви можете написати політику, яка відхиляє всі s3:PutObject, якщо запит не містить заголовка, що вимагає шифрування на стороні сервера (напр., AES256).
  • Обмеження за IP: Ви можете заборонити доступ до бакета, якщо запит надходить не з діапазону IP-адрес вашого корпоративного VPN.

Приклад: вимога шифрування для всіх завантажень:

{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "DenyUnencryptedUploads",
"Effect": "Deny",
"Principal": "*",
"Action": "s3:PutObject",
"Resource": "arn:aws:s3:::my-secure-bucket/*",
"Condition": {
"StringNotEquals": {
"s3:x-amz-server-side-encryption": "aws:kms"
}
}
}
]
}

4. Списки контролю доступу (ACL)

Розділ «4. Списки контролю доступу (ACL)»

ACL — це застарілий механізм контролю доступу ще з часів до появи IAM. Вони застосовуються до окремих об’єктів або бакета. AWS наполегливо рекомендує повністю вимикати ACL (встановлюючи бакет у режим “Bucket Owner Enforced”) і покладатися виключно на IAM та політики бакета.

Політика бакета vs ACL vs IAM — коли що використовувати?

Розділ «Політика бакета vs ACL vs IAM — коли що використовувати?»
АспектПолітика IAMПолітика бакетаACL
Приєднано доІдентичності (user/role)Ресурсу (bucket)Бакета або об’єкта
Крос-акаунтТільки на стороні запитувачаМожна давати зовнішнім принципаламМожна іншим акаунтам
Макс. розмір6 144 симв. (вбудована)20 КБФіксований список
ГранулярністьБудь-яка дія AWSТільки дії S3Тільки Read/Write/Full
УмовиПовний блок ConditionПовний блок ConditionНемає
Рекомендація AWSОсновний механізмДля крос-акаунт + обмеженьВимкнути (legacy)
Коли використ.Керування діями ваших юзерівКерування доступом до бакетаМайже ніколи

Емпіричне правило: Використовуйте політики IAM для контролю доступу всередині акаунта. Використовуйте політики бакета для крос-акаунт доступу, обмежень за IP та вимог до шифрування. Вимикайте ACL.


Підписані URL-адреси (Pre-Signed URLs): Тимчасовий безпечний доступ

Розділ «Підписані URL-адреси (Pre-Signed URLs): Тимчасовий безпечний доступ»

Уявіть, що ви будуєте додаток для обміну фотографіями. Користувачі завантажують приватні фото, а додаток їх відображає.

Поганий шлях: Веб-сервер завантажує фото з S3 і пересилає його клієнту. Це створює “пляшкове горло” для мережі та пам’яті сервера. Небезпечний шлях: Ви робите бакет S3 публічним, щоб браузер клієнта міг завантажити фото за прямим посиланням. Тепер будь-хто може вкрасти ці фото.

Шлях S3: Підписані URL (Pre-Signed URLs). Ваш бекенд-додаток (який має IAM-роль із доступом до S3) використовує AWS SDK для генерації тимчасової, криптографічно підписаної URL-адреси. Ця URL надає доступ до завантаження конкретного об’єкта на конкретний період (наприклад, 5 хвилин). Бекенд передає цю URL фронтенду. Браузер користувача використовує її для завантаження фото безпосередньо з S3. Як тільки 5 хвилин минають, посилання стає недійсним.

Генерація підписаних URL

Розділ «Генерація підписаних URL»
Terminal window
# Генеруємо посилання, дійсне 300 секунд (5 хвилин)
aws s3 presign s3://my-bucket/private/report.pdf --expires-in 300
# Приклад виводу:
# https://my-bucket.s3.amazonaws.com/private/report.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=...&X-Amz-Expires=300&X-Amz-Signature=abc123...
# Генеруємо посилання для ЗАВАНТАЖЕННЯ (PUT)
aws s3 presign s3://my-bucket/uploads/user-photo.jpg \
--expires-in 3600
# Будь-хто з цим посиланням зможе завантажити файл за цим ключем протягом 1 години

Важливі деталі про підписані URL:

  • Посилання успадковує дозволи того IAM-ідентифікатора, який його створив. Якщо цей ідентифікатор втратить доступ, посилання миттєво перестануть працювати.
  • Максимальний термін дії: 7 днів, якщо підписано IAM-користувачем; 36 годин, якщо підписано через тимчасові креденшали (STS ролі).
  • Працюють як для завантаження (GET), так і для передачі файлів на сервер (PUT).

Класи зберігання та правила життєвого циклу

Розділ «Класи зберігання та правила життєвого циклу»

S3 пропонує різні класи зберігання, розроблені під різні патерни доступу. Навіщо платити преміальну ціну за дані, якими ви користуєтеся раз на рік?

Порівняння класів зберігання

Розділ «Порівняння класів зберігання»
Клас зберіганняДоступністьМін. термін зберіг.Мін. розмір об’єктаЧас отриманняЦіна $/ГБ/місВартість отрим.Найкраще для
S3 Standard99.99%НемаєНемаєМиттєво~$0.023НемаєАктивні дані, сайти
S3 Intelligent-Tiering99.9%НемаєНемаєМиттєво*~$0.023 + збірНемаєНевідомі патерни
S3 Standard-IA99.9%30 днів128 КБМиттєво~$0.0125$0.01/ГББекапи, копії DR
S3 One Zone-IA99.5%30 днів128 КБМиттєво~$0.01$0.01/ГБДані, що можна відновити
S3 Glacier Instant99.9%90 днів128 КБМиттєво~$0.004$0.03/ГБАрхіви з миттєвим дост.
S3 Glacier Flexible99.99%90 днівНемає1 хв - 12 год~$0.0036$0.01-0.03/ГБДовготривалі архіви
S3 Glacier Deep Archive99.99%180 днівНемає12-48 годин~$0.00099$0.02/ГБКомплаєнс (7-10 років)

Примітка: Ціни орієнтовні для регіону us-east-1 станом на 2025 рік. Актуальні дані завжди на сторінці цін S3.

S3 Intelligent-Tiering заслуговує на особливу увагу. Він автоматично переміщує об’єкти між рівнем частого та нечастого доступу на основі реального використання. Він стягує невелику місячну плату за моніторинг об’єктів (~$0.0025 за 1000 об’єктів), але може значно заощадити на великих наборах даних із непередбачуваним доступом. Плати за отримання даних немає.

Припустимо, ви зберігаєте 10 ТБ логів додатків:

СтратегіяПриблизна вартість/міс
Все у S3 Standard$235
Все у S3 Standard-IA$128
Все у Glacier Deep Archive$10
Розумне шарування (30/90/365 днів)~$40-80 (залежно від доступу)

Використання правил життєвого циклу дозволяє скоротити витрати на 75-95%.

Правила життєвого циклу (Lifecycle Rules)

Розділ «Правила життєвого циклу (Lifecycle Rules)»

Ви не хочете вручну переміщувати дані між цими рівнями. Lifecycle Rules в S3 автоматизують цей процес.

Ви можете налаштувати правило, яке каже:

  1. Коли створюються лог-файли, зберігай їх у S3 Standard.
  2. Через 30 днів перемісти їх у S3 Standard-IA.
  3. Через 90 днів перемісти їх у S3 Glacier Flexible Retrieval.
  4. Через 365 днів остаточно Видали об’єкти.

Таке автоматичне шарування радикально зменшує витрати на зберігання історичних даних.

Terminal window
# Перегляд існуючих правил життєвого циклу на бакеті
aws s3api get-bucket-lifecycle-configuration --bucket my-bucket
# Видалення всіх правил життєвого циклу (обережно!)
aws s3api delete-bucket-lifecycle --bucket my-bucket

Обмеження правил життєвого циклу

Розділ «Обмеження правил життєвого циклу»

Існують правила черговості при переході між класами зберігання. S3 впроваджує принцип “водоспаду” — ви можете переходити тільки “вниз”:

S3 Standard
├──► S3 Intelligent-Tiering
├──► S3 Standard-IA (мін. 30 днів після створення)
├──► S3 One Zone-IA (мін. 30 днів після створення)
├──► S3 Glacier Instant Retrieval (мін. 90 днів після створення)
├──► S3 Glacier Flexible Retrieval
└──► S3 Glacier Deep Archive

Ви не можете перейти з Glacier назад у Standard-IA через правило життєвого циклу. Щоб підняти дані “вгору”, ви повинні відновити їх і скопіювати вручну.


Основні команди S3 CLI

Розділ «Основні команди S3 CLI»

AWS CLI надає дві групи команд для S3:

  • aws s3 — Команди високого рівня (cp, sync, ls, mv, rm). Вони автоматично обробляють багатопотокове завантаження, повтори та паралелізм.
  • aws s3api — Низькорівневі API-виклики (put-object, get-object, put-bucket-policy). Повний контроль, ввід/вивід у JSON.
Terminal window
# Завантаження одного файлу
aws s3 cp backup.tar.gz s3://my-bucket/backups/backup.tar.gz
# Скачування файлу
aws s3 cp s3://my-bucket/backups/backup.tar.gz ./backup.tar.gz
# Копіювання між бакетами
aws s3 cp s3://source-bucket/data.csv s3://dest-bucket/archive/data.csv
# Завантаження з конкретним класом зберігання
aws s3 cp archive.tar.gz s3://my-bucket/archives/ --storage-class GLACIER
# Завантаження із шифруванням (KMS)
aws s3 cp report.pdf s3://my-bucket/confidential/ --sse aws:kms --sse-kms-key-id alias/my-key
# Копіювання цілої папки (рекурсивно)
aws s3 cp ./logs/ s3://my-bucket/logs/ --recursive
# Копіювання з фільтром — тільки .log файли
aws s3 cp ./logs/ s3://my-bucket/logs/ --recursive --exclude "*" --include "*.log"

Синхронізація директорій

Розділ «Синхронізація директорій»

aws s3 sync — основний інструмент для бекапів. Він копіює тільки нові або змінені файли (на основі розміру та часу модифікації), подібно до rsync.

Terminal window
# Синхронізація локальної папки в S3
aws s3 sync ./website/ s3://my-website-bucket/
# Синхронізація з S3 на локальну машину
aws s3 sync s3://my-bucket/data/ ./local-data/
# Синхронізація з ВИДАЛЕННЯМ файлів у цілі, яких немає в джерелі
# (робить ціль точною копією — використовуйте обережно!)
aws s3 sync ./website/ s3://my-website-bucket/ --delete
# Dry run — подивитися, що БУЛО Б зроблено, без реальних змін
aws s3 sync ./website/ s3://my-website-bucket/ --dryrun

Перегляд та перевірка

Розділ «Перегляд та перевірка»
Terminal window
# Список усіх бакетів в акаунті
aws s3 ls
# Список об'єктів у бакеті ("папки" верхнього рівня)
aws s3 ls s3://my-bucket/
# Рекурсивний список усіх об'єктів із розмірами
aws s3 ls s3://my-bucket/ --recursive --human-readable --summarize
# Отримання детальних метаданих конкретного об'єкта
aws s3api head-object --bucket my-bucket --key reports/q4-summary.pdf

Управління бакетами

Розділ «Управління бакетами»
Terminal window
# Створення бакета
aws s3 mb s3://my-new-bucket --region us-west-2
# Видалення ПОРОЖНЬОГО бакета
aws s3 rb s3://my-empty-bucket
# Видалення бакета РАЗОМ із вмістом (деструктивно!)
aws s3 rb s3://my-bucket --force
# Увімкнення версійності
aws s3api put-bucket-versioning \
--bucket my-bucket \
--versioning-configuration Status=Enabled
# Увімкнення шифрування за замовчуванням (SSE-S3)
aws s3api put-bucket-encryption \
--bucket my-bucket \
--server-side-encryption-configuration '{
"Rules": [{"ApplyServerSideEncryptionByDefault": {"SSEAlgorithm": "AES256"}}]
}'

Об’єкти в класах Glacier не можна завантажити миттєво. Спочатку треба ініціювати відновлення (restore).

Terminal window
# Ініціація відновлення (Expedited = 1-5 хв, Standard = 3-5 год, Bulk = 5-12 год)
aws s3api restore-object \
--bucket my-archive-bucket \
--key old-logs/app-2023.tar.gz \
--restore-request '{"Days": 7, "GlacierJobParameters": {"Tier": "Standard"}}'
# Перевірка статусу відновлення
aws s3api head-object --bucket my-archive-bucket --key old-logs/app-2023.tar.gz
# Заголовок "Restore" покаже:
# ongoing-request="true" → ще відновлюється
# ongoing-request="false", expiry-date="..." → готово до завантаження

S3 пропонує кілька варіантів шифрування. З січня 2023 року всі нові об’єкти шифруються за замовчуванням за допомогою SSE-S3 (AES-256), навіть якщо ви не вказали налаштування.

Тип шифруванняКим керується ключКоли використовувати
SSE-S3 (AES-256)AWS (повністю керований)За замовчуванням, найпростіший варіант
SSE-KMSAWS KMS (ви керуєте політиками)Аудит, ротація ключів, крос-акаунт
SSE-CВами (надаєте ключ у кожному запиті)Регуляторна вимога тримати ключі у себе
Client-sideВами (шифруєте перед завантаж.)Zero-trust, наскрізне шифрування

SSE-KMS — найпопулярніший вибір для корпорацій, оскільки він інтегрується з CloudTrail (кожне використання ключа логується) та підтримує автоматичну щорічну ротацію ключів.


Глибоке занурення у версійність (Versioning)

Розділ «Глибоке занурення у версійність (Versioning)»

Коли версійність увімкнена, кожне перезаписування або видалення створює нову версію замість знищення даних.

Ключ: reports/q4.pdf
Стек версій (нові зверху):
┌─────────────────────────────────────────┐
│ Delete Marker (немає даних) │ ← поточний стан = "видалено"
├─────────────────────────────────────────┤
│ Version: abc789 (Фінальна версія) │
├─────────────────────────────────────────┤
│ Version: def456 (Друга чернетка) │
├─────────────────────────────────────────┤
│ Version: ghi123 (Перше завантаж.) │
└─────────────────────────────────────────┘
Звичайний GET поверне 404 (через delete marker).
GET з ?versionId=abc789 поверне Фінальну версію.
ВИДАЛЕННЯ delete marker → повертає abc789 у статус поточної версії.

Важливі особливості версійності:

  • Версійність не можна вимкнути після ввімкнення. Її можна тільки призупинити (suspended).
  • Призупинена версійність зберігає існуючі версії, але нові об’єкти отримують null як ID версії.
  • Ви платите за кожну збережену версію. Файл 1 ГБ, перезаписаний 100 разів = 100 ГБ у рахунку.
  • MFA Delete може вимагати двофакторну аутентифікацію для видалення версій.

  1. S3 забезпечує консистентність “read-after-write” для всіх операцій PUT та DELETE. Якщо ви записали новий об’єкт і миттєво спробували його прочитати — S3 поверне нові дані. (До грудня 2020 року S3 був “eventually consistent”, тобто миттєве читання могло повернути 404 або стару версію).

  2. S3 підтримує хостинг статичних сайтів. Додавши файл index.html, вимкнувши BPA та додавши публічну політику бакета, ви отримуєте глобально доступний, високонадійний веб-сервер без жодної віртуальної машини EC2.

  3. S3 може обробляти дані на місці за допомогою S3 Select та S3 Object Lambda. S3 Select дозволяє виконувати SQL-запити безпосередньо до файлів CSV або JSON у бакеті — замість того, щоб скачувати CSV на 10 ГБ і фільтрувати його локально, ви надсилаєте запит SELECT * FROM s3object WHERE status = 'error', і S3 повертає тільки потрібні рядки. Це економить 80-90% трафіку.

  4. S3 спроєктований для надійності 99.999999999% (11 дев’яток). Це означає: якщо ви зберігаєте 10 мільйонів об’єктів, статистично ви можете втратити один раз на 10 000 років. Це досягається автоматичною реплікацією кожного об’єкта мінімум у 3 зонах доступності в межах регіону.


ПомилкаЧому це стаєтьсяЯк виправити
Витік даних через публічні бакетиВимкнення BPA, бо “програма видає 403 і так воно запрацювало”.Ніколи не вимикайте BPA для приватних даних. Виправте IAM-політики або використовуйте підписані URL.
Оплата за мільйони дрібних файлів в IAПеренесення величезної кількості логів по 5 КБ у Standard-IA для “економії”.Standard-IA має мінімальний оплачуваний розмір 128 КБ. За файл 5 КБ ви заплатите як за 128 КБ. Об’єднуйте дрібні файли в архіви перед шаруванням.
Використання S3 як бази данихОскільки є API і можна зберігати JSON, розробники пробують робити тисячі транзакцій на секунду.S3 не оптимізований для частих мілісекундних транзакційних записів. Використовуйте DynamoDB або RDS.
Ігнорування витрат на версійністьУвімкнення версійності на бакеті, що постійно оновлюється, без правил очищення.S3 бере гроші за кожну стару версію. Якщо вмикаєте версійність — ОБОВ’ЯЗКОВО налаштуйте Lifecycle Rule для видалення старих версій через певний час.
Конфлікти імен бакетівСпроба створити бакет з назвою test-bucket.Імена бакетів S3 мають бути унікальними у всьому світі серед усіх акаунтів AWS. Використовуйте префікс компанії та ID акаунта.
Забування обох ARN в IAM політикахНаписання політики тільки з ARN бакета (arn:aws:s3:::my-bucket) або тільки об’єктів (.../*).ListBucket потребує ARN бакета. GetObject/PutObject потребують ARN об’єктів з /*. Завжди вказуйте обидва.
Відсутність правил для незавершених завантаженьВеликі файли, що не завантажилися до кінця, залишають невидимі фрагменти, за які ви платите вічно.Додайте правило життєвого циклу “Abort incomplete multipart uploads” через 7 днів. Це безкоштовна економія для кожного бакета.

Питання 1: Аудитор вимагає, щоб компанія зберігала логи додатків рівно 7 років для дотримання регуляторних норм. Логи ніколи не відкриваються, якщо немає перевірки, при якій затримка у 24 години на отримання даних є цілком прийнятною. Як зберігати ці логи максимально економно?

Завантажуйте логи в S3 і використовуйте Lifecycle Rule для негайного переведення їх у клас зберігання S3 Glacier Deep Archive, який має найнижчу ціну. Налаштуйте правило на видалення об’єктів через 2 555 днів (7 років).

Питання 2: Ви намагаєтеся додати політику бакета (Bucket Policy), що надає публічний доступ на читання до префікса `images/`. Консоль AWS видає помилку і відмовляється зберігати політику. Яка найбільш імовірна причина?

На бакеті (або на рівні акаунта) увімкнено S3 Block Public Access (BPA). BPA працює як головний запобіжник, який активно блокує спроби застосувати будь-яку політику або ACL, що відкриває публічний доступ.

Питання 3: Стороння компанія з аналізу даних має щодня завантажувати CSV-файл у бакет у вашому акаунті AWS. Вони надали вам ARN своєї IAM-ролі. Як надати їм доступ, не створюючи для них IAM-користувача у вашому акаунті?

Створіть політику ресурсу (Bucket Policy) на вашому бакеті. У ній вкажіть Effect: Allow, Action: s3:PutObject, Resource: ARN вашого бакета/*, а в полі Principal вкажіть наданий ними ARN IAM-ролі. Для крос-акаунт доступу важливо, щоб дозвіл був і у вашій політиці бакета, і в їхній політиці IAM.

Питання 4: Ви видалили відеофайл розміром 1 ГБ із бакета, на якому увімкнена версійність. Ви зрозуміли, що це помилка. Чи видалено файл назавжди і як його відновити?

Ні, файл не видалено. При ввімкненій версійності звичайне видалення просто вставляє “Delete Marker” поверх об’єкта, приховуючи його зі списків. Щоб відновити файл, перейдіть у перегляд версій об’єкта і видаліть цей “Delete Marker” — це поверне попередню версію файлу в статус поточної.

Питання 5: Команда зберігає 50 мільйонів дрібних JSON-файлів (в середньому по 2 КБ кожен) у S3 Standard. Перевірка витрат пропонує перенести їх у S3 Standard-IA для економії. Чи допоможе це заощадити гроші?

Ні, це, швидше за все, збільшить витрати. Клас Standard-IA має мінімальний оплачуваний розмір об’єкта 128 КБ. За кожен файл у 2 КБ ви платитимете як за 128 КБ, тобто за 6.4 ТБ замість реальних 100 ГБ. Також Standard-IA стягує плату за отримання кожного ГБ даних. Правильний підхід: об’єднати дрібні файли у великі архіви (напр., .tar.gz) перед зміною класу зберігання.


Практична вправа: Продуктовий бакет для бекапів із управлінням життєвим циклом

Розділ «Практична вправа: Продуктовий бакет для бекапів із управлінням життєвим циклом»

У цій вправі ви створите бакет для бекапів промислового рівня: із посиленою безпекою, версійністю, автоматизацією життєвого циклу та потренуєте основні команди CLI.

Завдання 1: Створення та захист бакета

Розділ «Завдання 1: Створення та захист бакета»
Terminal window
# Генеруємо унікальне ім'я бакета
export MY_BUCKET="dojo-backup-$(openssl rand -hex 6)"
echo "Bucket name: $MY_BUCKET"
# Створюємо бакет
aws s3 mb s3://$MY_BUCKET
# Вмикаємо Block Public Access (усі чотири налаштування)
aws s3api put-public-access-block \
--bucket $MY_BUCKET \
--public-access-block-configuration \
"BlockPublicAcls=true,IgnorePublicAcls=true,BlockPublicPolicy=true,RestrictPublicBuckets=true"
# Вмикаємо шифрування за замовчуванням (SSE-S3)
aws s3api put-bucket-encryption \
--bucket $MY_BUCKET \
--server-side-encryption-configuration '{
"Rules": [{"ApplyServerSideEncryptionByDefault": {"SSEAlgorithm": "AES256"}}]
}'
# Вмикаємо версійність
aws s3api put-bucket-versioning \
--bucket $MY_BUCKET \
--versioning-configuration Status=Enabled
# Перевірка налаштувань
aws s3api get-bucket-versioning --bucket $MY_BUCKET

Завдання 2: Завантаження бекапів та робота з версіями

Розділ «Завдання 2: Завантаження бекапів та робота з версіями»

Симулюємо щоденний бекап бази даних, який перезаписує той самий файл.

Terminal window
mkdir -p ./backup-exercise
# День 1
echo '{"date": "2025-01-01", "status": "healthy"}' > ./backup-exercise/db-dump.json
aws s3 cp ./backup-exercise/db-dump.json s3://$MY_BUCKET/backups/daily/db-dump.json
# День 2 (перезаписує файл, але версійність збереже День 1)
echo '{"date": "2025-01-02", "status": "healthy"}' > ./backup-exercise/db-dump.json
aws s3 cp ./backup-exercise/db-dump.json s3://$MY_BUCKET/backups/daily/db-dump.json
# День 3 (зіпсований бекап!)
echo '{"date": "2025-01-03", "status": "CORRUPTED"}' > ./backup-exercise/db-dump.json
aws s3 cp ./backup-exercise/db-dump.json s3://$MY_BUCKET/backups/daily/db-dump.json
# Список УСІХ версій — зверніть увагу на VersionId
aws s3api list-object-versions \
--bucket $MY_BUCKET \
--prefix backups/daily/db-dump.json \
--query 'Versions[].{Key:Key,VersionId:VersionId,LastModified:LastModified}'

Завдання 3: Відновлення зіпсованого бекапа

Розділ «Завдання 3: Відновлення зіпсованого бекапа»

Повернемося до здорового бекапа за День 2, завантаживши конкретну версію.

Terminal window
# Отримуємо ID версії за День 2 (другий у списку, індекс [1])
DAY2_VERSION=$(aws s3api list-object-versions \
--bucket $MY_BUCKET \
--prefix backups/daily/db-dump.json \
--query 'Versions[1].VersionId' --output text)
# Завантажуємо саме цю версію
aws s3api get-object \
--bucket $MY_BUCKET \
--key backups/daily/db-dump.json \
--version-id $DAY2_VERSION \
./backup-exercise/restored.json
# Перезаписуємо поточний файл здоровою версією
aws s3 cp ./backup-exercise/restored.json s3://$MY_BUCKET/backups/daily/db-dump.json
echo "Бекап відновлено."

Завдання 4: Синхронізація та підписані URL

Розділ «Завдання 4: Синхронізація та підписані URL»
Terminal window
# Створюємо кілька лог-файлів
for i in 1 2 3; do echo "Log $i" > ./backup-exercise/log-$i.txt; done
# Синхронізація папки в S3 (копіюються тільки нові файли)
aws s3 sync ./backup-exercise/ s3://$MY_BUCKET/logs/ --exclude "*.json"
# Генерація підписаного посилання на 10 хвилин
SIGNED_URL=$(aws s3 presign s3://$MY_BUCKET/logs/log-1.txt --expires-in 600)
echo "Тимчасове посилання: $SIGNED_URL"
# Перевірка (має вивести вміст лога)
curl -s "$SIGNED_URL"

Завдання 5: Налаштування правил життєвого циклу

Розділ «Завдання 5: Налаштування правил життєвого циклу»

Створимо комплексну політику автоматизації.

Terminal window
cat << 'EOF' > lifecycle.json
{
"Rules": [
{
"ID": "ArchiveOldLogs",
"Filter": {"Prefix": "logs/"},
"Status": "Enabled",
"Transitions": [
{"Days": 30, "StorageClass": "STANDARD_IA"},
{"Days": 90, "StorageClass": "GLACIER"}
],
"Expiration": {"Days": 365}
},
{
"ID": "CleanupIncompleteUploads",
"Filter": {"Prefix": ""},
"Status": "Enabled",
"AbortIncompleteMultipartUpload": {"DaysAfterInitiation": 7}
}
]
}
EOF
# Застосовуємо конфігурацію
aws s3api put-bucket-lifecycle-configuration \
--bucket $MY_BUCKET \
--lifecycle-configuration file://lifecycle.json

Оскільки бакет з версійністю містить приховані дані, звичайне видалення через CLI може бути складним. Використаємо Python-скрипт для повного очищення.

Terminal window
cat << EOF > empty_bucket.py
import boto3
import sys
bucket_name = sys.argv[1]
s3 = boto3.resource('s3')
bucket = s3.Bucket(bucket_name)
print(f"Видалення всіх версій у {bucket_name}...")
bucket.object_versions.delete()
print(f"Видалення бакета {bucket_name}...")
bucket.delete()
EOF
python3 empty_bucket.py $MY_BUCKET
rm -rf ./backup-exercise lifecycle.json empty_bucket.py
  • Я створив бакет із увімкненим Block Public Access, шифруванням та версійністю.
  • Я завантажив кілька версій одного файлу і переглянув історію версій.
  • Я відновив конкретну попередню версію після симуляції псування даних.
  • Я синхронізував локальну папку з S3 і згенерував робоче підписане посилання.
  • Я застосував правила життєвого циклу для архівації та очищення.
  • Я успішно очистив усі ресурси.

Тепер, коли ви опанували обчислення та зберігання, час навчитися направляти користувачів до ваших додатків. Переходьте до Модуля 1.5: Route 53 та DNS.