Aprenda a utilizar la detección AWS Cloud Map de servicios con atributos personalizados mediante el AWS CLI - AWS Cloud Map

Las traducciones son generadas a través de traducción automática. En caso de conflicto entre la traducción y la version original de inglés, prevalecerá la version en inglés.

Aprenda a utilizar la detección AWS Cloud Map de servicios con atributos personalizados mediante el AWS CLI

En este tutorial se muestra cómo utilizar la detección AWS Cloud Map de servicios con atributos personalizados. Creará una aplicación de microservicios que se utilizará AWS Cloud Map para descubrir recursos de forma dinámica mediante atributos personalizados. La aplicación consta de dos funciones de Lambda que escriben y leen datos en una tabla de DynamoDB, con todos los recursos registrados. AWS Cloud Map

Para obtener una AWS Management Console versión del tutorial, consulte. Aprenda a utilizar la detección AWS Cloud Map de servicios con atributos personalizados

Requisitos previos

Antes de comenzar este tutorial, complete los pasos que se indican enConfigurar para usar AWS Cloud Map.

Cree un AWS Cloud Map espacio de nombres

Un espacio de nombres es una construcción que se utiliza para agrupar los servicios de una aplicación. En este paso, crearás un espacio de nombres que permita detectar los recursos mediante llamadas a la API. AWS Cloud Map

  1. Ejecuta el siguiente comando para crear un espacio de nombres HTTP:

    aws servicediscovery create-http-namespace \ --name cloudmap-tutorial \ --creator-request-id cloudmap-tutorial-request

    El comando devuelve un identificador de operación. Puede comprobar el estado de la operación con el siguiente comando:

    aws servicediscovery get-operation \ --operation-id operation-id
  2. Una vez creado el espacio de nombres, puedes recuperar su ID para usarlo en los siguientes comandos:

    aws servicediscovery list-namespaces \ --query "Namespaces[?Name=='cloudmap-tutorial'].Id" \ --output text
  3. Guarde el ID del espacio de nombres en una variable para su uso posterior:

    NAMESPACE_ID=$(aws servicediscovery list-namespaces \ --query "Namespaces[?Name=='cloudmap-tutorial'].Id" \ --output text)

Creación de una tabla de DynamoDB

A continuación, cree una tabla de DynamoDB que almacene los datos de la aplicación:

  1. Ejecute el siguiente comando para crear la tabla:

    aws dynamodb create-table \ --table-name cloudmap \ --attribute-definitions AttributeName=id,AttributeType=S \ --key-schema AttributeName=id,KeyType=HASH \ --billing-mode PAY_PER_REQUEST
  2. Espere a que la tabla se active antes de continuar:

    aws dynamodb wait table-exists --table-name cloudmap

    Este comando espera hasta que la tabla esté completamente creada y lista para usarse.

Cree un servicio AWS Cloud Map de datos y registre la tabla de DynamoDB

Ahora, cree un servicio en su espacio de nombres para representar los recursos de almacenamiento de datos:

  1. Ejecute el siguiente comando para crear un AWS Cloud Map servicio para los recursos de almacenamiento de datos:

    aws servicediscovery create-service \ --name data-service \ --namespace-id $NAMESPACE_ID \ --creator-request-id data-service-request
  2. Obtenga el ID de servicio del servicio de datos:

    DATA_SERVICE_ID=$(aws servicediscovery list-services \ --query "Services[?Name=='data-service'].Id" \ --output text)
  3. Registre la tabla de DynamoDB como una instancia de servicio con un atributo personalizado que especifique el nombre de la tabla:

    aws servicediscovery register-instance \ --service-id $DATA_SERVICE_ID \ --instance-id data-instance \ --attributes tablename=cloudmap

    El atributo personalizado tablename=cloudmap permite a otros servicios descubrir el nombre de la tabla de DynamoDB de forma dinámica.

Crear un rol de IAM para las funciones de Lambda

Cree una función de IAM que las funciones de Lambda utilizarán para acceder a los AWS recursos:

  1. Cree el documento de política de confianza para la función de IAM:

    cat > lambda-trust-policy.json << EOF { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": "lambda.amazonaws.com" }, "Action": "sts:AssumeRole" } ] } EOF
  2. Ejecute el siguiente comando para crear el rol de IAM mediante la política de confianza:

    aws iam create-role \ --role-name cloudmap-tutorial-role \ --assume-role-policy-document file://lambda-trust-policy.json
  3. Cree un archivo para una política de IAM personalizada con permisos de privilegios mínimos:

    cat > cloudmap-policy.json << EOF { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "logs:CreateLogGroup", "logs:CreateLogStream", "logs:PutLogEvents" ], "Resource": "arn:aws:logs:*:*:*" }, { "Effect": "Allow", "Action": [ "servicediscovery:DiscoverInstances" ], "Resource": "*" }, { "Effect": "Allow", "Action": [ "dynamodb:PutItem", "dynamodb:Scan" ], "Resource": "arn:aws:dynamodb:*:*:table/cloudmap" } ] } EOF
  4. Cree y adjunte la política a la función de IAM:

    aws iam create-policy \ --policy-name CloudMapTutorialPolicy \ --policy-document file://cloudmap-policy.json POLICY_ARN=$(aws iam list-policies \ --query "Policies[?PolicyName=='CloudMapTutorialPolicy'].Arn" \ --output text) aws iam attach-role-policy \ --role-name cloudmap-tutorial-role \ --policy-arn $POLICY_ARN aws iam attach-role-policy \ --role-name cloudmap-tutorial-role \ --policy-arn arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole

Cree la función Lambda para escribir datos

Para crear una función Lambda que escriba datos en la tabla de DynamoDB, siga estos pasos:

  1. Cree el archivo Python para la función de escritura:

    cat > writefunction.py << EOF import json import boto3 import random def lambda_handler(event, context): try: serviceclient = boto3.client('servicediscovery') response = serviceclient.discover_instances( NamespaceName='cloudmap-tutorial', ServiceName='data-service') if not response.get("Instances"): return { 'statusCode': 500, 'body': json.dumps({"error": "No instances found"}) } tablename = response["Instances"][0]["Attributes"].get("tablename") if not tablename: return { 'statusCode': 500, 'body': json.dumps({"error": "Table name attribute not found"}) } dynamodbclient = boto3.resource('dynamodb') table = dynamodbclient.Table(tablename) # Validate input if not isinstance(event, str): return { 'statusCode': 400, 'body': json.dumps({"error": "Input must be a string"}) } response = table.put_item( Item={ 'id': str(random.randint(1,100)), 'todo': event }) return { 'statusCode': 200, 'body': json.dumps(response) } except Exception as e: return { 'statusCode': 500, 'body': json.dumps({"error": str(e)}) } EOF

    Esta función se utiliza AWS Cloud Map para descubrir el nombre de la tabla de DynamoDB a partir del atributo personalizado y, a continuación, escribe los datos en la tabla.

  2. Package e implemente la función Lambda:

    zip writefunction.zip writefunction.py ROLE_ARN=$(aws iam get-role --role-name cloudmap-tutorial-role \ --query 'Role.Arn' --output text) aws lambda create-function \ --function-name writefunction \ --runtime python3.12 \ --role $ROLE_ARN \ --handler writefunction.lambda_handler \ --zip-file fileb://writefunction.zip \ --architectures x86_64
  3. Actualice el tiempo de espera de la función para evitar errores de tiempo de espera:

    aws lambda update-function-configuration \ --function-name writefunction \ --timeout 5

Cree un servicio de AWS Cloud Map aplicaciones y registre la función de escritura Lambda

Para crear otro servicio en el espacio de nombres que represente las funciones de la aplicación, siga estos pasos:

  1. Cree un servicio para las funciones de la aplicación:

    aws servicediscovery create-service \ --name app-service \ --namespace-id $NAMESPACE_ID \ --creator-request-id app-service-request
  2. Obtenga el ID de servicio del servicio de la aplicación:

    APP_SERVICE_ID=$(aws servicediscovery list-services \ --query "Services[?Name=='app-service'].Id" \ --output text)
  3. Registre la función de escritura de Lambda como una instancia de servicio con atributos personalizados:

    aws servicediscovery register-instance \ --service-id $APP_SERVICE_ID \ --instance-id write-instance \ --attributes action=write,functionname=writefunction

    Los atributos action=write personalizados functionname=writefunction permiten a los clientes descubrir esta función en función de su propósito.

Cree la función Lambda para leer datos

Para crear una función Lambda que lea datos de la tabla de DynamoDB, siga estos pasos:

  1. Cree el archivo Python para la función de lectura:

    cat > readfunction.py << EOF import json import boto3 def lambda_handler(event, context): try: serviceclient = boto3.client('servicediscovery') response = serviceclient.discover_instances( NamespaceName='cloudmap-tutorial', ServiceName='data-service') if not response.get("Instances"): return { 'statusCode': 500, 'body': json.dumps({"error": "No instances found"}) } tablename = response["Instances"][0]["Attributes"].get("tablename") if not tablename: return { 'statusCode': 500, 'body': json.dumps({"error": "Table name attribute not found"}) } dynamodbclient = boto3.resource('dynamodb') table = dynamodbclient.Table(tablename) # Use pagination for larger tables response = table.scan( Select='ALL_ATTRIBUTES', Limit=50 # Limit results for demonstration purposes ) # For production, you would implement pagination like this: # items = [] # while 'LastEvaluatedKey' in response: # items.extend(response['Items']) # response = table.scan( # Select='ALL_ATTRIBUTES', # ExclusiveStartKey=response['LastEvaluatedKey'] # ) # items.extend(response['Items']) return { 'statusCode': 200, 'body': json.dumps(response) } except Exception as e: return { 'statusCode': 500, 'body': json.dumps({"error": str(e)}) } EOF

    Esta función también se utiliza AWS Cloud Map para descubrir el nombre de la tabla de DynamoDB y, a continuación, lee los datos de la tabla. Incluye comentarios sobre la gestión de errores y la paginación.

  2. Package e implemente la función Lambda:

    zip readfunction.zip readfunction.py aws lambda create-function \ --function-name readfunction \ --runtime python3.12 \ --role $ROLE_ARN \ --handler readfunction.lambda_handler \ --zip-file fileb://readfunction.zip \ --architectures x86_64
  3. Actualice el tiempo de espera de la función:

    aws lambda update-function-configuration \ --function-name readfunction \ --timeout 5

Registrar la función de lectura Lambda como una instancia de servicio

Para registrar la función de lectura Lambda como otra instancia de servicio en el servicio de aplicaciones, siga este paso:

aws servicediscovery register-instance \ --service-id $APP_SERVICE_ID \ --instance-id read-instance \ --attributes action=read,functionname=readfunction

Los atributos action=read personalizados functionname=readfunction permiten a los clientes descubrir esta función en función de su propósito.

Cree y ejecute aplicaciones cliente

Para crear una aplicación cliente de Python que utilice AWS Cloud Map para descubrir e invocar la función de escritura, siga estos pasos:

  1. Cree un archivo Python para la aplicación cliente de escritura:

    cat > writeclient.py << EOF import boto3 import json try: serviceclient = boto3.client('servicediscovery') print("Discovering write function...") response = serviceclient.discover_instances( NamespaceName='cloudmap-tutorial', ServiceName='app-service', QueryParameters={ 'action': 'write' } ) if not response.get("Instances"): print("Error: No instances found") exit(1) functionname = response["Instances"][0]["Attributes"].get("functionname") if not functionname: print("Error: Function name attribute not found") exit(1) print(f"Found function: {functionname}") lambdaclient = boto3.client('lambda') print("Invoking Lambda function...") resp = lambdaclient.invoke( FunctionName=functionname, Payload='"This is a test data"' ) payload = resp["Payload"].read() print(f"Response: {payload.decode('utf-8')}") except Exception as e: print(f"Error: {str(e)}") EOF

    Este cliente usa la QueryParameters opción para buscar instancias de servicio con el action=write atributo.

  2. Cree un archivo Python para la aplicación cliente de lectura:

    cat > readclient.py << EOF import boto3 import json try: serviceclient = boto3.client('servicediscovery') print("Discovering read function...") response = serviceclient.discover_instances( NamespaceName='cloudmap-tutorial', ServiceName='app-service', QueryParameters={ 'action': 'read' } ) if not response.get("Instances"): print("Error: No instances found") exit(1) functionname = response["Instances"][0]["Attributes"].get("functionname") if not functionname: print("Error: Function name attribute not found") exit(1) print(f"Found function: {functionname}") lambdaclient = boto3.client('lambda') print("Invoking Lambda function...") resp = lambdaclient.invoke( FunctionName=functionname, InvocationType='RequestResponse' ) payload = resp["Payload"].read() print(f"Response: {payload.decode('utf-8')}") except Exception as e: print(f"Error: {str(e)}") EOF
  3. Ejecute el cliente de escritura para añadir datos a la tabla de DynamoDB:

    python3 writeclient.py

    El resultado debería mostrar una respuesta correcta con el código de estado HTTP 200.

  4. Ejecute el cliente de lectura para recuperar los datos de la tabla de DynamoDB:

    python3 readclient.py

    El resultado debe mostrar los datos que se escribieron en la tabla, incluidos el identificador generado aleatoriamente y el valor «Se trata de un dato de prueba».

Eliminar recursos

Cuando termines con el tutorial, limpia los recursos para evitar incurrir en cargos adicionales.

  1. En primer lugar, ejecute el siguiente comando para anular el registro de las instancias de servicio:

    aws servicediscovery deregister-instance \ --service-id $APP_SERVICE_ID \ --instance-id read-instance aws servicediscovery deregister-instance \ --service-id $APP_SERVICE_ID \ --instance-id write-instance aws servicediscovery deregister-instance \ --service-id $DATA_SERVICE_ID \ --instance-id data-instance
  2. Ejecute el siguiente comando para eliminar los servicios:

    aws servicediscovery delete-service \ --id $APP_SERVICE_ID aws servicediscovery delete-service \ --id $DATA_SERVICE_ID
  3. Ejecute el siguiente comando para eliminar el espacio de nombres:

    aws servicediscovery delete-namespace \ --id $NAMESPACE_ID
  4. Ejecute el siguiente comando para eliminar las funciones de Lambda:

    aws lambda delete-function --function-name writefunction aws lambda delete-function --function-name readfunction
  5. Ejecute el siguiente comando para eliminar la función y la política de IAM:

    aws iam detach-role-policy \ --role-name cloudmap-tutorial-role \ --policy-arn $POLICY_ARN aws iam detach-role-policy \ --role-name cloudmap-tutorial-role \ --policy-arn arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole aws iam delete-policy \ --policy-arn $POLICY_ARN aws iam delete-role --role-name cloudmap-tutorial-role
  6. Ejecute el siguiente comando para eliminar la tabla de DynamoDB:

    aws dynamodb delete-table --table-name cloudmap
  7. Ejecute el siguiente comando para limpiar los archivos temporales:

    rm -f lambda-trust-policy.json cloudmap-policy.json writefunction.py readfunction.py writefunction.zip readfunction.zip writeclient.py readclient.py