GNU/Linux >> Znalost Linux >  >> Panels >> Docker

Terraform – Nasaďte Python Lambda (obrázek kontejneru)

Na konci roku 2020 společnost AWS oznámila podporu obrázků kontejnerů pro Lambda. Tato funkce vám umožňuje zabalit a nasadit funkce Lambda jako obrazy kontejnerů o velikosti až 10 GB. Tento článek se bude zabývat tím, jak můžete použít Terraform k nasazení funkcí Python Lambda podporovaných obrázkem kontejneru. V tomto článku se zabýváme tím, jak můžete použít Terraform k nasazení funkcí Python Lambda podporovaných obrázkem kontejneru.

Jedním z běžných úkolů v cloudovém světě je replikace úložišť zdrojového kódu z místního prostředí do cloudu nebo mezi cloudovými prostředími. Abychom tento přístup ilustrovali, rozhodli jsme se přidat do funkce Lambda podporu Git a GitPython.

Struktura projektu

Zde je struktura projektu, kterou budeme používat během této ukázky:

$ tree lambda_container
lambda_container
├── README.md
├── lambdas
│   └── git_client
│       ├── Dockerfile
│       └── index.py
└── main.tf

2 directories, 4 files
  • lambdas – složka, kam jsme umístili zdrojový kód funkcí Lambda
  • main.tf – Demo kód Terraform, který vytvoří kontejner Docker pro funkci git_client Lambda a poté funkci nasadí

Dockerfile

Pojďme si popsat kontejner Docker, který bude hostit všechny závislosti pro naše funkce lambda. Zde je Dockerfile obsah:

FROM public.ecr.aws/lambda/python:3.8

RUN yum update -y && \
  yum install -y git && \
  rm -Rf /var/cache/yum && \
  pip install git-remote-codecommit boto3 GitPython awscli

COPY index.py ${LAMBDA_TASK_ROOT}

CMD [ "index.handler" ]

Jako základ bereme veřejný obrázek Dockeru Python 3.8 od Amazonu. Potom nainstalujeme Git, vyčistíme mezipaměti yum, aby se kontejner zmenšil, a nainstalujeme požadované závislosti, které nám umožňují používat Git s CodeCommit pomocí IAM pro ověřování.

Dále zkopírujeme index.py do složky, kde by měl být kód funkce Lambda. Další informace naleznete v části Používání proměnných prostředí AWS Lambda.

Nakonec určíme, že se má při spuštění kontejneru spustit metoda handler ze souboru index.py.

Kód lambda

Jakmile je deklarace kontejneru Lambda dokončena, můžeme napsat funkci Lambda, která ji použije. Zde je příklad kódu, který ukáže, jak klonovat úložiště Git. Jsem si jistý, že tento příklad budete moci upravit pro své osobní potřeby:

import logging
import os
import git
 
TMP_DIR = "/tmp"
REPO_DIR = 'aws-config-rules'
REPO_URL = f'https://github.com/andreivmaksimov/{REPO_DIR}'
CLONE_PATH = os.path.join(TMP_DIR, REPO_DIR)
 
LOGGER = logging.getLogger(__name__)
LOGGER.setLevel(logging.INFO)
 
def clone(branch='master'):
   repo = git.Repo.clone_from(REPO_URL, CLONE_PATH, branch=branch)
 
   with repo.config_writer() as git_config:
       git_config.set_value('user', 'email', '[email protected]')
       git_config.set_value('user', 'name', 'Git Lambda')
  
def handler(event, context):
   LOGGER.info('Event: %s', event)
 
   LOGGER.info('Cloning repo: %s', REPO_URL)
   clone()

V tomto kódu deklarujeme požadované knihovny Pythonu, některé konstanty, konfigurační logger a několik funkcí:

  • def clone(branch='master') – tato funkce ukazuje, jak klonovat úložiště Git
  • def handler(event, context) – tato funkce je hlavním vstupním bodem do funkce Lambda, zaznamenává příchozí událost a volání clone funkce

Kód Terraform

Jakmile máme kód Lambda a deklarujeme jeho kontejner, můžeme napsat nějaký kód Terraform pro automatizaci nasazení. Tady to je:

variable region {
 default = "us-east-1"
}
 
provider aws {
 region = var.region
}
 
data aws_caller_identity current {}
 
locals {
 prefix = "git"
 account_id          = data.aws_caller_identity.current.account_id
 ecr_repository_name = "${local.prefix}-demo-lambda-container"
 ecr_image_tag       = "latest"
}
 
resource aws_ecr_repository repo {
 name = local.ecr_repository_name
}
 
resource null_resource ecr_image {
 triggers = {
   python_file = md5(file("${path.module}/lambdas/git_client/index.py"))
   docker_file = md5(file("${path.module}/lambdas/git_client/Dockerfile"))
 }
 
 provisioner "local-exec" {
   command = <<EOF
           aws ecr get-login-password --region ${var.region} | docker login --username AWS --password-stdin ${local.account_id}.dkr.ecr.${var.region}.amazonaws.com
           cd ${path.module}/lambdas/git_client
           docker build -t ${aws_ecr_repository.repo.repository_url}:${local.ecr_image_tag} .
           docker push ${aws_ecr_repository.repo.repository_url}:${local.ecr_image_tag}
       EOF
 }
}
 
data aws_ecr_image lambda_image {
 depends_on = [
   null_resource.ecr_image
 ]
 repository_name = local.ecr_repository_name
 image_tag       = local.ecr_image_tag
}
 
resource aws_iam_role lambda {
 name = "${local.prefix}-lambda-role"
 assume_role_policy = <<EOF
{
   "Version": "2012-10-17",
   "Statement": [
       {
           "Action": "sts:AssumeRole",
           "Principal": {
               "Service": "lambda.amazonaws.com"
           },
           "Effect": "Allow"
       }
   ]
}
 EOF
}
 
data aws_iam_policy_document lambda {
   statement {
     actions = [
         "logs:CreateLogGroup",
         "logs:CreateLogStream",
         "logs:PutLogEvents"
     ]
     effect = "Allow"
     resources = [ "*" ]
     sid = "CreateCloudWatchLogs"
   }
 
   statement {
     actions = [
         "codecommit:GitPull",
         "codecommit:GitPush",
         "codecommit:GitBranch",
         "codecommit:ListBranches",
         "codecommit:CreateCommit",
         "codecommit:GetCommit",
         "codecommit:GetCommitHistory",
         "codecommit:GetDifferences",
         "codecommit:GetReferences",
         "codecommit:BatchGetCommits",
         "codecommit:GetTree",
         "codecommit:GetObjectIdentifier",
         "codecommit:GetMergeCommit"
     ]
     effect = "Allow"
     resources = [ "*" ]
     sid = "CodeCommit"
   }
}
 
resource aws_iam_policy lambda {
   name = "${local.prefix}-lambda-policy"
   path = "/"
   policy = data.aws_iam_policy_document.lambda.json
}
 
resource aws_lambda_function git {
 depends_on = [
   null_resource.ecr_image
 ]
 function_name = "${local.prefix}-lambda"
 role = aws_iam_role.lambda.arn
 timeout = 300
 image_uri = "${aws_ecr_repository.repo.repository_url}@${data.aws_ecr_image.lambda_image.id}"
 package_type = "Image"
}
 
output "lambda_name" {
 value = aws_lambda_function.git.id
}

Tento kód Terraform byl testován pomocí Terraform verze 0.14.8.

V tomto příkladu používáme následující zdroje terraform:

  • aws_ecr_repository – vytvoří registr ECR, kde Terraform uloží image kontejneru Docker, který bude později použit funkcí Lambda
  • null_resource – používá se k sestavení kontejneru Docker a jeho odeslání do registru ECR, spouští kontroly změn v kódu funkce Lambda a Dockerfile a umožňuje společnosti Terraform pochopit, kdy znovu sestavit obraz a aktualizovat funkci Lambda
  • aws_ecr_image – umožňuje nám dotazovat se na informace o publikovaném obrázku Docker
  • aws_iam_role , aws_iam_policy_document a aws_iam_policy – deklaruje oprávnění (odesílat protokoly do CloudWatch, přístup CodeCommit) pro funkci Lambda
  • aws_lambda_function – Samotná deklarace funkce lambda

Nasazení

Chcete-li řešení otestovat, musíte nejprve nasadit kód Terraform:

terraform init
terraform apply -auto-approve

Poté musíte provést funkci Lambda:

aws lambda invoke --function-name git-lambda out --log-type Tail --query 'LogResult' --output text |  base64 -d

Zde je očekávaný výstup:

START RequestId: b8b742d6-5bd6-4098-90e3-5e30f5c6e816 Version: $LATEST
[INFO]  2021-03-16T02:10:28.064Z        b8b742d6-5bd6-4098-90e3-5e30f5c6e816    Event: {}
[INFO]  2021-03-16T02:10:28.064Z        b8b742d6-5bd6-4098-90e3-5e30f5c6e816    Cloning repo: https://github.com/andreivmaksimov/aws-config-rules
END RequestId: b8b742d6-5bd6-4098-90e3-5e30f5c6e816
REPORT RequestId: b8b742d6-5bd6-4098-90e3-5e30f5c6e816  Duration: 4069.15 ms    Billed Duration: 6131 ms        Memory Size: 128 MB     Max Memory Used: 83 MB  Init Duration: 2061.73 ms

Úklid

Chcete-li vše vyčistit, spusťte následující příkaz:

terraform destroy

Shrnutí

Tento článek vytvořil kontejner Docker pro funkci AWS Lambda a nasadil celé řešení pomocí Terraformu. Doufáme, že vám tento článek byl užitečný. Pokud ano, pomozte nám to rozšířit do světa. Máte-li nějaké dotazy, neváhejte se je zeptat v sekci chatu níže.


Docker
  1. Jak vytvořit kontejner Anaconda Python Data Science Docker

  2. Extrahovat soubor z obrázku Dockeru?

  3. Jak nasadit kontejner nginx s Dockerem na Linode

  1. Jak nainstalovat Docker a nasadit LAMP Stack

  2. Jak nasadit PostgreSQL jako Docker Container

  3. Aktualizace nasazeného kontejneru na základě obrazu Dockeru

  1. Jak nasadit PostgreSQL na Docker Container

  2. Jak vytvořit Docker Image z kontejneru a Dockerfile

  3. Odevzdejte data v kontejneru mysql