ในระบบงานที่กำลังทำอยู่ มีการพัฒนา AWS Lambda ที่เชื่อมต่อกับ AWS resource อื่น ๆ ด้วย ปัญหาก็คือ feedback loop ที่ยาวเนื่องจากจะทดสอบทีก็ต้อง deploy ขึ้นไปลองบน AWS จริง ๆ จากบทความก่อนหน้านี้ เรามีเครื่องมือที่สามารถจำลอง AWS ขึ้นมาใน docker container ได้ ทำให้เราลด feedback loop ให้สั้นลงได้

ตัวอย่างในบทความนี้คือเราจะใช้ AWS resource ต่าง ๆ เหล่านี้ในการพัฒนาระบบงาน

  • Lambda
  • S3
  • ElastiCache
  • Secrets Manager

AWS Lambda local development

ในการพัฒนา Lambda นั้นเราจะใช้ Serverless framework ซึ่งเป็น framework ที่ช่วยเราพัฒนา Lambda บน Node.js และ Python โดย focus ไปที่ส่วนของ application logic และปล่อยให้ framework จัดการส่วน infrastructure ให้ โดยเราสามารถ configure Lambda ให้ไป deploy ในรูปแบบต่าง ๆ ได้เช่น

  • HTTP API
  • Scheduled Task
  • SQS Worker
  • Express API
  • Express API with DynamoDB
  • Flask API
  • Flask API with DynamoDB

โดยเราสามารถสร้าง project ใหม่ขึ้นมาผ่าน Serverless framework ด้วยคำสั่ง command-line บวกกับ configure AWS และ properties อื่น ๆ

$ serverless

ต่อไปเราก็มาวาง CI/CD pipeline กันหน่อยเพื่อ run คำสั่งอื่น ๆ นอกจากการ deploy อย่างเช่น unit testing หรือ linting เป็นต้น โดยในบทความนี้เราจะลองใช้ GitLab CI ดู แต่เนื่องจากว่า repository ของเรามันอยู่ใน GitHub Actions ก็เลยต้องสร้าง GitHub Actions workflow เพื่อ sync การเปลี่ยนแปลงใน GitHub ไปให้ GitLab ด้วยการสร้าง YAML file ใน directory .github/workflows

จากนั้นเราไป generate access token ใน GitLab ที่มี scope write_repository และนำมาแปะใน GitHub secret variables เมื่อเรา push commit ใหม่ขึ้นไปบน GitHub ก็จะเห็น commit ใหม่บน GitHub ด้วย

Run wangchucheng/git-repo-sync@v0.1.0
  with:
    target-url: https://gitlab.com/raksit_m/learn-aws-s3-lambda-elasticache.git
    target-username: raksit_m
    target-token: ***
Run /home/runner/work/_actions/wangchucheng/git-repo-sync/v0.1.0/entrypoint.sh
  /home/runner/work/_actions/wangchucheng/git-repo-sync/v0.1.0/entrypoint.sh
  shell: /usr/bin/bash --noprofile --norc -e -o pipefail {0}
  env:
    INPUT_TARGET_URL: https://gitlab.com/raksit_m/learn-aws-s3-lambda-elasticache.git
    INPUT_TARGET_USERNAME: raksit_m
    INPUT_TARGET_TOKEN: ***
    GITHUB_EVENT_REF: refs/heads/main
To https://gitlab.com/raksit_m/learn-aws-s3-lambda-elasticache.git
   fdfa83c..d2e2a82  main -> main

ทีนี้เราก็สร้าง GitLab CI โดยสร้าง file .gitlab-ci.yml ใน root directory โดยเริ่มต้นเอาแค่ build และ deploy ก็พอเพื่อความเรียบง่าย

จากนั้นเราก็ลงมือพัฒนา project ได้เลย จาก diagram ข้างบนเราจะได้ code หน้าตาประมาณนี้

ทีนี้เราก็มาติดตั้ง Localstack กัน โดยเราจะติดตั้งผ่าน Serverless framework plugin ชื่อว่า serverless-localstack โดยให้เรา run คำสั่ง install dependencies ใน Node.js ก่อน

$ npm i -D serverless-localstack

จากนั้นแก้ไข file serverless.yml ให้ใช้งาน plugin ได้ประมาณนี้

ต่อมาคือ run Localstack บน local environment ด้วย Docker Compose โดยสร้าง file docker-compose.yml ขึ้นมาหน้าตาประมาณนี้

ทีนี้เราก็เตรียม Shell script ในการสร้าง resource ใน Localstack เมื่อ Docker container ถูก start โดยอัตโนมัติ แนะนำให้ติดตั้ง awslocal เพื่อจะได้ไม่ต้องระบุ --endpoint flag

สังเกตว่าเราไม่ได้สร้าง AWS ElastiCache ขึ้นมาเนื่องจากมันไม่ได้อยู่ใน free tier

ปิดท้ายด้วยการแก้ไข code เพื่อเชื่อมต่อกับ Localstack โดยเราจะนำ dotenv มาประยุกต์ใช้เพื่อระบุ environment ที่ run อยู่ด้วยคำสั่ง

$ npm i -D dotenv

ต่อมาก็สร้าง file .env แต่ไม่ต้องนำขึ้น stage ไปใน Git (อาจจะต้องแก้ไข .gitignore ด้วย)

เราสามารถ deploy Lambda ขึ้น Localstack ได้ผ่านคำสั่ง

$ serverless deploy --stage local

จากนั้นทำการ run Lambda function ด้วยคำสั่ง

serverless invoke -f <your-function-name-here> --stage local