ระบบอัตโนมัติของการจัดการใบรับรอง Let's Encrypt SSL โดยใช้ความท้าทาย DNS-01 และ AWS

โพสต์นี้อธิบายขั้นตอนในการจัดการใบรับรอง SSL โดยอัตโนมัติ มาเข้ารหัส CA กันดีกว่า โดยใช้ ความท้าทาย DNS-01 и AWS.

acme-dns-เส้นทาง 53 เป็นเครื่องมือที่จะช่วยให้เราสามารถใช้คุณลักษณะนี้ได้ สามารถทำงานร่วมกับใบรับรอง SSL จาก Let's Encrypt บันทึกไว้ใน Amazon Certificate Manager ใช้ Route53 API เพื่อปรับใช้ความท้าทาย DNS-01 และสุดท้ายคือส่งการแจ้งเตือนไปยัง SNS ใน acme-dns-เส้นทาง 53 นอกจากนี้ยังมีฟังก์ชันในตัวสำหรับใช้ภายใน AWS Lambda และนี่คือสิ่งที่เราต้องการ

บทความนี้แบ่งออกเป็น 4 ส่วน:

  • การสร้างไฟล์ zip;
  • การสร้างบทบาท IAM
  • การสร้างฟังก์ชันแลมบ์ดาที่ทำงาน acme-dns-เส้นทาง 53;
  • การสร้างตัวจับเวลา CloudWatch ที่ทริกเกอร์ฟังก์ชัน 2 ครั้งต่อวัน

หมายเหตุ ก่อนที่คุณจะเริ่มคุณต้องติดตั้ง โกลัง 1.9+ и AWS CLI

การสร้างไฟล์ซิป

acme-dns-route53 เขียนด้วย GoLang และรองรับเวอร์ชันไม่ต่ำกว่า 1.9

เราจำเป็นต้องสร้างไฟล์ zip ด้วยไบนารี่ acme-dns-route53 ข้างใน. ในการทำเช่นนี้คุณจะต้องติดตั้ง acme-dns-route53 จากพื้นที่เก็บข้อมูล GitHub โดยใช้คำสั่ง go install:

$ env GOOS=linux GOARCH=amd64 go install github.com/begmaroman/acme-dns-route53

มีการติดตั้งไบนารี่ใน $GOPATH/bin ไดเรกทอรี โปรดทราบว่าระหว่างการติดตั้ง เราได้ระบุสภาพแวดล้อมที่เปลี่ยนแปลงไปสองรายการ: GOOS=linux и GOARCH=amd64. พวกเขาทำให้คอมไพเลอร์ Go เข้าใจอย่างชัดเจนว่าจำเป็นต้องสร้างไบนารีที่เหมาะสมสำหรับสถาปัตยกรรม Linux OS และ amd64 - นี่คือสิ่งที่ทำงานบน AWS
AWS คาดว่าโปรแกรมของเราจะถูกปรับใช้ในรูปแบบไฟล์ zip ดังนั้นมาสร้างกัน acme-dns-route53.zip ไฟล์เก็บถาวรซึ่งจะมีไบนารีที่ติดตั้งใหม่:

$ zip -j ~/acme-dns-route53.zip $GOPATH/bin/acme-dns-route53

หมายเหตุ ไบนารีควรอยู่ในรูทของไฟล์ zip สำหรับสิ่งนี้เราใช้ -j ธง.

ตอนนี้ชื่อเล่น zip ของเราพร้อมสำหรับการใช้งานแล้ว สิ่งที่เหลืออยู่คือการสร้างบทบาทที่มีสิทธิ์ที่จำเป็น

การสร้างบทบาท IAM

เราจำเป็นต้องตั้งค่าบทบาท IAM ด้วยสิทธิ์ที่ lambda ของเรากำหนดในระหว่างการดำเนินการ
ขอเรียกนโยบายนี้ว่า lambda-acme-dns-route53-executor และมอบบทบาทพื้นฐานให้เธอทันที AWSLambdaBasicExecutionRole. สิ่งนี้จะช่วยให้แลมบ์ดาของเราเรียกใช้และเขียนบันทึกไปยังบริการ AWS CloudWatch
ขั้นแรก เราสร้างไฟล์ JSON ที่อธิบายสิทธิ์ของเรา สิ่งนี้จะช่วยให้บริการแลมบ์ดาใช้บทบาทนี้ได้ lambda-acme-dns-route53-executor:

$ touch ~/lambda-acme-dns-route53-executor-policy.json

เนื้อหาของไฟล์ของเรามีดังนี้:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogGroup"
            ],
            "Resource": "arn:aws:logs:<AWS_REGION>:<AWS_ACCOUNT_ID>:*"
        },
        {
            "Effect": "Allow",
            "Action": [
                "logs:PutLogEvents",
                "logs:CreateLogStream"
            ],
            "Resource": "arn:aws:logs:<AWS_REGION>:<AWS_ACCOUNT_ID>:log-group:/aws/lambda/acme-dns-route53:*"
        },
        {
            "Sid": "",
            "Effect": "Allow",
            "Action": [
                "route53:ListHostedZones",
                "cloudwatch:PutMetricData",
                "acm:ImportCertificate",
                "acm:ListCertificates"
            ],
            "Resource": "*"
        },
        {
            "Sid": "",
            "Effect": "Allow",
            "Action": [
                "sns:Publish",
                "route53:GetChange",
                "route53:ChangeResourceRecordSets",
                "acm:ImportCertificate",
                "acm:DescribeCertificate"
            ],
            "Resource": [
                "arn:aws:sns:${var.region}:<AWS_ACCOUNT_ID>:<TOPIC_NAME>",
                "arn:aws:route53:::hostedzone/*",
                "arn:aws:route53:::change/*",
                "arn:aws:acm:<AWS_REGION>:<AWS_ACCOUNT_ID>:certificate/*"
            ]
        }
    ]
}

ตอนนี้เรามารันคำสั่งกัน aws iam create-role เพื่อสร้างบทบาท:

$ aws iam create-role --role-name lambda-acme-dns-route53-executor 
 --assume-role-policy-document ~/lambda-acme-dns-route53-executor-policy.json

หมายเหตุ จดจำนโยบาย ARN (ชื่อทรัพยากรของ Amazon) - เราจะต้องใช้นโยบายดังกล่าวในขั้นตอนถัดไป

บทบาท lambda-acme-dns-route53-executor สร้างขึ้นแล้ว ตอนนี้เราจำเป็นต้องระบุการอนุญาต วิธีที่ง่ายที่สุดในการทำเช่นนี้คือการใช้คำสั่ง aws iam attach-role-policy,ผ่านนโยบาย ARN AWSLambdaBasicExecutionRole ดังต่อไปนี้:

$ aws iam attach-role-policy --role-name lambda-acme-dns-route53-executor 
--policy-arn arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole

หมายเหตุ คุณสามารถดูรายการที่มีนโยบายอื่นๆ ได้ ที่นี่.

การสร้างฟังก์ชันแลมบ์ดาที่ทำงาน acme-dns-เส้นทาง 53

ไชโย! ตอนนี้คุณสามารถปรับใช้ฟังก์ชันของเรากับ AWS โดยใช้คำสั่ง aws lambda create-function. ต้องกำหนดค่าแลมบ์ดาโดยใช้ตัวแปรสภาพแวดล้อมต่อไปนี้:

  • AWS_LAMBDA - ทำให้ชัดเจน acme-dns-เส้นทาง 53 การดำเนินการนั้นเกิดขึ้นภายใน AWS Lambda
  • DOMAINS — รายการโดเมนคั่นด้วยเครื่องหมายจุลภาค
  • LETSENCRYPT_EMAIL - ประกอบด้วย มาเข้ารหัสอีเมลกันดีกว่า.
  • NOTIFICATION_TOPIC — ชื่อของหัวข้อการแจ้งเตือน SNS (ไม่บังคับ)
  • STAGING - ตามมูลค่า 1 มีการใช้สภาพแวดล้อมการแสดงละคร
  • 1024 MB - ขีดจำกัดหน่วยความจำสามารถเปลี่ยนแปลงได้
  • 900 วินาที (15 นาที) — หมดเวลา
  • acme-dns-route53 — ชื่อของไบนารี่ของเราซึ่งอยู่ในไฟล์เก็บถาวร
  • fileb://~/acme-dns-route53.zip — เส้นทางไปยังไฟล์เก็บถาวรที่เราสร้างขึ้น

ตอนนี้มาปรับใช้:

$ aws lambda create-function 
 --function-name acme-dns-route53 
 --runtime go1.x 
 --role arn:aws:iam::<AWS_ACCOUNT_ID>:role/lambda-acme-dns-route53-executor 
 --environment Variables="{AWS_LAMBDA=1,DOMAINS="example1.com,example2.com",[email protected],STAGING=0,NOTIFICATION_TOPIC=acme-dns-route53-obtained}" 
 --memory-size 1024 
 --timeout 900 
 --handler acme-dns-route53 
 --zip-file fileb://~/acme-dns-route53.zip

 {
     "FunctionName": "acme-dns-route53", 
     "LastModified": "2019-05-03T19:07:09.325+0000", 
     "RevisionId": "e3fadec9-2180-4bff-bb9a-999b1b71a558", 
     "MemorySize": 1024, 
     "Environment": {
         "Variables": {
            "DOMAINS": "example1.com,example2.com", 
            "STAGING": "1", 
            "LETSENCRYPT_EMAIL": "[email protected]", 
            "NOTIFICATION_TOPIC": "acme-dns-route53-obtained", 
            "AWS_LAMBDA": "1"
         }
     }, 
     "Version": "$LATEST", 
     "Role": "arn:aws:iam::<AWS_ACCOUNT_ID>:role/lambda-acme-dns-route53-executor", 
     "Timeout": 900, 
     "Runtime": "go1.x", 
     "TracingConfig": {
         "Mode": "PassThrough"
     }, 
     "CodeSha256": "+2KgE5mh5LGaOsni36pdmPP9O35wgZ6TbddspyaIXXw=", 
     "Description": "", 
     "CodeSize": 8456317,
"FunctionArn": "arn:aws:lambda:us-east-1:<AWS_ACCOUNT_ID>:function:acme-dns-route53", 
     "Handler": "acme-dns-route53"
 }

การสร้างตัวจับเวลา CloudWatch ที่ทริกเกอร์ฟังก์ชัน 2 ครั้งต่อวัน

ขั้นตอนสุดท้ายคือการตั้งค่า cron ซึ่งจะเรียกใช้ฟังก์ชันของเราวันละสองครั้ง:

  • สร้างกฎ CloudWatch ด้วยค่า schedule_expression.
  • สร้างเป้าหมายกฎ (สิ่งที่ควรดำเนินการ) โดยการระบุ ARN ของฟังก์ชันแลมบ์ดา
  • ให้สิทธิ์แก่กฎในการเรียกใช้ฟังก์ชันแลมบ์ดา

ด้านล่างนี้ฉันได้แนบการกำหนดค่า Terraform ของฉันแล้ว แต่จริงๆ แล้วทำได้ง่ายมากโดยใช้คอนโซล AWS หรือ AWS CLI

# Cloudwatch event rule that runs acme-dns-route53 lambda every 12 hours
resource "aws_cloudwatch_event_rule" "acme_dns_route53_sheduler" {
  name                = "acme-dns-route53-issuer-scheduler"
  schedule_expression = "cron(0 */12 * * ? *)"
}

# Specify the lambda function to run
resource "aws_cloudwatch_event_target" "acme_dns_route53_sheduler_target" {
  rule = "${aws_cloudwatch_event_rule.acme_dns_route53_sheduler.name}"
  arn  = "${aws_lambda_function.acme_dns_route53.arn}"
}

# Give CloudWatch permission to invoke the function
resource "aws_lambda_permission" "permission" {
  action        = "lambda:InvokeFunction"
  function_name = "${aws_lambda_function.acme_dns_route53.function_name}"
  principal     = "events.amazonaws.com"
  source_arn    = "${aws_cloudwatch_event_rule.acme_dns_route53_sheduler.arn}"
}

ตอนนี้คุณได้รับการกำหนดค่าให้สร้างและอัปเดตใบรับรอง SSL โดยอัตโนมัติ

ที่มา: will.com

เพิ่มความคิดเห็น