Введение
Работающему приложению нужно читать закрытый отчёт. Вы свяжете роль IAM и профиль экземпляра через ссылки Terraform, предоставите доступ к нужному объекту и проверите фактические запросы приложения до и после удаления разрешения.
Эта лабораторная работа предполагает знание ссылок Terraform и развёртывания EC2, а также доверия ролей AWS, профилей экземпляров и ограниченных разрешений S3. Новая среда предоставляет работающее приложение, его сеть, закрытый бакет с отчётом и постороннее эталонное приложение. Вы сохраните предоставленные данные и эталонную среду нетронутыми.
Связь с сертификацией
| Сертификация | Задача экзамена | Практика |
|---|---|---|
| Cloud Practitioner (CLF-C02) | Задача 2.3 | Роли IAM и разрешения на объекты с минимальными привилегиями. |
| Solutions Architect – Associate (SAA-C03) | Задача 1.1 | Доступ рабочей нагрузки на основе роли с ограниченными разрешениями. |
| CloudOps Engineer – Associate (SOA-C03) | Задача 4.1 | Базовая реализация роли и политики IAM. |
Обзор лабораторной работы

Предоставление работающему приложению идентичности роли
На этом шаге вы определите роль EC2 и профиль экземпляра, прикрепите профиль к предоставленному приложению и увидите его действующую идентичность рабочей нагрузки.
Верхний AWS View отображает те же ресурсы, которые запрашиваются в Terminal. Его селектор Request path позволяет запросить состояние приложения, идентичность рабочей нагрузки или любой из двух закрытых объектов. Terminal использует подготовленную идентичность оператора; приложение использует собственную роль экземпляра. Успешный запрос оператора не доказывает, что у приложения есть разрешение.
Изучите подготовленную корневую конфигурацию и запишите идентификатор экземпляра:
cd /home/labex/project/application-reports
cat terraform.tfvars.json
cat application.tf
terraform state list
INSTANCE_ID=$(terraform output -raw instance_id)
echo "$INSTANCE_ID"
REPORT_BUCKET=$(terraform output -raw report_bucket)
echo "$REPORT_BUCKET"
Существующее состояние управляет экземпляром приложения. Сеть, AMI, бакет и эталонное приложение предоставлены отдельно. User Data уже указывает приложению на report.csv в подготовленном бакете, но не содержит ключа доступа.
В AWS View выберите application-server, User · 198.51.100.10, Application · 8081 и Health, затем нажмите Send request. Ожидайте Connected · 200 и Report application. Выберите Private report и отправьте запрос снова. Приложение пока не может его прочитать и сообщает Connected · 503 с Application storage unavailable: HTTP-приложение доступно, но у него нет учётных данных рабочей нагрузки.
Политика доверия роли IAM определяет, кто может принять эту роль. Профиль экземпляра связывает роль с EC2. Ни один из этих объектов сам по себе не предоставляет разрешение читать объект S3. Создайте эти два ресурса:
cat > identity.tf <<'HCL'
resource "aws_iam_role" "reports" {
name = "tf-report-reader"
assume_role_policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Effect = "Allow"
Principal = { Service = "ec2.amazonaws.com" }
Action = "sts:AssumeRole"
}]
})
}
resource "aws_iam_instance_profile" "reports" {
name = "tf-report-reader"
role = aws_iam_role.reports.name
}
HCL
sed -i '/vpc_security_group_ids/a\ iam_instance_profile = aws_iam_instance_profile.reports.name' application.tf
terraform fmt
terraform validate
terraform plan
Команда sed вставляет атрибут профиля экземпляра после существующего атрибута группы безопасности. Его ссылка на ресурс связывает работающий экземпляр с профилем, который ссылается на роль. Изучите план: создание роли и профиля и обновление существующей связи экземпляра без замены экземпляра или изменения User Data.
Примените изменения и введите yes:
terraform apply
Изучите фактическую связь и профиль:
aws ec2 \
describe-iam-instance-profile-associations \
--filters "Name=instance-id,Values=$INSTANCE_ID" \
--query 'IamInstanceProfileAssociations[].{Instance:InstanceId,State:State,Profile:IamInstanceProfile.Arn}'
aws iam \
get-instance-profile \
--instance-profile-name tf-report-reader \
--query 'InstanceProfile.{Name:InstanceProfileName,Roles:Roles[].RoleName}'
В AWS View выберите Workload identity для application-server и отправьте запрос. Ожидайте Connected · 200 и ARN, содержащий assumed-role/tf-report-reader/. Он поступает от STS внутри гостевой системы с использованием временных учётных данных роли, а не от оператора Terminal.
Выберите Private report и отправьте запрос снова. Ожидайте Connected · 403 и Access denied. Идентичность роли теперь работает, но разрешения на чтение объекта пока нет. Это намеренная ошибка авторизации.
Предоставление доступа только к нужному отчёту
На этом шаге вы предоставите роли приложения одно разрешение на чтение объекта и проверите как разрешённый отчёт, так и посторонний закрытый объект.
Политика разрешений роли определяет, что может делать её сеанс. Используйте политику идентичности, разрешающую s3:GetObject для точного ARN report.csv. Имя бакета берётся из предоставленного входного значения; роль — из ссылки на ресурс. Статическим учётным данным не место в User Data.
cat > permissions.tf <<'HCL'
resource "aws_iam_role_policy" "report" {
name = "ReadApplicationReport"
role = aws_iam_role.reports.id
policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Effect = "Allow"
Action = ["s3:GetObject"]
Resource = ["arn:aws:s3:::${var.report_bucket}/report.csv"]
}]
})
}
HCL
terraform fmt
terraform validate
terraform plan
План добавляет одну политику. Он не должен заменять приложение или создавать новый бакет. Примените изменения и введите yes:
terraform apply
В AWS View оставьте выбранными application-server, User и порт 8081. Выберите Private report и отправьте запрос. Ожидайте Connected · 200 с отчётом:
period,total
Q1,320
Выберите Unrelated private object и отправьте ещё один запрос. Ожидайте Connected · 403 и Access denied. Приложение может читать свой отчёт, тогда как private.csv остаётся вне разрешения. Этот 403 — фактический результат авторизации S3, возвращённый доступным приложением, а не ошибка сетевого подключения.
Вернитесь к Workload identity и отправьте запрос снова. Его ARN по-прежнему должен определять роль рабочей нагрузки. Подтвердите согласованность:
terraform plan
Ожидайте No changes.

Отзыв разрешения и проверка фактического результата
На этом шаге вы удалите только политику чтения и покажете, что работающее приложение с действительной идентичностью роли больше не имеет доступа к отчёту.
Удаление разрешения отличается от отсоединения профиля или остановки экземпляра. Сохраните роль и профиль, удалите конфигурацию ресурса политики, затем изучите удаление:
rm permissions.tf
terraform plan
Ожидайте удаление политики чтения без замены экземпляра. Примените изменения и введите yes:
terraform apply
Независимо прочитайте имена оставшихся встроенных политик:
aws iam \
list-role-policies \
--role-name tf-report-reader \
--query PolicyNames
Ожидайте []. В AWS View отправьте приложению запрос Workload identity. Он по-прежнему возвращает Connected · 200 с тем же именем роли. Затем отправьте запросы Private report и Unrelated private object. Оба должны вернуть Connected · 403 и Access denied. Отказ в чтении доказывает, что удаление разрешения влияет на фактические запросы рабочей нагрузки, хотя приложение и его связь с ролью всё ещё существуют.
terraform plan
Ожидайте No changes.
Удаление управляемых ресурсов с сохранением предоставленных данных
На этом шаге вы удалите управляемые экземпляр, профиль и роль, сохранив внешний бакет с отчётом, его объекты и эталонную среду.
Политика уже удалена. Изучите оставшуюся область удаления:
terraform plan -destroy
Ожидайте три управляемых ресурса: экземпляр приложения, профиль экземпляра и роль IAM. Затем удалите их и введите yes:
terraform destroy
Завершение работы того же экземпляра должно подтверждаться самим сервисом:
aws ec2 \
describe-instances \
--instance-ids "$INSTANCE_ID" \
--query 'Reservations[].Instances[].{ID:InstanceId,State:State.Name}'
terraform state list
Ожидайте terminated и отсутствие управляемых ресурсов в состоянии. Запросите списки ролей и профилей по точным именам; успешно полученные пустые списки подтверждают отсутствие, не принимая ошибку аутентификации за очистку:
aws iam list-roles --query "Roles[?RoleName=='tf-report-reader'].RoleName"
aws iam list-instance-profiles --query "InstanceProfiles[?InstanceProfileName=='tf-report-reader'].InstanceProfileName"
Оба возвращают []. Бакет предоставлен вне этого состояния. Используйте оператора Terminal, чтобы прочитать оба сохранённых объекта и изучить их байты. Эти чтения оператором проверяют сохранность; ограниченный доступ приложения проверялся отдельно через его роль.
aws s3api get-object --bucket "$REPORT_BUCKET" --key report.csv /tmp/retained-report.csv
cat /tmp/retained-report.csv
aws s3api get-object --bucket "$REPORT_BUCKET" --key private.csv /tmp/retained-private.csv
cat /tmp/retained-private.csv
Отчёт остаётся period,total / Q1,320; посторонний объект остаётся private,retained. В AWS View выберите reference-server, User, Application · 8081 и Health, затем отправьте запрос. Ожидайте Connected · 200 и Reference application.
Сохраните файлы Terraform для изучения. Последующий обычный план предложил бы повторное создание по оставшейся конфигурации; успешное удаление не требует удаления этой конфигурации.
Резюме
Вы связали экземпляр приложения с ролью через ссылки Terraform, разобрались в различии между идентичностью роли и разрешением на объект и проверили как успешное чтение закрытого отчёта, так и отказ для постороннего объекта. Затем вы отозвали разрешение, увидели фактическую ошибку авторизации и удалили управляемые ресурсы, сохранив предоставленные данные и эталонное приложение.



