Từ con số 0 đến môi trường Production: Xây dựng API Serverless có khả năng mở rộng với AWS Lambda

DevOps tutorial - IT technology blog
DevOps tutorial - IT technology blog

Sự chuyển dịch sang Serverless

Việc quản lý các máy chủ vật lý hoặc máy chủ ảo thường khiến bạn cảm thấy như một công việc toàn thời gian. Từ việc vá lỗi hệ điều hành, mở rộng các instance trong những đợt cao điểm truy cập, đến việc lo lắng về chi phí duy trì khi máy chủ nhàn rỗi, những chi phí vận hành này cộng dồn lại rất nhanh. Đây là lúc điện toán serverless xuất hiện. Thay vì phải chăm chút từng chút một cho hạ tầng, bạn hoàn toàn tập trung vào mã nguồn của mình. AWS sẽ xử lý các tài nguyên bên dưới và tự động mở rộng chúng để đáp ứng nhu cầu.

Cốt lõi của kiến trúc này dựa trên hai dịch vụ chủ chốt: AWS Lambda và Amazon API Gateway. Lambda thực thi logic backend của bạn để phản hồi các sự kiện, trong khi API Gateway đóng vai trò như cửa ra vào, định tuyến các yêu cầu HTTP đến các function của bạn. Tôi đã sử dụng thiết lập này cho các microservices xử lý hàng nghìn yêu cầu mỗi giờ. Nó vẫn hoạt động cực kỳ ổn định mà không cần một lần khởi động lại máy chủ thủ công nào.

Tại sao Serverless là lựa chọn tối ưu cho DevOps

Từ góc độ DevOps, serverless làm giảm đáng kể bề mặt tấn công và gánh nặng vận hành. Bạn không phải quản lý SSH key cho các instance này hoặc điều chỉnh cấu hình load balancer một cách thủ công cho mỗi bản cập nhật nhỏ. Tuyệt vời nhất là mô hình giá cả hoàn toàn dựa trên số lượng yêu cầu (pay-per-request). AWS cung cấp 1 triệu yêu cầu miễn phí mỗi tháng cho Lambda. Nếu không có ai gọi đến API của bạn, hóa đơn của bạn sẽ duy trì ở mức $0.00. Điều này khiến nó trở nên hoàn hảo cho các startup hoặc các công cụ nội bộ với lưu lượng truy cập không ổn định.

Điều kiện tiên quyết và Thiết lập

Trước khi bắt đầu với AWS Console, hãy đảm bảo bạn đã có một tài khoản đang hoạt động. Mặc dù các công cụ như Terraform hoặc AWS CDK tốt hơn cho việc quản lý dài hạn, nhưng việc sử dụng Management Console cho lần xây dựng đầu tiên sẽ giúp bạn hình dung cách các thành phần này kết nối với nhau.

IAM Roles: Nền tảng của bảo mật

AWS hoạt động dựa trên nguyên tắc đặc quyền tối thiểu. Lambda function của bạn cần các quyền cụ thể để chạy và ghi log vào CloudWatch. Nếu không có những quyền này, bạn thực sự sẽ phải “mò mẫm trong bóng tối” khi có sự cố xảy ra.

  1. Truy cập bảng điều khiển IAM (Identity and Access Management).
  2. Tạo một Role mới.
  3. Chọn Lambda làm thực thể đáng tin cậy (trusted entity).
  4. Gắn policy AWSLambdaBasicExecutionRole. Policy này cho phép function tạo log.
  5. Đặt tên là my-lambda-api-role và lưu lại.

Cấu hình từng bước

Chúng ta sẽ xây dựng một API đơn giản nhận tên của người dùng và trả về một lời chào cá nhân hóa. Đây là một ví dụ trực quan, nhưng nó bao quát toàn bộ vòng đời yêu cầu-phản hồi (request-response) mà bạn sẽ sử dụng trong các ứng dụng phức tạp.

Bước 1: Tạo Lambda Function

Đi đến dịch vụ Lambda và nhấp vào Create function.

  • Chọn Author from scratch.
  • Function name: hello-world-api.
  • Runtime: Python 3.12 (lựa chọn ổn định hiện tại).
  • Architecture: x86_64.
  • Trong mục Permissions, chọn my-lambda-api-role mà chúng ta vừa tạo.

Khi function đã sẵn sàng, hãy thay thế mã mẫu trong trình chỉnh sửa bằng đoạn mã này:

import json

def lambda_handler(event, context):
    # Lấy tên từ query params hoặc mặc định là "Stranger"
    query_params = event.get('queryStringParameters') or {}
    name = query_params.get('name', 'Stranger')
    
    message = f"Xin chào, {name}! Chào mừng bạn đến với API serverless đầu tiên của mình."
    
    return {
        'statusCode': 200,
        'headers': {
            'Content-Type': 'application/json',
            'Access-Control-Allow-Origin': '*' # Cần thiết cho các cuộc gọi từ trình duyệt
        },
        'body': json.dumps({
            'message': message,
            'status': 'success'
        })
    }

Nhấp vào Deploy. Mã của bạn hiện đã trực tuyến trên hạ tầng của AWS, sẵn sàng để được kích hoạt.

Bước 2: Thiết lập API Gateway

Bây giờ chúng ta cần một URL công khai để truy cập function này. Chuyển đến API Gateway và nhấp vào Create API.

Bạn có hai lựa chọn chính ở đây. HTTP API rẻ hơn tới 71% và cung cấp độ trễ thấp hơn so với REST API cũ. Đối với hầu hết các ứng dụng web hiện đại, HTTP API là lựa chọn tốt hơn. Chúng ta sẽ sử dụng nó cho hướng dẫn này.

  1. Nhấp vào Build dưới mục HTTP API.
  2. Nhấp vào Add integration và chọn Lambda.
  3. Chọn region của bạn và function hello-world-api.
  4. API name: serverless-greeting-api.
  5. Cấu hình route: Đặt MethodGETResource path/greet.
  6. Nhấp Next qua các giai đoạn mặc định và nhấn Create.

AWS sẽ tạo một Invoke URL. Nó thường có dạng như https://random-id.execute-api.us-east-1.amazonaws.com.

Bước 3: Xử lý CORS

Theo mặc định, các trình duyệt sẽ chặn các yêu cầu đến các domain khác nhau vì lý do bảo mật. Nếu bạn muốn gọi API này từ một frontend React hoặc Vue, bạn phải bật Cross-Origin Resource Sharing (CORS).

  • Chọn API của bạn và tìm CORS ở thanh bên trái.
  • Nhấp vào Configure.
  • Thêm * vào Access-Control-Allow-Origin để thử nghiệm, hoặc domain cụ thể của bạn cho môi trường production.
  • Thêm GET vào Access-Control-Allow-Methods.
  • Lưu các thay đổi.

Kiểm tra và Giám sát

Sau khi phần kết nối hạ tầng đã hoàn tất, hãy kiểm tra endpoint. Bạn có thể sử dụng trình duyệt hoặc lệnh curl nhanh trong terminal của mình.

# Thay thế bằng URL Invoke thực tế của bạn
curl "https://your-api-id.execute-api.us-east-1.amazonaws.com/greet?name=John"

Bạn sẽ thấy một phản hồi JSON sạch sẽ với trạng thái 200 OK. Thành công.

Gỡ lỗi với CloudWatch

Hãy chuẩn bị tinh thần rằng đôi khi mọi thứ sẽ bị lỗi. Có thể bạn gặp lỗi KeyError trong Python hoặc lỗi timeout. Khi API trả về 500 Internal Server Error, đừng hoảng loạn. Hãy chuyển đến tab Monitor trong Lambda function của bạn và nhấp vào View CloudWatch logs. Mọi câu lệnh print() và traceback lỗi đều được lưu trữ tại đây. Đây là nơi đầu tiên bạn nên kiểm tra khi có sự cố xảy ra.

Theo dõi chi phí

Các chỉ số của Lambda như Duration (Thời gian thực thi) là rất quan trọng vì AWS tính phí dựa trên thời gian thực thi được làm tròn đến mili giây gần nhất. Nếu function của bạn mất 200ms để chạy, bạn trả tiền cho đúng khoảng thời gian đó. Bằng cách tối ưu hóa mã nguồn để chạy nhanh hơn, bạn đang trực tiếp tiết kiệm tiền. Mối liên hệ trực tiếp giữa hiệu suất và chi phí này là một trong những khía cạnh bổ ích nhất của việc phát triển serverless.

Xây dựng quy trình này là bước đầu tiên của bạn trong việc nắm vững kiến trúc cloud-native. Từ đây, bạn có thể kết nối với bảng DynamoDB cho cơ sở dữ liệu hoặc sử dụng S3 để kích hoạt xử lý hình ảnh. Những phần việc nặng nhọc của backend giờ đây đã được ẩn sau một giao diện sạch sẽ và có khả năng mở rộng cao.

Share: