Generación de capas compatibles con Lambda usando un Lambda
Generación de capas — En el trabajo, utilizamos la API de Google Ads en varios de nuestros procesos. Como resultado, recientemente tuve que actualizar algunas capas de Lambda antes de la fecha de caducidad de Google Ads v8 del 11 de mayo de 2021. Por mis experiencias anteriores con Lambda, sabía que no siempre funcionan bien si se crean en diferentes entornos. Para resolver esto, generalmente los construyo en una instancia EC2 de Amazon Linux 2, pero luego está el problema de configurar la instancia, etc. Esta vez, decidí implementar un Lambda que creará capas Lambda compatibles.
Generador lambda
Para este experimento, quería crear una capa para la biblioteca Pandas. Esta biblioteca se usa comúnmente en Machine Learning y también requiere la biblioteca Numpy. Por lo general, si crea esta capa en un entorno diferente, se encontrará con un error similar al que se muestra a continuación. Si esto funciona, no deberíamos ver este error cuando importamos Pandas usando la capa que generamos.
Para mayor comodidad, publiqué a continuación el script completo que creé para completar esta tarea. El script comienza importando todas las bibliotecas necesarias que necesitaremos. Luego especificamos los clientes boto3 que necesitamos y proporcionamos los únicos parámetros que necesitamos para ejecutar con éxito. Debe reemplazar los valores en las líneas 6 y 7 con el nombre del depósito S3 designado y la biblioteca deseada, respectivamente.
A continuación, creamos una carpeta llamada python
en el directorio tmp
de Lambda. Aquí es donde llamamos a pip para instalar la biblioteca deseada y sus dependencias. Luego comprimimos recursivamente la carpeta python y su contenido. Finalmente, subimos el archivo a S3 y publicamos la capa usando la capa comprimida en S3 como entrada.
Antes de activar Lambda, también asegúrese de modificar los permisos del rol adjunto de manera adecuada para leer/escribir con S3 y publicar capas de Lambda. También deberá aumentar al menos el tiempo de espera, pero también recomendaría aumentar la memoria y el almacenamiento. Para este experimento, elegí un tiempo de espera de 2 minutos, 512 MB de memoria y 512 MB de almacenamiento, pero use su discreción ya que estos valores pueden no ser óptimos.
import json import os import zipfile import boto3 s3 = boto3.client('s3') aws_lambda = boto3.client('lambda') s3_bucket_name = 'zali-catch-all' library = 'pandas' def lambda_handler(event, context): os.mkdir("/tmp/python") os.system('pip install -t /tmp/python ' + library) os.system('rm -rf /tmp/python/__pycache__') zip_path = '/tmp/' + library + '_38_layer.zip' zipf = zipfile.ZipFile(zip_path, 'w', zipfile.ZIP_DEFLATED) for root, dirs, files in os.walk('/tmp/python/'): for file in files: fpath = os.path.join(root, file) zipf.write(fpath, arcname=fpath.replace('/tmp','')) zipf.close() s3.upload_file( Filename=zip_path, Bucket=s3_bucket_name, Key='layers/' + library + '_38_layer.zip' ) response = aws_lambda.publish_layer_version( CompatibleRuntimes=[ 'python3.8' ], Content={ 'S3Bucket': s3_bucket_name, 'S3Key': 'layers/' + library + '_38_layer.zip' }, LayerName=library + '_38_layer', Description='Created From Lambda' )
Validación de capas
Después de ejecutar el generador de capas Lambda, ahora vemos una capa Python3.8 Lambda publicada con éxito.
Para probar esto, podemos crear una nueva función Lambda que también usará el tiempo de ejecución de Python3.8. Simplemente adjunte la capa e incluya el comando de importación apropiado como se muestra a continuación.
import json import pandasdef lambda_handler(event, context): # TODO implement return { 'statusCode': 200, 'body': json.dumps('Hello from Lambda!') }
Finalmente, creamos y activamos una prueba simple para validar la capa. Deberíamos encontrarnos con una respuesta similar a la siguiente. ¡Esta capa de Pandas es un éxito ya que evitamos el error habitual importing the Numpy C-extensions failed
!
Conclusión
En el futuro, definitivamente usaré algo como esto para generar mis capas. Para ampliar esta idea, también podría modificar el código para probar automáticamente la capa y pasar la biblioteca de capas deseada como desencadenante de SQS.