Ngân hàng đề — AWS Certified Solutions Architect Associate

Tìm thấy 2194 câu.

Câu 971 Chọn nhiều đáp án AWS Security, Identity, & Compliance

A research institute uses an Amazon Elastic Kubernetes Service (Amazon EKS) cluster to run machine learning workloads. The institute must ensure that Kubernetes service accounts within the EKS cluster have secure, fine-grained access to specific AWS resources for model training and data processing. The solution must use IAM roles for service accounts (IRSA) to meet these requirements.

Which combination of solutions will meet these requirements? (Select TWO.)

  1. A

    Define an IAM role that includes the required permissions. Annotate the Kubernetes service accounts with the Amazon Resource Name (ARN) of the IAM role.

  2. B

    Create an IAM policy that defines the necessary permissions for AWS resources. Attach the policy directly to the IAM role of the EKS worker nodes.

  3. C

    Configure a trust relationship between the IAM roles for the service accounts and an OpenID Connect (OIDC) identity provider associated with the EKS cluster.

  4. D

    Modify the EKS cluster's worker node IAM role to include permissions for Kubernetes service accounts. Ensure all service accounts map to a single IAM role.

  5. E

    Implement pod security policies in the EKS cluster to restrict pods from accessing unauthorized AWS resources.

Xem giải thích

Đáp án

A và C.

  • A — Định nghĩa IAM role chứa quyền cần thiết, rồi annotate Kubernetes service account bằng ARN của role đó
  • C — Cấu hình trust relationship giữa IAM role và OIDC identity provider gắn với cụm EKS

Vì sao đúng

IRSA (IAM Roles for Service Accounts) gồm đúng hai mảnh, và hai phương án này là hai mảnh đó: | Mảnh | Việc | |---|---| | OIDC provider + trust policy (C) | cho phép service account "đóng vai" IAM role | | Annotation trên service account (A) | nói pod dùng role nào |

Cách IRSA hoạt động:

1. EKS phát hành một JWT token cho service account
2. Pod gọi sts:AssumeRoleWithWebIdentity kèm token đó
3. IAM kiểm tra token với OIDC provider của cụm
4. Trust policy của role xác nhận đúng service account
5. IAM trả về credential TẠM THỜI
        ↓
    Pod dùng credential đó gọi API AWS

Bước 1 — tạo OIDC provider cho cụm:

eksctl utils associate-iam-oidc-provider \
  --cluster cum-nghien-cuu --approve

Bước 2 — trust policy của role:

{"Version": "2012-10-17",
 "Statement": [{
   "Effect": "Allow",
   "Principal": {"Federated":
     "arn:aws:iam::123456789012:oidc-provider/oidc.eks.ap-southeast-1.amazonaws.com/id/ABC123"},
   "Action": "sts:AssumeRoleWithWebIdentity",
   "Condition": {"StringEquals": {
     "oidc.eks.ap-southeast-1.amazonaws.com/id/ABC123:sub":
       "system:serviceaccount:hoc-may:sa-huan-luyen",
     "oidc.eks.ap-southeast-1.amazonaws.com/id/ABC123:aud":
       "sts.amazonaws.com"}}}]}

⚠ Điều kiện :sub là phần tạo ra "fine-grained":

system:serviceaccount:<namespace>:<tên-service-account>
        ↓
    CHỈ service account đó, trong CHỈ namespace đó
    mới dùng được role này
    → pod ở namespace khác không đóng vai được

Bước 3 — annotate service account:

apiVersion: v1
kind: ServiceAccount
metadata:
  name: sa-huan-luyen
  namespace: hoc-may
  annotations:
    eks.amazonaws.com/role-arn: arn:aws:iam::123456789012:role/VaiTroHuanLuyen

Hoặc dùng eksctl làm cả ba bước:

eksctl create iamserviceaccount \
  --name sa-huan-luyen --namespace hoc-may \
  --cluster cum-nghien-cuu \
  --attach-policy-arn arn:aws:iam::aws:policy/AmazonS3ReadOnlyAccess \
  --approve

Ba lợi ích so với gắn quyền vào node role: | Lợi ích | Chi tiết | |---|---| | Mỗi pod có quyền RIÊNG | không chia sẻ | | Credential tạm, tự luân chuyển | | | Đặc quyền tối thiểu thật sự | |

Vì sao các phương án khác sai

  • **B. Gắn IAM policy trực tiếp vào IAM role của worker node — đây là phương án gần nhất vì cũng cấp được quyền, nhưng nó phá vỡ yêu cầu "fine-grained": MỌI pod chạy trên node đó đều dùng chung quyền. Một pod bị xâm nhập là kẻ tấn công có toàn bộ quyền của node.
  • **D. Sửa node role để gồm quyền cho service account, ánh xạ mọi service account vào MỘT role — nói thẳng ra là ngược hẳn nguyên tắc đặc quyền tối thiểu, và cũng không phải cách IRSA hoạt động.
  • **E. Dùng Pod Security Policy hạn chế pod truy cập tài nguyên AWS — sai công cụ: PSP (nay là Pod Security Standards) kiểm soát cấu hình bảo mật của pod (chạy dưới root không, mount host path không), không liên quan tới quyền AWS. Và PSP đã bị loại bỏ từ Kubernetes 1.25.

Ghi nhớ

⚠ Ba cách cấp quyền AWS cho pod EKS — bảng phải thuộc: | Cách | Phạm vi | Đánh giá | |---|---|---| | Node instance role | MỌI pod trên node | thô, không nên | | IRSA | từng service account | chuẩn mực ← câu này | | EKS Pod Identity | từng service account | mới hơn, đơn giản hơn |

⚠ EKS Pod Identity là lựa chọn mới đáng biết:

aws eks create-addon --cluster-name cum-nghien-cuu \
  --addon-name eks-pod-identity-agent

aws eks create-pod-identity-association --cluster-name cum-nghien-cuu \
  --namespace hoc-may --service-account sa-huan-luyen \
  --role-arn arn:aws:iam::123456789012:role/VaiTroHuanLuyen

IRSA và Pod Identity — bảng phân biệt: | | IRSA | Pod Identity | |---|---|---| | Cần OIDC provider | ✅ | ❌ | | Trust policy | phức tạp, theo cụm | đơn giản, dùng lại được | | Dùng cho nhiều cụm | mỗi cụm một trust | một role nhiều cụm | | Hỗ trợ | mọi phiên bản EKS | EKS 1.24+ |

Đề nói rõ "must use IRSA" nên đáp án là IRSA
    → nhưng với thiết kế mới, Pod Identity ít việc hơn

Từ khoá nhận diện:

"fine-grained IAM for Kubernetes service accounts" → IRSA hoặc Pod Identity "ECS task needs AWS permissions" → task role (taskRoleArn) "EC2 needs AWS permissions" → instance profile "restrict pod capabilities (root, hostPath)" → Pod Security Standards

Ba thành phần của IRSA: | Thành phần | Việc | |---|---| | OIDC identity provider | IAM tin cụm EKS | | Trust policy có điều kiện :sub | giới hạn service account nào | | Annotation eks.amazonaws.com/role-arn | pod dùng role nào |

⚠ Ba lỗi hay gặp với IRSA: | Lỗi | Nguyên nhân | |---|---| | AccessDenied dù đã annotate | quên tạo OIDC provider | | Pod vẫn dùng node role | thiếu serviceAccountName trong pod spec | | Điều kiện :sub sai namespace | |

Pod phải khai service account:

spec:
  serviceAccountName: sa-huan-luyen     # ← thiếu dòng này là dùng "default"
  containers:
    - name: huan-luyen
      image: ...

Kiểm tra pod đang dùng danh tính nào:

kubectl exec -it <pod> -- env | grep AWS_ROLE_ARN
kubectl exec -it <pod> -- aws sts get-caller-identity
Hai lệnh này cho biết ngay IRSA có hoạt động không

Ba lưu ý về đặc quyền tối thiểu: | Lưu ý | Chi tiết | |---|---| | Mỗi tải một service account riêng | | | Giới hạn Resource tới đúng ARN | | | Thêm điều kiện nếu được | |

Ba lưu ý về node role khi dùng IRSA: | Lưu ý | Chi tiết | |---|---| | Node role vẫn cần quyền cơ bản | ECR, CNI, CloudWatch | | Nhưng KHÔNG nên có quyền ứng dụng | | | Chặn pod truy cập IMDS của node | |

⚠ Chặn IMDS là bước bảo mật quan trọng:

aws ec2 modify-instance-metadata-options --instance-id i-abc \
  --http-put-response-hop-limit 1 --http-tokens required
Không chặn: pod gọi được IMDS
    → lấy được credential của NODE ROLE
    → IRSA trở nên vô nghĩa

Ba dịch vụ ML thường dùng với IRSA: | Dịch vụ | Quyền | |---|---| | Amazon S3 | đọc dữ liệu huấn luyện | | Amazon ECR | kéo ảnh | | SageMaker | gọi endpoint |

Ba việc kiểm chứng: | Việc | Cách | |---|---| | aws sts get-caller-identity trong pod | | | Thử gọi API được phép | | | Thử từ pod khác — phải bị từ chối | |

Và một lời khuyên: hãy chặn pod truy cập IMDS của node cùng lúc với việc bật IRSA. Nếu không, mọi công sức phân quyền chi tiết sẽ bị vô hiệu bởi một lệnh curl tới 169.254.169.254 — pod vẫn lấy được credential của node role và dùng toàn bộ quyền của nó.

Câu 972 AWS Database

An online store uses an Amazon Aurora database. The database is deployed as a Multi-AZ deployment. Recently, metrics have shown that database read requests are high and causing performance issues which result in latency for write requests.

What should the solutions architect do to separate the read requests from the write requests?

  1. A

    Enable read through caching on the Amazon Aurora database

  2. B

    Create a read replica and modify the application to use the appropriate endpoint

  3. C

    Update the application to read from the Aurora Replica

  4. D

    Create a second Amazon Aurora database and link it to the primary database as a read replica

Xem giải thích

Đáp án

C — Cập nhật ứng dụng để đọc từ Aurora Replica.

Vì sao đúng

Đề có một chi tiết quyết định mà rất nhiều người bỏ qua: | Dữ kiện | Ý nghĩa | |---|---| | **Aurora triển khai dạng Multi-AZ | ĐÃ CÓ SẴN một Aurora Replica | | Tải đọc cao làm chậm cả ghi | cần tách hai loại tải | | Cần tách đọc khỏi ghi | chỉ cần trỏ đọc vào replica đã có |

⚠ Aurora Multi-AZ khác RDS Multi-AZ ở đúng điểm này: | | RDS Multi-AZ | Aurora Multi-AZ | |---|---|---| | Máy ở AZ thứ hai là gì | standby — KHÔNG phục vụ đọc | Aurora Replica — ĐỌC ĐƯỢC | | Muốn phân tán đọc | phải tạo read replica riêng | dùng ngay replica đã có |

Aurora Multi-AZ = cụm có ít nhất một Aurora Replica ở AZ khác
    → replica đó đang chạy, đang đồng bộ, và ĐỌC ĐƯỢC
        ↓
    Không cần tạo thêm gì
    → chỉ cần ứng dụng biết dùng nó

Đây chính là lý do C đúng còn B thừa một bước.

Cách làm:

Ứng dụng hiện dùng CLUSTER ENDPOINT cho mọi truy vấn
    → cluster endpoint luôn trỏ tới instance GHI
        ↓
    Đổi phần đọc sang READER ENDPOINT
    → nó tự cân bằng qua mọi Aurora Replica

Hai endpoint cần phân biệt:

Ghi:  cum.cluster-abc123.ap-southeast-1.rds.amazonaws.com
Đọc:  cum.cluster-ro-abc123.ap-southeast-1.rds.amazonaws.com
                    ↑
              chú ý "-ro-"

Trong ứng dụng:

ket_noi_ghi = psycopg2.connect(host=ENDPOINT_GHI, ...)
ket_noi_doc = psycopg2.connect(host=ENDPOINT_DOC, ...)

def lay_don_hang(ma):
    with ket_noi_doc.cursor() as cur:      # đọc → replica
        cur.execute("SELECT * FROM don_hang WHERE ma = %s", (ma,))

def tao_don_hang(du_lieu):
    with ket_noi_ghi.cursor() as cur:      # ghi → writer
        cur.execute("INSERT INTO don_hang ...")

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Không tốn thêm tiền | replica đã tồn tại và đang tính phí | | Không phải chờ tạo replica | | | Instance ghi được giải phóng ngay | |

Và nếu cần thêm sức đọc:

aws rds create-db-instance --db-instance-identifier replica-2 \
  --db-cluster-identifier cum-cua-hang \
  --db-instance-class db.r6g.xlarge --engine aurora-mysql \
  --promotion-tier 15
Aurora Replica mới TỰ vào reader endpoint
    → ứng dụng không cần đổi gì nữa

Vì sao các phương án khác sai

  • **B. Tạo một read replica và sửa ứng dụng dùng endpoint phù hợp — đây là phương án gần nhất và hoàn toàn chạy được, nhưng nó thừa một bước: cụm Multi-AZ đã có sẵn Aurora Replica. Tạo thêm nghĩa là trả tiền cho một instance nữa mà chưa cần.
  • **D. Tạo một CSDL Aurora thứ hai rồi liên kết làm read replica — hiểu sai kiến trúc Aurora: replica là một instance trong cùng cụm, chia sẻ cùng tầng lưu trữ, không phải một CSDL riêng biệt được "liên kết".
  • **A. Bật read-through caching trên Aurora — không có tính năng này. Muốn cache thì dùng ElastiCache đặt trước CSDL, hoặc Aurora có buffer pool nội bộ nhưng không phải thứ bật/tắt được.

Ghi nhớ

⚠ Bốn loại endpoint của Aurora — bảng phải thuộc: | Endpoint | Trỏ tới | |---|---| | Cluster (writer) | instance GHI hiện tại | | Reader | cân bằng qua MỌI Aurora Replica | | Custom | nhóm instance tự chọn | | Instance | một instance cụ thể |

Từ khoá nhận diện:

"Aurora Multi-AZ" + "separate reads" → dùng reader endpoint (replica đã có) "RDS Multi-AZ" + "separate reads" → phải TẠO read replica | "same query repeated" → ElastiCache "specific replicas for reporting" → custom endpoint

⚠ Aurora Replica và RDS Read Replica — bảng phân biệt: | | Aurora Replica | RDS Read Replica | |---|---|---| | Cơ chế | chia sẻ tầng lưu trữ | sao chép qua binlog | | Độ trễ | < 100 ms | giây | | Dung lượng thêm | không | nhân đôi | | Số lượng tối đa | 15 | 5 | | Failover | tự động | thủ công (promote) |

⚠ Vế "standby không phục vụ đọc" chỉ đúng với RDS:

RDS Multi-AZ:  standby nằm chờ, KHÔNG đọc được
Aurora:        mọi replica đều đọc được VÀ là đích failover
        ↓
    Đây là hiểu nhầm phổ biến nhất khi chuyển từ RDS sang Aurora

Ba đặc điểm của reader endpoint: | Đặc điểm | Chi tiết | |---|---| | Cân bằng qua DNS round-robin | | | Chỉ gồm replica, không gồm writer | | | Replica mới TỰ vào | |

⚠ Cân bằng qua DNS có hạn chế thật:

Cân bằng xảy ra lúc PHÂN GIẢI DNS, không phải mỗi truy vấn
    → connection pool giữ kết nối lâu
    → mọi truy vấn dồn vào một replica
        ↓
    Cách chữa: đặt TTL ngắn, dùng RDS Proxy,
    hoặc mở lại kết nối định kỳ

Ba lưu ý về replica lag: | Lưu ý | Chi tiết | |---|---| | Aurora lag thường < 100 ms | rất thấp | | Nhưng KHÔNG bằng 0 | | | Đọc-sau-ghi có thể thấy dữ liệu cũ | |

Vế thứ ba là chỗ hay gây lỗi nghiệp vụ:

Người dùng tạo đơn hàng (ghi vào writer)
    → ngay lập tức xem lại (đọc từ replica)
    → chưa thấy đơn hàng
        ↓
    Với thao tác cần đọc-sau-ghi ngay: đọc từ writer
    → hoặc dùng session pinning

Ba lưu ý về promotion tier: | Tier | Ý nghĩa | |---|---| | 0 | được chọn làm writer trước tiên | | 1-15 | ưu tiên giảm dần | | — | cùng tier thì chọn máy lớn nhất |

Custom endpoint cho tải riêng biệt:

aws rds create-db-cluster-endpoint --db-cluster-identifier cum-cua-hang \
  --db-cluster-endpoint-identifier bao-cao --endpoint-type READER \
  --static-members replica-bao-cao

Ba cách giảm tải đọc: | Cách | Khi nào | |---|---| | Reader endpoint | tách đọc khỏi ghi ← câu này | | ElastiCache | cùng dữ liệu đọc lại nhiều | | Aurora Serverless v2 làm replica | tải đọc biến động |

Ba metric cần theo dõi: | Metric | Ý nghĩa | |---|---| | AuroraReplicaLag | độ trễ dữ liệu | | DatabaseConnections theo instance | có cân bằng không | | SelectLatency | |

Ba lưu ý về RDS Proxy: | Lưu ý | Chi tiết | |---|---| | Gộp kết nối, giảm áp lực | | | Có endpoint chỉ đọc riêng | | | Rút ngắn thời gian failover | |

Và một lời khuyên: hãy kiểm tra số kết nối trên từng instance sau khi đổi sang reader endpoint. Nếu một replica nhận gần hết kết nối còn replica kia gần như rảnh, đó là dấu hiệu connection pool đang giữ kết quả phân giải DNS cũ — và bạn vừa tách được tải đọc nhưng chưa phân tán được nó.

Câu 973 AWS Security, Identity, & Compliance

A Solutions Architect created the following policy and associated to an AWS IAM group containing several administrative users:

{

   "Version": "2012-10-17",

    "Statement": [

    {

            "Effect": "Allow",

            "Action": "ec2:TerminateInstances",

            "Resource": "*",

            "Condition": {

                     "IpAddress": {

                          "aws:SourceIp": "10.1.2.0/24"

                   }

             }

    },

   {

                    "Effect": "Deny",

                    "Action": "ec2:*",

                     "Resource": "*",

                     "Condition": {

                           "StringNotEquals": {

                                       "ec2:Region": "us-east-1"

                            }

                      }

                 }

           ]

   }

What is the effect of this policy?

  1. A

    Administrators cannot terminate an EC2 instance in the us-east-1 Region when the user's source IP is 10.1.2.28.

  2. B

    Administrators can terminate an EC2 instance in any AWS Region except us-east-1.

  3. C

    Administrators can terminate an EC2 instance with the IP address 10.1.2.5 in the us-east-1 Region.

  4. D

    Administrators can terminate an EC2 instance in the us-east-1 Region when the user's source IP is 10.1.2.28.

Xem giải thích

Đáp án

D — Quản trị viên CÓ THỂ chấm dứt một EC2 instance ở vùng us-east-1 khi IP nguồn của người dùng là 10.1.2.28.

Vì sao đúng

Chính sách có hai câu lệnh, và phải đánh giá cả hai: | Câu | Effect | Điều kiện | |---|---|---| | 1 | Allow ec2:TerminateInstances | aws:SourceIp thuộc 10.1.2.0/24 | | 2 | Deny ec2:* | ec2:Region KHÁC us-east-1 |

Đánh giá cho tình huống của phương án D:

Hành động:  ec2:TerminateInstances
Vùng:       us-east-1
IP nguồn:   10.1.2.28
        ↓
Câu 1: IP 10.1.2.28 CÓ thuộc 10.1.2.0/24 → Allow ÁP DỤNG ✅
Câu 2: Region LÀ us-east-1 → StringNotEquals KHÔNG khớp
       → Deny KHÔNG áp dụng ✅
        ↓
    Kết quả: ĐƯỢC PHÉP

⚠ Quy tắc đánh giá IAM — thứ tự bắt buộc nhớ:

1. Mặc định: TỪ CHỐI
2. Có Allow tường minh nào khớp không?  → nếu không, từ chối
3. Có Deny tường minh nào khớp không?   → nếu có, TỪ CHỐI
        ↓
    Deny tường minh LUÔN THẮNG Allow

Kiểm tra 10.1.2.28 có thuộc 10.1.2.0/24 không:

10.1.2.0/24 → 24 bit đầu cố định
    → dải từ 10.1.2.0 tới 10.1.2.255
        ↓
    10.1.2.28 nằm trong dải → khớp

Bảng đánh giá đầy đủ các tình huống: | Vùng | IP nguồn | Câu 1 (Allow) | Câu 2 (Deny) | Kết quả | |---|---|---|---|---| | us-east-1 | 10.1.2.28 | khớp | không khớp | CHO PHÉP | | us-east-1 | 192.168.1.5 | không khớp | không khớp | từ chối (không có Allow) | | eu-west-1 | 10.1.2.28 | khớp | khớp → Deny | TỪ CHỐI | | eu-west-1 | 192.168.1.5 | không khớp | khớp | từ chối |

⚠ Và một chi tiết quan trọng về aws:SourceIp:

aws:SourceIp là IP của NGƯỜI GỌI API
    → không phải IP của instance bị chấm dứt
        ↓
    Đây là lý do phương án C sai

Vì sao các phương án khác sai

  • **A. Quản trị viên KHÔNG THỂ chấm dứt instance ở us-east-1 khi IP nguồn là 10.1.2.28 — đây là phương án gần nhất và mô tả đúng tình huống nhưng kết luận ngược: cả hai điều kiện đều thuận lợi, nên thao tác được phép.
  • **B. Quản trị viên có thể chấm dứt instance ở mọi vùng TRỪ us-east-1 — ngược hoàn toàn: câu Deny từ chối mọi hành động EC2 ở vùng khác us-east-1, nên us-east-1 là vùng duy nhất được phép.
  • **C. Quản trị viên có thể chấm dứt instance có địa chỉ IP 10.1.2.5 ở us-east-1 — nhầm ý nghĩa của aws:SourceIp: khoá này chỉ IP của người gọi API, không phải IP của tài nguyên bị tác động.

Ghi nhớ

⚠ Quy tắc đánh giá IAM — phải thuộc:

1. Mặc định TỪ CHỐI 2. Allow tường minh → cho phép 3. Deny tường minh → TỪ CHỐI (thắng mọi Allow)

Công thức quyền hiệu lực đầy đủ:

Quyền thật = SCP ∩ Permissions Boundary ∩ Identity Policy
             ∩ (Resource Policy) ∩ (Session Policy)
        ↓
    Deny ở BẤT KỲ tầng nào cũng thắng

⚠ Ba khoá điều kiện về mạng — bảng phải thuộc: | Khoá | Nghĩa | |---|---| | aws:SourceIp | IP CÔNG KHAI của người gọi API | | aws:SourceVpc | VPC mà request đi qua | | aws:SourceVpce | VPC endpoint cụ thể |

⚠ Bẫy lớn nhất với aws:SourceIp:

Request đi qua VPC ENDPOINT
    → aws:SourceIp KHÔNG còn là IP của bạn
    → chính sách dựa trên SourceIp sẽ TỪ CHỐI
        ↓
    Với request qua endpoint, dùng aws:SourceVpce hoặc aws:SourceVpc

Ba toán tử điều kiện hay gặp: | Toán tử | Việc | |---|---| | IpAddress / NotIpAddress | so IP với CIDR | | StringEquals / StringNotEquals | so chuỗi chính xác | | StringLike | có ký tự đại diện * | | Bool, Null, DateGreaterThan | |

⚠ Mẫu "chặn mọi vùng trừ vài vùng" rất phổ biến:

{"Effect": "Deny", "Action": "*", "Resource": "*",
 "Condition": {"StringNotEquals": {
   "aws:RequestedRegion": ["us-east-1", "ap-southeast-1"]}}}

⚠ Phân biệt ec2:Region và aws:RequestedRegion: | Khoá | Phạm vi | |---|---| | aws:RequestedRegion | khoá TOÀN CỤC — áp cho mọi dịch vụ | | ec2:Region | khoá riêng của EC2 |

Muốn chặn theo vùng cho TOÀN BỘ dịch vụ
    → dùng aws:RequestedRegion
        ↓
    ec2:Region chỉ áp cho hành động EC2

Ba khoá toàn cục hay dùng: | Khoá | Việc | |---|---| | aws:PrincipalOrgID | chỉ tài khoản trong tổ chức | | aws:MultiFactorAuthPresent | bắt buộc MFA | | aws:SecureTransport | bắt buộc HTTPS |

Bắt buộc MFA cho thao tác nguy hiểm:

{"Effect": "Deny", "Action": "ec2:TerminateInstances", "Resource": "*",
 "Condition": {"BoolIfExists": {"aws:MultiFactorAuthPresent": "false"}}}

⚠ Dùng BoolIfExists chứ không phải Bool:

Bool: nếu khoá KHÔNG tồn tại (ví dụ gọi từ role của dịch vụ)
      → điều kiện không khớp → Deny không áp dụng
        ↓
BoolIfExists: coi khoá thiếu là false → Deny vẫn áp dụng

Ba công cụ phân tích chính sách: | Công cụ | Việc | |---|---| | IAM Policy Simulator | thử một hành động cụ thể | | IAM Access Analyzer | tìm truy cập ngoài ý muốn | | CloudTrail | xem lệnh bị từ chối thật |

aws iam simulate-principal-policy \
  --policy-source-arn arn:aws:iam::123456789012:user/quantri \
  --action-names ec2:TerminateInstances \
  --resource-arns "*" \
  --context-entries \
    ContextKeyName=aws:SourceIp,ContextKeyValues=10.1.2.28,ContextKeyType=ip

Ba lưu ý khi viết chính sách có điều kiện IP: | Lưu ý | Chi tiết | |---|---| | VPC endpoint làm SourceIp thay đổi | | | NAT Gateway đổi IP nguồn | | | Người dùng dùng VPN có IP khác | |

Ba lưu ý về Deny theo vùng: | Lưu ý | Chi tiết | |---|---| | Một số dịch vụ là TOÀN CẦU | IAM, CloudFront, Route 53 | | Chúng "chạy ở" us-east-1 | | | Loại trừ chúng khỏi Deny | |

{"Effect": "Deny", "NotAction": ["iam:*","cloudfront:*","route53:*","support:*"],
 "Resource": "*",
 "Condition": {"StringNotEquals": {"aws:RequestedRegion": ["us-east-1"]}}}
Không loại trừ: chặn luôn cả việc quản lý IAM
    → có thể tự khoá mình ra ngoài

Và một lời khuyên: hãy dùng IAM Policy Simulator với --context-entries để kiểm chứng chính sách có điều kiện, đừng đọc bằng mắt. Một chính sách hai câu lệnh đã đủ để bốn tình huống cho ra bốn kết quả khác nhau — và điều kiện là chỗ mà trực giác sai thường xuyên nhất.

Câu 974 AWS Compute

An application runs on a fleet of Amazon EC2 instances in an Amazon EC2 Auto Scaling group behind an Elastic Load Balancer. The operations team has determined that the application performs best when the CPU utilization of the EC2 instances is at or near 60%.

Which scaling configuration should a Solutions Architect use to optimize the applications performance?

  1. A

    Use a target tracking policy to dynamically scale the Auto Scaling group.

  2. B

    Use a scheduled scaling policy to dynamically the Auto Scaling group.

  3. C

    Use a simple scaling policy to dynamically scale the Auto Scaling group.

  4. D

    Use a step scaling policy to dynamically scale the Auto Scaling group.

Xem giải thích

Đáp án

A — Dùng target tracking policy để co giãn Auto Scaling group.

Vì sao đúng

Đề nêu một dữ kiện rất cụ thể, và target tracking sinh ra đúng cho nó: | Dữ kiện | Cách đáp ứng | |---|---| | **Ứng dụng chạy tốt nhất khi CPU ở mức GẦN 60% | đặt TargetValue = 60 | | Cần tối ưu hiệu năng | AWS tự giữ metric quanh mục tiêu |

Vì sao "at or near 60%" là gợi ý trực tiếp:

Target tracking hoạt động như một bộ điều nhiệt:
    → bạn khai một CON SỐ MỤC TIÊU
    → AWS tự tính cần thêm hoặc bớt bao nhiêu máy
        ↓
    Đề đã cho sẵn con số mục tiêu → dùng đúng kiểu chính sách đó

Cấu hình:

aws autoscaling put-scaling-policy \
  --auto-scaling-group-name asg-ung-dung \
  --policy-name giu-cpu-60 --policy-type TargetTrackingScaling \
  --target-tracking-configuration '{
    "TargetValue": 60.0,
    "PredefinedMetricSpecification": {
      "PredefinedMetricType": "ASGAverageCPUUtilization"},
    "ScaleInCooldown": 300,
    "ScaleOutCooldown": 60}'

Ba việc AWS tự lo: | Việc | Chi tiết | |---|---| | Tự tạo HAI CloudWatch alarm | một để thêm, một để bớt | | Tự tính số máy cần thay đổi | theo mức lệch khỏi mục tiêu | | Scale out nhanh, scale in chậm | tránh dao động |

Vế thứ ba đáng nhấn mạnh:

Target tracking cố ý BẤT ĐỐI XỨNG:
    → thêm máy nhanh (bảo vệ trải nghiệm)
    → bớt máy chậm và thận trọng
        ↓
    Đây là hành vi mong muốn cho hầu hết ứng dụng

So sánh với step scaling: | | Target tracking | Step scaling | |---|---|---| | Cấu hình | một con số mục tiêu | nhiều bậc ngưỡng | | Tự tính lượng thay đổi | ✅ | ❌ phải khai từng bậc | | Tự tạo alarm | ✅ | phải tự tạo | | Kiểm soát chi tiết | ít hơn | nhiều hơn |

Vì sao các phương án khác sai

  • **D. Dùng step scaling policy — đây là phương án gần nhất và cũng co giãn theo CPU được, nhưng nó bắt bạn tự định nghĩa từng bậc ("CPU 60-70% thêm 1 máy, 70-85% thêm 2 máy..."). Với một mục tiêu duy nhất đã cho sẵn thì target tracking đơn giản và chính xác hơn.
  • **C. Dùng simple scaling policy — kiểu cũ nhất: mỗi lần kích hoạt chỉ thực hiện một hành động rồi chờ hết cooldown mới đánh giá lại. Phản ứng chậm, và AWS không còn khuyến nghị.
  • **B. Dùng scheduled scaling policy — co giãn theo thời gian, phù hợp khi tải lặp lại theo lịch biết trước. Đề không nói gì về mẫu thời gian; nó nói về một mức CPU mục tiêu.

Ghi nhớ

⚠ Bốn kiểu chính sách co giãn — bảng phải thuộc: | Kiểu | Kích hoạt bởi | Khi nào | |---|---|---| | Target tracking | giữ metric ở mục tiêu | mặc định nên dùng | | Step scaling | ngưỡng theo bậc | cần kiểm soát chi tiết | | Simple scaling | một hành động + cooldown | kiểu cũ | | Scheduled | thời gian | tải biết trước | | Predictive | học máy từ lịch sử | tải có chu kỳ |

Từ khoá nhận diện:

"maintain CPU at X%", "performs best at" → target tracking "every day at 9am" → scheduled "different actions for different breach sizes" → step scaling "scale based on queue depth" → target tracking với custom metric

Ba metric dựng sẵn cho target tracking: | Metric | Dùng khi | |---|---| | ASGAverageCPUUtilization | tải nặng CPU ← câu này | | ALBRequestCountPerTarget | phản ứng nhanh hơn CPU | | ASGAverageNetworkIn/Out | tải nặng mạng |

⚠ Request-per-target thường tốt hơn CPU:

CPU là chỉ báo TRỄ — lên tới ngưỡng thì người dùng đã chờ
Số request tăng NGAY khi lưu lượng tăng
        ↓
    Với ứng dụng web, request-per-target phản ứng sớm hơn

Custom metric cho target tracking:

aws autoscaling put-scaling-policy --auto-scaling-group-name asg-xu-ly \
  --policy-name theo-hang-doi --policy-type TargetTrackingScaling \
  --target-tracking-configuration '{
    "TargetValue": 100.0,
    "CustomizedMetricSpecification": {
      "MetricName": "BacklogPerInstance",
      "Namespace": "UngDung",
      "Statistic": "Average"}}'

Ba tham số quan trọng: | Tham số | Lưu ý | |---|---| | TargetValue | mức muốn giữ | | ScaleOutCooldown | ngắn — phản ứng nhanh | | ScaleInCooldown | dài hơn — tránh bớt sớm | | DisableScaleIn | chỉ thêm, không bớt |

⚠ DisableScaleIn hữu ích khi kết hợp nhiều chính sách:

Một chính sách theo CPU, một theo request count
    → cả hai cùng bớt máy có thể bớt quá tay
        ↓
    Tắt scale-in ở một chính sách, để chính sách kia lo

Ba lưu ý về thời gian phản ứng: | Lưu ý | Chi tiết | |---|---| | Metric có độ trễ 1-5 phút | bật detailed monitoring cho 1 phút | | health-check-grace-period đủ cho khởi động | | | AMI có sẵn ứng dụng | không cài lúc khởi động |

⚠ Detailed monitoring giúp co giãn nhanh hơn:

Basic monitoring: metric mỗi 5 phút
    → alarm phải chờ điểm dữ liệu
        ↓
Detailed monitoring: mỗi 1 phút
    → phản ứng nhanh gấp 5 lần

Ba tham số dung lượng: | Tham số | Lưu ý | |---|---| | min-size | đủ chịu tải nền và dự phòng AZ | | max-size | trần chi phí | | desired-capacity | co giãn thay đổi con số này |

Ba lưu ý về health check: | Lưu ý | Chi tiết | |---|---| | Đặt --health-check-type ELB | không dùng EC2 | | Kiểu EC2 chỉ xem máy có chạy không | | | Ứng dụng treo mà máy "running" thì ASG không thay | |

Ba cách giảm chi phí: | Cách | Chi tiết | |---|---| | Mixed instance policy với Spot | | | Savings Plans cho tải nền | | | Right-size bằng Compute Optimizer | |

Ba metric theo dõi sau khi cấu hình: | Metric | Ý nghĩa | |---|---| | GroupInServiceInstances | ASG có phản ứng không | | CPUUtilization trung bình | có bám mục tiêu không | | TargetResponseTime của ALB | trải nghiệm thật |

Ba việc kiểm chứng: | Việc | Cách | |---|---| | Thử tải và xem CPU có hội tụ về 60% không | | | Xem lịch sử hoạt động của ASG | | | Kiểm tra không có dao động lên xuống liên tục | |

aws autoscaling describe-scaling-activities \
  --auto-scaling-group-name asg-ung-dung --max-items 20 \
  --query "Activities[].[StartTime,Description,StatusCode]" --output table

Và một lời khuyên: hãy để ScaleInCooldown dài hơn ScaleOutCooldown một cách rõ rệt. Thêm máy sớm chỉ tốn thêm chút tiền, còn bớt máy sớm rồi phải thêm lại ngay là vòng dao động làm cả hiệu năng lẫn hoá đơn đều tệ hơn.

Câu 975 AWS Application Integration

A company is deploying an application that produces data that must be processed in the order it is received. The company requires a solution for decoupling the event data from the processing layer. The solution must minimize operational overhead.

How can a Solutions Architect meet these requirements?

  1. A

    Create an Amazon SNS topic to decouple the application. Configure an AWS Lambda function as a subscriber.

  2. B

    Create an Amazon SNS topic to decouple the application. Configure an Amazon SQS queue as a subscriber.

  3. C

    Create an Amazon SQS FIFO queue to decouple the application. Configure an AWS Lambda function to process messages from the queue.

  4. D

    Create an Amazon SQS standard queue to decouple the application. Set up an AWS Lambda function to process messages from the queue independently.

Xem giải thích

Đáp án

C — Tạo một Amazon SQS FIFO queue để tách rời ứng dụng, và cấu hình một AWS Lambda function xử lý thông điệp từ hàng đợi.

Vì sao đúng

Đề nêu ba yêu cầu, và FIFO queue + Lambda là lựa chọn duy nhất thoả hết: | Yêu cầu | Cách đáp ứng | |---|---| | **Dữ liệu phải xử lý ĐÚNG THỨ TỰ NHẬN ĐƯỢC | FIFO queue đảm bảo thứ tự | | Tách rời tầng sự kiện khỏi tầng xử lý | hàng đợi ở giữa | | Tối thiểu công vận hành | SQS + Lambda đều serverless |

Vế đầu là ràng buộc quyết định:

"must be processed in the ORDER IT IS RECEIVED"
    → SQS Standard KHÔNG đảm bảo thứ tự
    → SNS cũng không
        ↓
    Chỉ SQS FIFO (hoặc Kinesis theo partition key)
    đảm bảo thứ tự

Tạo FIFO queue:

aws sqs create-queue --queue-name su-kien.fifo --attributes '{
  "FifoQueue":"true",
  "ContentBasedDeduplication":"true",
  "VisibilityTimeout":"300",
  "MessageRetentionPeriod":"1209600"}'

⚠ Tên hàng đợi FIFO BẮT BUỘC kết thúc bằng .fifo.

Nối Lambda vào hàng đợi:

aws lambda create-event-source-mapping \
  --function-name xu-ly-su-kien \
  --event-source-arn arn:aws:sqs:ap-southeast-1:123456789012:su-kien.fifo \
  --batch-size 10

⚠ Hai thuộc tính quyết định hành vi FIFO: | Thuộc tính | Việc | |---|---| | MessageGroupId | thứ tự được đảm bảo TRONG một group | | MessageDeduplicationId | chống trùng trong 5 phút |

sqs.send_message(
    QueueUrl=URL,
    MessageBody=json.dumps(su_kien),
    MessageGroupId=su_kien['ma_thiet_bi'],       # thứ tự theo thiết bị
    MessageDeduplicationId=su_kien['ma_su_kien'])

⚠ MessageGroupId là khái niệm quan trọng nhất của FIFO:

Thứ tự chỉ đảm bảo TRONG cùng một message group
    → group khác nhau xử lý SONG SONG được
        ↓
    Một group duy nhất  → thứ tự tuyệt đối nhưng KHÔNG song song
    Nhiều group          → song song và vẫn giữ thứ tự trong mỗi group

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Thứ tự được đảm bảo | | | Giao ĐÚNG MỘT LẦN | không trùng như Standard | | Không có máy chủ nào | |

Vì sao các phương án khác sai

  • **D. Tạo SQS STANDARD queue và Lambda xử lý — đây là phương án gần nhất và chỉ khác một từ, nhưng Standard queue không đảm bảo thứ tự (chỉ "cố gắng" giữ) và có thể giao trùng. Đề nêu rõ yêu cầu thứ tự.
  • **B. Dùng SNS topic với SQS queue làm subscriber — thêm một tầng không cần thiết, và SNS không đảm bảo thứ tự khi chuyển tiếp (trừ FIFO topic ghép với FIFO queue, nhưng phương án không nói vậy).
  • **A. Dùng SNS topic với Lambda làm subscriber — SNS là mô hình đẩy, không lưu trữ: nếu Lambda bị giới hạn hoặc lỗi, thông điệp có thể mất. Và không có đảm bảo thứ tự.

Ghi nhớ

⚠ SQS Standard và FIFO — bảng phải thuộc: | | Standard | FIFO | |---|---|---| | Thứ tự | cố gắng, KHÔNG đảm bảo | đảm bảo trong message group | | Giao | ít nhất một lần (có thể TRÙNG) | đúng một lần | | Thông lượng | không giới hạn | 300 TPS (3.000 khi gộp lô) | | Tên hàng đợi | bất kỳ | phải kết thúc .fifo |

Từ khoá nhận diện:

"in the order received", "exactly once", "no duplicates" → SQS FIFO "maximum throughput", "order doesn't matter" → SQS Standard "multiple consumers read same data", "replay" → Kinesis "fan-out to many subscribers" → SNS

⚠ Kinesis cũng đảm bảo thứ tự — khi nào chọn cái nào: | | SQS FIFO | Kinesis Data Streams | |---|---|---| | Thứ tự theo | message group | partition key (trong shard) | | Sau khi xử lý | thông điệp bị XOÁ | dữ liệu VẪN CÒN | | Nhiều consumer độc lập | ❌ | ✅ | | Quản lý | không có | shard (hoặc on-demand) |

Chỉ một bên xử lý, xử lý xong là xong → SQS FIFO
Nhiều bên đọc cùng dữ liệu, cần đọc lại → Kinesis

Ba đặc điểm về thông lượng FIFO: | Chế độ | Thông lượng | |---|---| | Mặc định | 300 thông điệp/giây | | Gộp lô (10 thông điệp mỗi lần gọi) | 3.000/giây | | High throughput mode | tới 70.000/giây (theo vùng) |

Bật high throughput:

aws sqs set-queue-attributes --queue-url $URL --attributes '{
  "FifoThroughputLimit":"perMessageGroupId",
  "DeduplicationScope":"messageGroup"}'
Chuyển giới hạn từ "cả hàng đợi" sang "mỗi message group"
    → nhiều group = thông lượng cao hơn nhiều

Hai cách chống trùng: | Cách | Chi tiết | |---|---| | ContentBasedDeduplication | băm SHA-256 nội dung thông điệp | | MessageDeduplicationId tường minh | bạn tự đặt |

⚠ Cửa sổ chống trùng là 5 PHÚT:

Gửi cùng một MessageDeduplicationId hai lần trong 5 phút
    → lần thứ hai bị BỎ QUA (không lỗi, không cảnh báo)
        ↓
    Với dữ liệu hợp lệ giống hệt nhau, phải đặt id khác nhau

Ba lưu ý về Lambda đọc FIFO queue: | Lưu ý | Chi tiết | |---|---| | Mỗi message group xử lý TUẦN TỰ | | | Số group quyết định độ song song | | | Lỗi một thông điệp chặn cả group đó | |

Vế thứ ba là bẫy vận hành:

Một thông điệp gây lỗi trong group A
    → mọi thông điệp sau nó trong group A bị chặn
    → group B, C vẫn chạy bình thường
        ↓
    Cấu hình DLQ với maxReceiveCount hợp lý
    → thông điệp lỗi được tách ra, group chạy tiếp

Dead-letter queue cho FIFO:

aws sqs create-queue --queue-name su-kien-loi.fifo \
  --attributes '{"FifoQueue":"true"}'

aws sqs set-queue-attributes --queue-url $URL --attributes '{
  "RedrivePolicy":"{\"deadLetterTargetArn\":\"<arn-dlq>\",\"maxReceiveCount\":\"3\"}"}'
DLQ của FIFO queue cũng PHẢI là FIFO queue

Ba tham số quan trọng: | Tham số | Mặc định | Lưu ý | |---|---|---| | Visibility timeout | 30 giây | ≥ thời gian xử lý | | Message retention | 4 ngày | tối đa 14 ngày | | WaitTimeSeconds | 0 | đặt 20 — long polling |

Ba metric cần theo dõi: | Metric | Ý nghĩa | |---|---| | ApproximateNumberOfMessagesVisible | tồn đọng | | ApproximateAgeOfOldestMessage | có group nào bị kẹt không | | Số thông điệp trong DLQ | |

Ba lưu ý về chi phí: | Khoản | Chi tiết | |---|---| | FIFO đắt hơn Standard một chút | | | Long polling giảm phí request | | | Gộp lô 10 thông điệp mỗi lần | |

Và một lời khuyên: hãy chọn MessageGroupId sao cho có nhiều group nhất mà vẫn giữ đúng thứ tự nghiệp vụ. Dùng một group duy nhất cho toàn hệ thống là cách chắc chắn nhất để có thứ tự tuyệt đối — và cũng là cách chắc chắn nhất để thông lượng đứng yên ở 300 thông điệp mỗi giây.

Câu 976 AWS Migration & Transfer

A logistics company needs to replicate ongoing data changes from an on-premises Microsoft SQL Server database to Amazon RDS for SQL Server. The volume of data to replicate varies throughout the day due to periodic spikes in activity. The company plans to use AWS Database Migration Service (AWS DMS) for this task. The solution must dynamically allocate capacity based on workload demand while keeping operational overhead low.

Which solution will meet these requirements?

  1. A

    Configure AWS DMS Serverless to create a replication task that scales its capacity automatically based on workload demand.

  2. B

    Use Amazon EC2 Spot Instances to host the AWS DMS replication instance and manually scale up or down based on replication needs.

  3. C

    Create an AWS DMS replication instance with provisioned capacity in a Multi-AZ deployment to improve availability and fault tolerance.

  4. D

    Deploy AWS DMS in an Amazon Elastic Kubernetes Service (Amazon EKS) cluster and use an autoscaler to adjust compute capacity during data spikes.

Xem giải thích

Đáp án

A — Cấu hình AWS DMS Serverless tạo một replication task tự co giãn năng lực theo nhu cầu.

Vì sao đúng

Đề nêu ba yêu cầu, và DMS Serverless được thiết kế chính xác cho việc này: | Yêu cầu | Cách đáp ứng | |---|---| | Sao chép thay đổi liên tục từ SQL Server tại chỗ sang RDS | DMS với CDC | | Khối lượng BIẾN ĐỘNG, có đợt tăng đột biến | Serverless tự co giãn | | Ít công vận hành nhất | không chọn cỡ replication instance |

Vì sao DMS Serverless khác DMS truyền thống:

DMS thường:  phải chọn replication instance class trước
    → chọn nhỏ → nghẽn lúc cao điểm
    → chọn to → trả tiền cho năng lực không dùng
        ↓
DMS Serverless: khai một dải DCU (min - max)
    → tự co giãn trong dải đó theo tải thật

Tạo replication serverless:

aws dms create-replication-config \
  --replication-config-identifier sao-chep-sql-server \
  --source-endpoint-arn <arn-nguon> \
  --target-endpoint-arn <arn-dich> \
  --replication-type cdc \
  --table-mappings file://anh-xa-bang.json \
  --compute-config '{
    "MinCapacityUnits": 2,
    "MaxCapacityUnits": 16,
    "MultiAZ": true,
    "ReplicationSubnetGroupId": "nhom-subnet-dms",
    "VpcSecurityGroupIds": ["sg-dms"]}'

⚠ DCU (DMS Capacity Unit) là đơn vị co giãn:

1 DCU ≈ 2 GB RAM và CPU tương ứng
    → tăng giảm tự động trong dải min-max
        ↓
    Đợt tăng đột biến → DMS tự lên
    Ban đêm ít thay đổi → tự xuống min

Ba loại migration type: | Loại | Việc | |---|---| | full-load | chép toàn bộ một lần | | cdc | chỉ sao chép thay đổi liên tục ← đề cần | | full-load-and-cdc | chép hết rồi theo dõi thay đổi |

⚠ CDC với SQL Server cần bật ở nguồn:

-- Bật CDC hoặc MS-REPLICATION trên CSDL nguồn
EXEC sys.sp_cdc_enable_db;
EXEC sys.sp_cdc_enable_table
  @source_schema = N'dbo', @source_name = N'don_hang',
  @role_name = NULL, @supports_net_changes = 1;
Không bật CDC ở nguồn
    → DMS không đọc được thay đổi
    → task chạy nhưng không sao chép gì

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Không chọn cỡ instance | | | Tự co giãn theo tải thật | | | Trả tiền theo DCU-giờ thực dùng | |

Vì sao các phương án khác sai

  • **C. Tạo DMS replication instance với năng lực cấp phát ở chế độ Multi-AZ — đây là phương án gần nhất và là cách làm chuẩn trước khi có Serverless, nhưng nó không tự co giãn: bạn phải chọn instance class cố định và tự thay đổi khi tải đổi. Đề đòi "dynamically allocate capacity" và "low operational overhead".
  • **B. Chạy DMS trên EC2 Spot và co giãn thủ công — DMS là dịch vụ được quản lý, bạn không tự host nó trên EC2. Và Spot bị thu hồi sẽ làm đứt luồng sao chép.
  • **D. Triển khai DMS trong cụm EKS với autoscaler — cùng lý do: DMS không phải phần mềm bạn tự triển khai vào container.

Ghi nhớ

⚠ Hai chế độ của AWS DMS — bảng phải thuộc: | Chế độ | Đặc điểm | |---|---| | DMS Serverless | tự co giãn theo DCU, không chọn instance | | DMS provisioned | chọn replication instance class cố định |

Từ khoá nhận diện:

"varying workload", "dynamically allocate capacity", "low overhead" → DMS Serverless "migrate database with schema conversion" → DMS + SCT "same engine, minimal downtime" → DMS với CDC "NoSQL to DynamoDB, huge data" → SCT + Snowball Edge

Ba thành phần của một migration DMS: | Thành phần | Việc | |---|---| | Source endpoint | CSDL nguồn | | Target endpoint | CSDL đích | | Replication task / config | ánh xạ bảng và loại migration |

⚠ Ba loại migration type — phải thuộc: | Loại | Khi nào | |---|---| | full-load | chuyển một lần, chấp nhận ngừng | | cdc | nguồn đã đồng bộ, chỉ theo dõi thay đổi | | full-load-and-cdc | chuyển với thời gian ngừng tối thiểu |

Mẫu di chuyển với thời gian ngừng tối thiểu:

1. full-load-and-cdc bắt đầu
2. DMS chép toàn bộ dữ liệu hiện có
3. Rồi tự chuyển sang theo dõi thay đổi
4. Khi độ trễ ≈ 0 → chuyển ứng dụng sang đích
5. Dừng task

Ba metric cần theo dõi: | Metric | Ý nghĩa | |---|---| | CDCLatencySource | độ trễ đọc từ nguồn | | CDCLatencyTarget | độ trễ ghi vào đích | | CDCChangesMemorySource | thay đổi đang giữ trong bộ nhớ |

⚠ Hai metric độ trễ chỉ ra hai vấn đề khác nhau:

CDCLatencySource cao → nguồn sinh thay đổi nhanh hơn DMS đọc
    → tăng năng lực, hoặc kiểm tra transaction log của nguồn

CDCLatencyTarget cao → đích ghi chậm
    → kiểm tra IOPS, index, hoặc tăng cỡ instance đích

Ba lưu ý về SQL Server làm nguồn: | Lưu ý | Chi tiết | |---|---| | Phải bật CDC hoặc MS-REPLICATION | | | Cần quyền sysadmin hoặc tương đương | | | Transaction log phải giữ đủ lâu | |

⚠ Transaction log là chỗ hay gãy:

Log bị truncate trước khi DMS đọc kịp
    → mất thay đổi, task lỗi
        ↓
    Đặt chính sách backup log phù hợp
    → hoặc dùng sp_repldone cẩn thận

Ba lưu ý về table mapping: | Lưu ý | Chi tiết | |---|---| | Chọn schema và bảng cần sao chép | | | Có thể đổi tên, lọc dòng | | | Transformation rule đổi tên cột | |

{"rules": [{
  "rule-type": "selection", "rule-id": "1", "rule-name": "chon-bang",
  "object-locator": {"schema-name": "dbo", "table-name": "%"},
  "rule-action": "include"}]}

Ba lưu ý về mạng: | Lưu ý | Chi tiết | |---|---| | DMS cần tới được cả nguồn và đích | | | Qua VPN hoặc Direct Connect với nguồn tại chỗ | | | Replication subnet group ở ít nhất 2 AZ | |

⚠ SCT và DMS — phân biệt: | | Schema Conversion Tool (SCT) | DMS | |---|---|---| | Việc | chuyển đổi SCHEMA và mã | chuyển DỮ LIỆU | | Khi nào cần SCT | đổi engine (Oracle→PostgreSQL) | | | Cùng engine | không cần SCT | |

SQL Server → RDS for SQL Server = CÙNG engine
    → không cần chuyển đổi schema
    → chỉ cần DMS

Ba lưu ý về chi phí: | Khoản | Chi tiết | |---|---| | Serverless tính theo DCU-giờ | | | Provisioned tính theo instance-giờ | | | Đặt MaxCapacityUnits làm trần chi phí | |

Ba lưu ý về xác thực dữ liệu: | Lưu ý | Chi tiết | |---|---| | Bật EnableValidation trong task settings | | | DMS so sánh dữ liệu nguồn và đích | | | Báo cáo dòng không khớp | |

{"ValidationSettings": {"EnableValidation": true,
  "ValidationMode": "ROW_LEVEL", "ThreadCount": 5}}

Và một lời khuyên: hãy bật validation và theo dõi hai metric độ trễ ngay từ ngày đầu. Sao chép liên tục thất bại theo cách rất im lặng — task vẫn ở trạng thái "Running", chỉ có độ trễ tăng dần, và bạn sẽ phát hiện ra khi ai đó hỏi vì sao báo cáo trên AWS thiếu dữ liệu của tuần trước.

Câu 977 AWS Compute

A company has deployed an application that consists of several microservices running on Amazon EC2 instances behind an Amazon API Gateway API. A Solutions Architect is concerned that the microservices are not designed to elastically scale when large increases in demand occur.

Which solution addresses this concern?

  1. A

    Create an Amazon SQS queue to store incoming requests. Configure the microservices to retrieve the requests from the queue for processing.

  2. B

    Spread the microservices across multiple Availability Zones and configure Amazon Data Lifecycle Manager to take regular snapshots.

  3. C

    Use an Elastic Load Balancer to distribute the traffic between the microservices. Configure Amazon CloudWatch metrics to monitor traffic to the microservices.

  4. D

    Use Amazon CloudWatch alarms to notify operations staff when the microservices are suffering high CPU utilization.

Xem giải thích

Đáp án

A — Tạo một Amazon SQS queue để lưu request đến, và cấu hình các microservice lấy request từ hàng đợi để xử lý.

Vì sao đúng

Đề nêu một lo ngại cụ thể, và hàng đợi giải quyết đúng nguyên nhân gốc: | Dữ kiện | Vấn đề | |---|---| | Microservice trên EC2 sau API Gateway | | | KHÔNG được thiết kế để co giãn đàn hồi | không kịp phản ứng khi tải tăng | | Lo ngại khi nhu cầu tăng mạnh | request bị từ chối hoặc timeout |

Vì sao hàng đợi là lời giải:

Không có hàng đợi:
    API Gateway → microservice (đồng bộ)
    → tải tăng vượt năng lực → request thất bại
        ↓
Có hàng đợi:
    API Gateway → SQS (nhận ngay, lưu bền)
                → microservice lấy khi xử lý được
        ↓
    Hàng đợi HẤP THỤ đợt tăng
    → không request nào bị mất

Đây là mẫu "load levelling" — san bằng tải:

Tải đến:  ▁▁▇▇▇▇▁▁  (đột biến)
Hàng đợi: đệm phần đỉnh
Tải xử lý: ▃▃▃▃▃▃▃▃  (đều)
        ↓
    Microservice không cần co giãn tức thì nữa

API Gateway tích hợp thẳng với SQS:

aws apigateway put-integration --rest-api-id abc123 \
  --resource-id xyz789 --http-method POST --type AWS \
  --integration-http-method POST \
  --uri arn:aws:apigateway:ap-southeast-1:sqs:path/123456789012/hang-doi-request \
  --credentials arn:aws:iam::123456789012:role/VaiTroApiGatewaySQS \
  --request-parameters '{"integration.request.header.Content-Type":
    "'"'"'application/x-www-form-urlencoded'"'"'"}' \
  --request-templates '{"application/json":"Action=SendMessage&MessageBody=$input.body"}'
Không cần Lambda ở giữa
    → API Gateway đẩy thẳng vào SQS

Và microservice co giãn theo độ dài hàng đợi:

aws autoscaling put-scaling-policy \
  --auto-scaling-group-name asg-microservice \
  --policy-name theo-hang-doi --policy-type TargetTrackingScaling \
  --target-tracking-configuration '{"TargetValue":100.0,
    "CustomizedMetricSpecification":{
      "MetricName":"ApproximateNumberOfMessagesVisible",
      "Namespace":"AWS/SQS",
      "Dimensions":[{"Name":"QueueName","Value":"hang-doi-request"}],
      "Statistic":"Average"}}'

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Không mất request khi tải tăng | | | Microservice xử lý theo nhịp của nó | | | Có cơ sở đo lường để co giãn | độ dài hàng đợi |

Vì sao các phương án khác sai

  • **C. Dùng Elastic Load Balancer phân phối lưu lượng và CloudWatch giám sát — đây là phương án gần nhất và cải thiện phân phối tải, nhưng nó không giải quyết vấn đề năng lực: ELB chia đều request cho các máy hiện có, nhưng nếu tổng năng lực không đủ thì request vẫn thất bại. Giám sát chỉ cho biết, không sửa.
  • **D. Dùng CloudWatch alarm báo cho đội vận hành khi CPU cao — chỉ là cảnh báo: cần con người can thiệp, và tới lúc đó đợt tăng đã gây lỗi rồi.
  • **B. Trải microservice qua nhiều AZ và dùng Data Lifecycle Manager chụp snapshot — đa AZ cải thiện tính sẵn sàng, không phải khả năng co giãn. Và snapshot EBS hoàn toàn không liên quan.

Ghi nhớ

⚠ Ba dịch vụ tách rời — bảng phải thuộc: | Dịch vụ | Mô hình | Đệm tải | |---|---|---| | Amazon SQS | hàng đợi, KÉO | ✅ | | Amazon SNS | pub/sub, ĐẨY | ❌ | | Kinesis Data Streams | luồng, nhiều consumer | ✅ |

Từ khoá nhận diện:

"not designed to scale elastically", "spikes in demand" → SQS đệm tải "multiple systems need the same event" → SNS fan-out "process in order" → SQS FIFO "replay events" → Kinesis

⚠ Ba mẫu kiến trúc dùng hàng đợi: | Mẫu | Việc | |---|---| | Queue-based load levelling | san bằng đợt tăng ← câu này | | Competing consumers | nhiều worker cùng lấy việc | | Priority queue | hàng đợi riêng cho việc gấp |

Ba tham số quan trọng của SQS: | Tham số | Mặc định | Lưu ý | |---|---|---| | Visibility timeout | 30 giây | ≥ thời gian xử lý | | Message retention | 4 ngày | tối đa 14 ngày | | WaitTimeSeconds | 0 | đặt 20 — long polling |

Long polling giảm chi phí đáng kể:

Short polling: gọi liên tục, phần lớn trả rỗng
    → trả tiền cho hàng triệu request vô ích
Long polling (20 giây): giữ kết nối chờ
    → ít request hơn nhiều, độ trễ cũng thấp hơn

⚠ Dead-letter queue là bắt buộc:

aws sqs set-queue-attributes --queue-url $URL --attributes '{
  "RedrivePolicy":"{\"deadLetterTargetArn\":\"<arn-dlq>\",\"maxReceiveCount\":\"5\"}"}'
Không có DLQ: thông điệp lỗi quay vòng mãi
    → chiếm chỗ, làm metric co giãn sai
    → ASG thêm máy để xử lý một việc không xử lý được

Ba metric cần theo dõi: | Metric | Ý nghĩa | |---|---| | ApproximateNumberOfMessagesVisible | tồn đọng — dùng co giãn | | ApproximateAgeOfOldestMessage | thời gian chờ thật của khách | | Số thông điệp trong DLQ | có lỗi hệ thống |

Metric thứ hai đáng đặt alarm nhất — nó cho biết người dùng đang phải chờ bao lâu.

⚠ Đánh đổi khi chuyển sang bất đồng bộ: | Trước | Sau | |---|---| | Client chờ kết quả ngay | client nhận "đã nhận" rồi hỏi lại sau | | Lỗi báo ngay | lỗi phát hiện muộn hơn | | Đơn giản | phải thiết kế cách trả kết quả |

Ba cách trả kết quả cho client: | Cách | Chi tiết | |---|---| | Polling một endpoint trạng thái | đơn giản nhất | | WebSocket API của API Gateway | đẩy khi xong | | Webhook gọi lại client | |

Ba lưu ý về idempotent: | Lưu ý | Chi tiết | |---|---| | Standard queue giao ÍT NHẤT MỘT LẦN | | | Consumer phải chịu được xử lý lại | | | Dùng khoá nghiệp vụ chống ghi trùng | |

Ba cách co giãn microservice: | Cách | Chi tiết | |---|---| | ASG theo độ dài hàng đợi | ← câu này | | ECS Service Auto Scaling | nếu chạy container | | Lambda đọc trực tiếp SQS | serverless hoàn toàn |

Công thức tính mục tiêu backlog:

Mục tiêu = (thông lượng mỗi máy) × (thời gian chờ chấp nhận được)

Ví dụ: 20 thông điệp/phút mỗi máy, chấp nhận chờ 5 phút
    → mục tiêu backlog mỗi instance = 100

Ba lưu ý về scale in: | Lưu ý | Chi tiết | |---|---| | ScaleInCooldown dài hơn scale out | | | Lifecycle hook để xử lý nốt việc | | | Ứng dụng xử lý SIGTERM | |

Và một lời khuyên: hãy đặt alarm trên ApproximateAgeOfOldestMessage chứ không chỉ trên độ dài hàng đợi. Hàng đợi hấp thụ được đợt tăng, nhưng nếu tầng xử lý chậm hơn tốc độ nhận thì hàng đợi chỉ đang biến một sự cố tức thì thành một sự cố kéo dài — và tuổi của thông điệp cũ nhất là con số duy nhất cho bạn biết điều đó.

Câu 978 AWS Networking & Content Delivery

A media company is building a video content distribution platform on AWS. The platform uses an REST API hosted on Amazon API Gateway to serve metadata about the videos, such as titles and descriptions. The metadata is confidential and must be accessible only from a specific set of trusted IP addresses belonging to the company’s office network.

Which solution will meet these requirements?

  1. A

    Configure an API Gateway resource policy that denies access to any IP address that is not explicitly allowed.

  2. B

    Modify the API Gateway security group to allow inbound requests only from the trusted IP addresses.

  3. C

    Set up API Gateway with a private integration and restrict access to the trusted IP addresses using a VPC endpoint policy.

  4. D

    Deploy the API Gateway in a private subnet and configure a network ACL to permit traffic only from the trusted IP addresses.

Xem giải thích

Đáp án

A — Cấu hình một API Gateway resource policy từ chối truy cập từ mọi địa chỉ IP không nằm trong danh sách cho phép.

Vì sao đúng

Đề nêu hai yêu cầu, và resource policy là cơ chế đúng: | Yêu cầu | Cách đáp ứng | |---|---| | API metadata chạy trên API Gateway | | | Chỉ truy cập được từ một dải IP văn phòng | resource policy với điều kiện aws:SourceIp |

Vì sao phải là resource policy:

API Gateway là dịch vụ ĐƯỢC QUẢN LÝ, KHÔNG nằm trong VPC của bạn
    → không có security group
    → không có network ACL
    → không đặt vào subnet được
        ↓
    Cách duy nhất lọc theo IP là resource policy

Đây là lý do loại cả B, C và D.

Resource policy:

{"Version": "2012-10-17",
 "Statement": [
   {"Effect": "Allow",
    "Principal": "*",
    "Action": "execute-api:Invoke",
    "Resource": "arn:aws:execute-api:ap-southeast-1:123456789012:abc123/*"},
   {"Effect": "Deny",
    "Principal": "*",
    "Action": "execute-api:Invoke",
    "Resource": "arn:aws:execute-api:ap-southeast-1:123456789012:abc123/*",
    "Condition": {"NotIpAddress": {
      "aws:SourceIp": ["203.0.113.0/24", "198.51.100.0/24"]}}}]}

⚠ Cấu trúc hai câu lệnh là bắt buộc:

Câu 1 (Allow):  mở cho tất cả
Câu 2 (Deny):   từ chối nếu IP KHÔNG thuộc danh sách
        ↓
    Chỉ có Deny mà không có Allow
    → không ai gọi được (mặc định là từ chối)

Áp policy:

aws apigateway update-rest-api --rest-api-id abc123 \
  --patch-operations op=replace,path=/policy,value="$(cat policy.json)"

aws apigateway create-deployment --rest-api-id abc123 --stage-name prod

⚠ Phải TRIỂN KHAI LẠI sau khi đổi resource policy:

Sửa policy mà không create-deployment
    → thay đổi KHÔNG có hiệu lực
        ↓
    Đây là lỗi hay gặp: policy nhìn đúng nhưng không áp dụng

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Chặn ngay ở tầng API Gateway | request không tới backend | | Không tốn phí xử lý cho request bị chặn | | | Kết hợp được với authorizer | hai lớp |

Vì sao các phương án khác sai

  • **C. Dùng private integration và giới hạn IP bằng VPC endpoint policy — đây là phương án gần nhất vì cũng nói về giới hạn truy cập, nhưng nó nhầm hai khái niệm: private integration là cách API Gateway gọi backend trong VPC, không liên quan tới ai gọi được API. Còn private API (loại endpoint) thì chỉ truy cập được từ trong VPC — mà văn phòng ở bên ngoài.
  • **B. Sửa security group của API Gateway — API Gateway KHÔNG có security group. Nó là dịch vụ được quản lý nằm ngoài VPC của bạn.
  • **D. Triển khai API Gateway trong subnet riêng tư và dùng network ACL — cùng lý do: API Gateway không đặt vào subnet được.

Ghi nhớ

⚠ Ba loại endpoint của API Gateway — bảng phải thuộc: | Loại | Truy cập từ | |---|---| | Edge-optimized | Internet, qua edge của CloudFront | | Regional | Internet, thẳng tới vùng | | Private | CHỈ từ trong VPC qua interface endpoint |

Đề nói văn phòng truy cập qua Internet
    → không dùng private endpoint được
    → phải lọc bằng resource policy

⚠ Bốn cách kiểm soát truy cập API Gateway: | Cách | Kiểm soát theo | |---|---| | Resource policy | IP, VPC, VPC endpoint, tài khoản AWS | | IAM authorization | danh tính AWS (SigV4) | | Cognito authorizer | người dùng ứng dụng | | Lambda authorizer | logic tuỳ chỉnh (JWT, OAuth) | | API key + usage plan | giới hạn tần suất, KHÔNG phải bảo mật |

⚠ API key KHÔNG phải cơ chế xác thực:

AWS nói rõ: API key dùng để ĐO LƯỜNG và GIỚI HẠN TẦN SUẤT
    → không dùng làm cơ chế bảo mật duy nhất
        ↓
    Luôn kết hợp với authorizer hoặc resource policy

Từ khoá nhận diện:

"restrict API to specific IP addresses" → resource policy "only accessible from within VPC" → private API endpoint "authenticate app users" → Cognito authorizer "backend is in a private subnet" → private integration (VPC Link)

⚠ Private integration và Private endpoint — hai thứ khác nhau: | | Private integration | Private API endpoint | |---|---|---| | Nói về | API Gateway gọi BACKEND thế nào | AI gọi được API | | Cơ chế | VPC Link tới NLB/ALB | interface endpoint | | Hướng | API Gateway → VPC | VPC → API Gateway |

Ba khoá điều kiện dùng trong resource policy: | Khoá | Nghĩa | |---|---| | aws:SourceIp | IP công khai của người gọi | | aws:SourceVpc | VPC nếu gọi qua endpoint | | aws:SourceVpce | VPC endpoint cụ thể |

⚠ Bẫy lớn với aws:SourceIp:

Request đi qua VPC endpoint
    → aws:SourceIp KHÔNG còn là IP thật của bạn
    → chính sách dựa trên SourceIp sẽ TỪ CHỐI
        ↓
    Với private API, dùng aws:SourceVpce

Ba lưu ý khi viết resource policy: | Lưu ý | Chi tiết | |---|---| | Phải có CẢ Allow lẫn Deny | | | Dùng NotIpAddress cho danh sách cho phép | | | Triển khai lại sau khi sửa | |

Ba lưu ý về ARN trong resource policy:

arn:aws:execute-api:<vùng>:<tài-khoản>:<api-id>/<stage>/<method>/<path>
                                                  ↓
    Dùng "*" để áp cho mọi stage và method
    Hoặc chỉ định cụ thể: abc123/prod/GET/metadata

Ba lớp bảo vệ nên kết hợp: | Lớp | Việc | |---|---| | Resource policy | lọc IP ← câu này | | Authorizer | xác thực danh tính | | AWS WAF | chặn tấn công, giới hạn tần suất |

Gắn WAF vào API Gateway:

aws wafv2 associate-web-acl \
  --web-acl-arn <arn-web-acl> \
  --resource-arn arn:aws:apigateway:ap-southeast-1::/restapis/abc123/stages/prod
WAF cũng lọc được IP, và có IP set tới 10.000 địa chỉ
    → hợp hơn resource policy khi danh sách IP dài

Ba lưu ý về throttling: | Lưu ý | Chi tiết | |---|---| | Đặt giới hạn ở stage level | | | Usage plan cho từng API key | | | Bảo vệ backend khỏi quá tải | |

Ba lưu ý về log và giám sát: | Lưu ý | Chi tiết | |---|---| | Bật execution log và access log | | | Theo dõi metric 4XXError | | | CloudTrail ghi thay đổi cấu hình | |

Ba việc kiểm chứng: | Việc | Cách | |---|---| | Gọi API từ IP văn phòng | phải thành công | | Gọi từ IP khác | phải nhận 403 | | Kiểm tra đã triển khai lại chưa | |

curl -i https://abc123.execute-api.ap-southeast-1.amazonaws.com/prod/metadata

Và một lời khuyên: hãy nhớ triển khai lại (create-deployment) sau mỗi lần sửa resource policy. Đây là kiểu lỗi tệ nhất trong nhóm này — console hiển thị policy mới, không có thông báo lỗi nào, và API vẫn chấp nhận request từ mọi nơi cho tới khi bạn chạy thêm một lệnh nữa.

Câu 979 Chọn nhiều đáp án AWS Compute

A gaming company recently launched a multiplayer gaming platform for its users. The platform runs on multiple Amazon EC2 instances across two Availability Zones. Players use TCP to communicate with the platform in real time. The platform must be highly available and automatically scale as the number of players increases, while remaining cost-effective.

Which combination of steps will meet these requirements MOST cost-effectively? (Select TWO.)

  1. A

    Add a Network Load Balancer in front of the EC2 instances to manage TCP traffic.

  2. B

    Use an Application Load Balancer to distribute TCP traffic to the EC2 instances.

  3. C

    Configure Amazon Route 53 to implement latency-based routing across multiple EC2 instances.

  4. D

    Configure an Auto Scaling group to add or remove EC2 instances based on player traffic.

  5. E

    Deploy an Amazon ECS cluster to replace the EC2 instances and handle player traffic.

Xem giải thích

Đáp án

A và D.

  • A — Đặt một Network Load Balancer trước các EC2 instance để xử lý lưu lượng TCP
  • D — Cấu hình một Auto Scaling group thêm bớt EC2 theo lượng người chơi

Vì sao đúng

Đề nêu bốn yêu cầu, và hai hành động này giải quyết từng cặp: | Yêu cầu | Hành động | |---|---| | Người chơi dùng TCP thời gian thực | A: NLB — tầng 4 | | Phải có tính sẵn sàng cao | A + D: LB đa AZ + ASG đa AZ | | Tự co giãn khi số người chơi tăng | D: Auto Scaling group | | Tiết kiệm chi phí | D: bớt máy khi ít người chơi |

⚠ Vì sao NLB chứ không phải ALB:

Người chơi giao tiếp bằng TCP thời gian thực
    → không phải HTTP
        ↓
    ALB hoạt động ở TẦNG 7 — chỉ hiểu HTTP/HTTPS
    NLB hoạt động ở TẦNG 4 — xử lý TCP, UDP, TLS

Đây là lý do loại phương án B.

Và NLB còn hợp với game ở ba điểm: | Đặc điểm | Chi tiết | |---|---| | Độ trễ rất thấp | xử lý ở tầng 4 | | Giữ IP nguồn của client | với target kiểu instance | | Gán được Elastic IP tĩnh mỗi AZ | |

Cấu hình:

aws elbv2 create-load-balancer --name nlb-game --type network \
  --scheme internet-facing --subnets subnet-a subnet-b

aws autoscaling create-auto-scaling-group \
  --auto-scaling-group-name asg-game \
  --launch-template LaunchTemplateName=mau-game,Version='$Latest' \
  --min-size 2 --max-size 20 --desired-capacity 4 \
  --vpc-zone-identifier "subnet-a,subnet-b" \
  --target-group-arns <arn-tg> --health-check-type ELB

Co giãn theo số kết nối:

aws autoscaling put-scaling-policy --auto-scaling-group-name asg-game \
  --policy-name theo-ket-noi --policy-type TargetTrackingScaling \
  --target-tracking-configuration '{"TargetValue":500.0,
    "CustomizedMetricSpecification":{
      "MetricName":"ActiveFlowCount","Namespace":"AWS/NetworkELB",
      "Dimensions":[{"Name":"LoadBalancer","Value":"net/nlb-game/abc"}],
      "Statistic":"Average"}}'

Ba lợi ích về chi phí: | Lợi ích | Chi tiết | |---|---| | Chỉ trả cho số máy đang cần | | | Ban đêm ít người chơi → ít máy | | | Không nhân bản hạ tầng ra nhiều vùng | |

Vì sao các phương án khác sai

  • **B. Dùng Application Load Balancer phân phối lưu lượng TCP — đây là phương án gần nhất và rất dễ chọn nhầm, nhưng ALB hoạt động ở tầng 7 và chỉ xử lý HTTP/HTTPS/gRPC. Nó không phân phối được lưu lượng TCP thuần.
  • **C. Dùng Route 53 latency-based routing giữa nhiều EC2 — định tuyến DNS không cân bằng tải thật sự: nó không biết máy nào đang bận, không kiểm tra sức khoẻ theo từng kết nối, và client cache DNS làm phân bố lệch.
  • **E. Thay EC2 bằng cụm Amazon ECS — có thể là hướng hiện đại hoá tốt, nhưng đề không yêu cầu đổi nền tảng, và bản thân ECS không giải quyết hai vấn đề nêu ra (cân bằng TCP và co giãn) — vẫn cần load balancer và cơ chế co giãn.

Ghi nhớ

⚠ Ba loại Elastic Load Balancer — bảng phải thuộc: | Loại | Tầng | Giao thức | |---|---|---| | Application Load Balancer | 7 | HTTP, HTTPS, gRPC | | Network Load Balancer | 4 | TCP, UDP, TLS | | Gateway Load Balancer | 3/4 | thiết bị bảo mật (GENEVE) |

Từ khoá nhận diện:

"TCP", "UDP", "real-time gaming", "low latency" → NLB "HTTP routing by path/host" → ALB "static IP address" → NLB (Elastic IP) "multi-Region + static IP" → Global Accelerator

⚠ Ba khác biệt quan trọng giữa ALB và NLB: | | ALB | NLB | |---|---|---| | IP nguồn thấy ở target | IP của ALB (client IP ở X-Forwarded-For) | IP THẬT của client | | Cross-zone mặc định | BẬT, miễn phí | TẮT, có phí khi bật | | Elastic IP tĩnh | ❌ | ✅ | | Độ trễ | cao hơn | thấp hơn |

⚠ Cross-zone tắt mặc định ở NLB gây phân bố lệch:

Mỗi node NLB chỉ gửi tới target trong CÙNG AZ
    → AZ có ít target hơn → mỗi máy nhận tải nặng hơn
        ↓
    Giữ số target cân bằng giữa các AZ
    → hoặc bật cross-zone và chấp nhận phí truyền

Ba metric của NLB dùng để co giãn: | Metric | Ý nghĩa | |---|---| | ActiveFlowCount | số kết nối đang mở | | NewFlowCount | kết nối mới mỗi giây | | ProcessedBytes | lưu lượng |

⚠ Với game, ActiveFlowCount phản ánh số người chơi tốt hơn CPU.

Ba lưu ý về health check của NLB: | Lưu ý | Chi tiết | |---|---| | Kiểm tra bằng TCP hoặc HTTP | | | KHÔNG kiểm tra bằng UDP | | | Đặt --health-check-type ELB cho ASG | |

Ba lưu ý về trạng thái phiên game: | Lưu ý | Chi tiết | |---|---| | Game thường giữ trạng thái trong bộ nhớ | | | Bật sticky session (NLB dùng source IP) | | | Hoặc lưu trạng thái ở ElastiCache | |

Bật sticky session cho NLB:

aws elbv2 modify-target-group-attributes --target-group-arn <arn> \
  --attributes Key=stickiness.enabled,Value=true \
               Key=stickiness.type,Value=source_ip

Ba cách giảm chi phí thêm: | Cách | Chi tiết | |---|---| | Mixed instance policy với Spot | game session ngắn thì chịu được | | Savings Plans cho tải nền | | | Right-size loại instance | |

⚠ Spot cho máy chủ game — cân nhắc kỹ:

Spot bị thu hồi với 2 phút báo trước
    → người chơi đang trong trận bị ngắt
        ↓
    Dùng Spot cho phần TĂNG THÊM, giữ On-Demand làm nền
    → và có cơ chế chuyển người chơi sang máy khác

Ba lưu ý về scale in với game: | Lưu ý | Chi tiết | |---|---| | Lifecycle hook để chờ trận kết thúc | | | Instance protection cho máy đang có trận | | | Deregistration delay đủ dài | |

Instance protection:

aws autoscaling set-instance-protection \
  --instance-ids i-abc --auto-scaling-group-name asg-game \
  --protected-from-scale-in
Đánh dấu máy đang có trận là được bảo vệ
    → ASG không chọn nó để tắt
    → gỡ bảo vệ khi trận kết thúc

Ba lựa chọn chuyên biệt cho game: | Lựa chọn | Việc | |---|---| | Amazon GameLift | dịch vụ chuyên cho máy chủ game | | Global Accelerator | nhiều vùng, IP tĩnh, UDP | | NLB + ASG | ← câu này |

Ba việc kiểm chứng: | Việc | Cách | |---|---| | Thử tải để xem ASG có co giãn không | | | Tắt hết máy một AZ, xem còn phục vụ không | | | Đo độ trễ phía người chơi | |

Và một lời khuyên: hãy dùng instance protection hoặc lifecycle hook trước khi bật scale-in cho máy chủ game. Auto Scaling không biết máy nào đang có trận đấu dở — và việc bớt một máy vào lúc tải giảm sẽ ngắt giữa chừng đúng những người chơi vẫn đang chơi.

Câu 980 AWS Application Integration

A web app allows users to upload images for viewing online. The compute layer that processes the images is behind an Auto Scaling group. The processing layer should be decoupled from the front end and the ASG needs to dynamically adjust based on the number of images being uploaded.

How can this be achieved?

  1. A

    Create an Amazon SNS Topic to generate a notification each time a message is uploaded. Have the ASG scale based on the number of SNS messages

  2. B

    Create a target tracking policy that keeps the ASG at 70% CPU utilization

  3. C

    Create a scheduled policy that scales the ASG at times of expected peak load

  4. D

    Create an Amazon SQS queue and custom CloudWatch metric to measure the number of messages in the queue. Configure the ASG to scale based on the number of messages in the queue

Xem giải thích

Đáp án

D — Tạo một Amazon SQS queue và một custom CloudWatch metric đo số thông điệp trong hàng đợi, rồi cấu hình ASG co giãn theo con số đó.

Vì sao đúng

Đề nêu hai yêu cầu, và cả hai được giải quyết bằng cùng một cơ chế: | Yêu cầu | Cách đáp ứng | |---|---| | Tách rời tầng xử lý khỏi tầng giao diện | hàng đợi ở giữa | | **ASG co giãn theo SỐ ẢNH ĐANG CHỜ | metric độ dài hàng đợi |

Vì sao độ dài hàng đợi là metric đúng:

Đề nói rõ: co giãn theo "số ảnh đang được tải lên"
    → đó chính là số thông điệp chờ trong hàng đợi
        ↓
    CPU chỉ nói "máy đang bận"
    → không nói còn bao nhiêu việc chưa làm

Luồng:

Người dùng tải ảnh
    ▼
Giao diện lưu ảnh vào S3, đẩy thông điệp vào SQS
    ▼
SQS (đệm)
    ▼
ASG các máy xử lý ảnh — lấy thông điệp và xử lý
        ↓
    Số thông điệp trong hàng đợi = lượng việc còn lại

Cách làm chuẩn — metric "backlog per instance":

Backlog mỗi instance = số thông điệp / số máy đang chạy
        ↓
    Đây mới là con số nên đặt làm mục tiêu
    → vì nó độc lập với quy mô hiện tại

Đẩy custom metric:

import boto3
sqs = boto3.client('sqs'); asg = boto3.client('autoscaling')
cw = boto3.client('cloudwatch')

so_tin = int(sqs.get_queue_attributes(QueueUrl=URL,
    AttributeNames=['ApproximateNumberOfMessages'])
    ['Attributes']['ApproximateNumberOfMessages'])
so_may = len([i for i in asg.describe_auto_scaling_groups(
    AutoScalingGroupNames=['asg-xu-ly-anh'])['AutoScalingGroups'][0]['Instances']
    if i['LifecycleState'] == 'InService'])

cw.put_metric_data(Namespace='UngDung/XuLyAnh', MetricData=[{
    'MetricName': 'BacklogPerInstance',
    'Value': so_tin / max(so_may, 1)}])

Chính sách co giãn:

aws autoscaling put-scaling-policy \
  --auto-scaling-group-name asg-xu-ly-anh \
  --policy-name theo-hang-doi --policy-type TargetTrackingScaling \
  --target-tracking-configuration '{
    "TargetValue": 20.0,
    "CustomizedMetricSpecification": {
      "MetricName": "BacklogPerInstance",
      "Namespace": "UngDung/XuLyAnh",
      "Statistic": "Average"}}'

Ba lợi ích: | Lợi ích | Chi tiết | |---|---| | Phản ứng với lượng việc thật | không phải triệu chứng | | Hàng đợi đệm khi tải tăng đột ngột | | | Ảnh không bị mất khi máy xử lý bận | |

Công thức tính mục tiêu:

Mục tiêu = (số ảnh một máy xử lý mỗi phút) × (thời gian chờ chấp nhận được)

Ví dụ: 10 ảnh/phút mỗi máy, chấp nhận chờ 2 phút
    → mục tiêu backlog mỗi instance = 20

Vì sao các phương án khác sai

  • **B. Tạo target tracking policy giữ CPU ở 70% — đây là phương án gần nhất và là chính sách co giãn hợp lệ, nhưng nó không tách rời gì cả: đề yêu cầu tách tầng xử lý khỏi giao diện, mà một chính sách co giãn không tạo ra sự tách rời. Và CPU không phản ánh số ảnh đang chờ.
  • **C. Tạo scheduled policy co giãn vào giờ cao điểm dự kiến — lượng ảnh người dùng tải lên không đoán trước được, nên co giãn theo lịch sẽ vừa thừa lúc vắng vừa thiếu lúc đông.
  • **A. Dùng SNS topic và co giãn theo số thông điệp SNS — SNS là mô hình đẩy, không lưu trữ: không có "số thông điệp đang chờ" để đo, và nếu tầng xử lý bận thì thông điệp mất.

Ghi nhớ

⚠ SQS và SNS — bảng phải thuộc: | | Amazon SQS | Amazon SNS | |---|---|---| | Mô hình | hàng đợi, KÉO | pub/sub, ĐẨY | | Lưu trữ | tới 14 ngày | không lưu | | Đo được tồn đọng | ✅ | ❌ | | Đệm tải | ✅ | ❌ |

Từ khoá nhận diện:

"scale based on number of items waiting" → SQS + metric độ dài hàng đợi "decouple front end from processing" → SQS "notify multiple systems" → SNS "predictable daily pattern" → scheduled scaling

Ba metric SQS quan trọng: | Metric | Ý nghĩa | |---|---| | ApproximateNumberOfMessagesVisible | đang chờ xử lý | | ApproximateNumberOfMessagesNotVisible | đang được xử lý | | ApproximateAgeOfOldestMessage | có bị kẹt không |

⚠ Vì sao dùng "backlog per instance" thay vì số thông điệp thô:

Đặt mục tiêu "500 thông điệp trong hàng đợi"
    → với 2 máy: mỗi máy gánh 250 → quá tải
    → với 50 máy: mỗi máy gánh 10 → thừa máy
        ↓
    Chia cho số máy làm con số độc lập với quy mô

Bốn kiểu chính sách co giãn: | Kiểu | Kích hoạt bởi | |---|---| | Target tracking | giữ metric ở mục tiêu | | Step scaling | ngưỡng theo bậc | | Simple scaling | kiểu cũ | | Scheduled | thời gian |

Ba tham số quan trọng của SQS: | Tham số | Mặc định | Lưu ý | |---|---|---| | Visibility timeout | 30 giây | ≥ thời gian xử lý ảnh | | Message retention | 4 ngày | tối đa 14 ngày | | WaitTimeSeconds | 0 | đặt 20 — long polling |

⚠ Visibility timeout với xử lý ảnh:

Xử lý một ảnh lớn mất 5 phút, visibility timeout 30 giây
    → sau 30 giây thông điệp hiện lại
    → máy KHÁC cũng xử lý cùng ảnh đó
        ↓
    Đặt visibility timeout ≥ thời gian xử lý dài nhất

Gia hạn động khi cần:

sqs.change_message_visibility(
    QueueUrl=URL, ReceiptHandle=rh, VisibilityTimeout=600)

⚠ Dead-letter queue là bắt buộc:

aws sqs set-queue-attributes --queue-url $URL --attributes '{
  "RedrivePolicy":"{\"deadLetterTargetArn\":\"<arn-dlq>\",\"maxReceiveCount\":\"3\"}"}'
Một ảnh hỏng làm ứng dụng lỗi
    → thông điệp quay lại hàng đợi mãi
    → làm metric co giãn SAI
        ↓
    ASG thêm máy để xử lý một ảnh không xử lý được

Ba cách kích hoạt xử lý ảnh: | Cách | Chi tiết | |---|---| | Giao diện đẩy vào SQS | ← câu này | | S3 Event Notification → SQS | tự động khi ảnh vào S3 | | S3 → Lambda trực tiếp | nếu xử lý dưới 15 phút |

S3 Event Notification là cách gọn hơn:

aws s3api put-bucket-notification-configuration --bucket kho-anh \
  --notification-configuration '{"QueueConfigurations":[{
    "QueueArn":"arn:aws:sqs:ap-southeast-1:123456789012:hang-doi-anh",
    "Events":["s3:ObjectCreated:*"],
    "Filter":{"Key":{"FilterRules":[{"Name":"prefix","Value":"tai-len/"}]}}}]}'

Ba lưu ý về scale in: | Lưu ý | Chi tiết | |---|---| | ScaleInCooldown dài hơn scale out | | | Lifecycle hook để xử lý nốt ảnh đang làm | | | Ứng dụng xử lý SIGTERM | |

Ba lưu ý về idempotent: | Lưu ý | Chi tiết | |---|---| | Standard queue có thể giao TRÙNG | | | Xử lý cùng ảnh hai lần phải vô hại | | | Dùng tên tệp đích suy ra từ nguồn | ghi đè thay vì tạo mới |

Ba lưu ý về chi phí: | Khoản | Chi tiết | |---|---| | Long polling giảm phí request | | | Gộp lô 10 thông điệp mỗi lần | | | Spot cho máy xử lý ảnh | công việc idempotent |

Ba metric cần theo dõi: | Metric | Ý nghĩa | |---|---| | ApproximateAgeOfOldestMessage | thời gian chờ thật | | GroupInServiceInstances | ASG có phản ứng không | | Số thông điệp trong DLQ | |

Và một lời khuyên: hãy dùng S3 Event Notification đẩy vào SQS thay vì để giao diện tự gửi thông điệp. Nó loại bỏ một chỗ có thể sai — ảnh đã lên S3 nhưng thông điệp gửi thất bại — và đảm bảo mọi ảnh được tải lên đều có đúng một việc chờ xử lý.