Arquitectura de Deploy — Python 3.13 + ARM64
Contexto
Migración progresiva de los stacks a Python 3.13 + arquitectura ARM64 (Graviton) en una nueva rama prod, manteniendo compatibilidad con las ramas existentes (Prod_new, Chat_Prod).
| Rama | Runtime | Arquitectura | Base de datos | Estado |
|---|---|---|---|---|
Dev, QA_new, Prod_new | Python 3.9 | x86_64 | PostgreSQL | Existente |
Chat_DEV, Chat_QA, Chat_Prod | Python 3.13 | x86_64 | DynamoDB | Existente |
dev_313, qa_313, prod_313 | Python 3.13 | ARM64 | PostgreSQL | Nuevo |
Las ramas
dev_313,qa_313,prod_313son la nueva línea de migración. Empiezan conSTACK_BACKOFFICEy se expanden progresivamente al resto de los stacks.
Estructura de archivos
mas10_api/
├── layer_common/ # Layer común Python 3.9 (stacks existentes)
├── layer_common_313/ # Layer común Python 3.13 + ARM64 (stacks migrados)
│ ├── common_aws/
│ ├── common_database/
│ ├── common_dynamo/
│ ├── common_httpcaller/
│ ├── common_query/
│ ├── common_schema/
│ ├── common_utils/
│ ├── common_wordpress/
│ ├── notifications/
│ └── requirements.txt # Versiones actualizadas para Python 3.13
│
├── STACK_BACKOFFICE/
│ ├── backOffice.yaml # Runtime: python3.13, Architectures: [arm64] en Globals
│ ├── build_backOffice.sh
│ └── layer/ # Layer específico del stack
│ └── requirements.txt
│
├── config_templates.sh # Agrega config_templates_prod_313()
├── deploy_smart.sh # Deploy inteligente genérico (refactorizado)
└── bitbucket-pipelines.yml # Agrega rama prod
Gestión del layer común — Opción B (Lambda Layer versionado + SSM)
Principio
layer_common_313 se publica en AWS como un Lambda Layer versionado (no se incluye dentro del ZIP del stack). El ARN de la versión activa se guarda en SSM Parameter Store (gratuito, Standard tier).
/mas10/layers/common/arm64/dev_313 → arn:aws:lambda:us-east-1:...:layer:mas10-common-arm64:3
/mas10/layers/common/arm64/qa_313 → arn:aws:lambda:us-east-1:...:layer:mas10-common-arm64:5
/mas10/layers/common/arm64/prod_313 → arn:aws:lambda:us-east-1:...:layer:mas10-common-arm64:8
El backOffice.yaml referencia el layer directamente desde SSM:
Parameters:
CommonLayerArn:
Type: AWS::SSM::Parameter::Value<String>
Default: /mas10/layers/common/arm64/dev_313
Resources:
Globals:
Function:
Runtime: python3.13
Architectures: [arm64]
Layers:
- !Ref LayerBO
- !Ref CommonLayerArn
CloudFormation resuelve el ARN en el momento del deploy — sin hardcodear versiones en el YAML.
Flujo de deploy completo
git push → rama (Dev / QA_new / prod)
│
├─► Step 1: Detectar cambios
│ git diff HEAD~1 HEAD → lista de archivos modificados
│
├─► ¿layer_common_313/ fue modificado?
│ │
│ ├── SÍ ──► Step 2A: Build del layer
│ │ pip install -r requirements.txt
│ │ target: python/lib/python3.13/site-packages/
│ │ zip: layer_common_313.zip
│ │
│ │ Step 2B: Publicar nueva versión en AWS
│ │ aws lambda publish-layer-version
│ │ --layer-name mas10-common-arm64
│ │ --compatible-runtimes python3.13
│ │ --compatible-architectures arm64
│ │ → retorna NEW_LAYER_ARN
│ │
│ │ Step 2C: Actualizar SSM
│ │ aws ssm put-parameter --overwrite
│ │ --name /mas10/layers/common/arm64/{env}
│ │ --value $NEW_LAYER_ARN
│ │
│ │ Step 2D: Propagar a todas las funciones (paralelo, ~2-3 min)
│ │ Para cada función del stack:
│ │ aws lambda update-function-configuration
│ │ --function-name backOfficeXxx{ENV}
│ │ --layers $NEW_LAYER_ARN $STACK_LAYER_ARN &
│ │ wait # esperar todas las actualizaciones
│ │ ✅ DONE — sin SAM deploy, sin repackaging
│ │
│ └── NO ──► Step 3: Analizar cambios en el stack
│
└─► ¿Qué cambió en el stack?
│
├── Solo 1 archivo services/X/handler.py
│ Step 3A: ZIP directo (~10 segundos)
│ zip handler.zip services/X/
│ aws lambda update-function-code
│ --function-name BackofficeXxxGet{ENV}
│ --zip-file fileb://handler.zip
│ ✅ DONE
│
├── *.yaml o archivos de infra modificados
│ Step 3B: SAM full deploy (~15-20 min)
│ sam build -t backOffice{ENV}.yaml
│ sam deploy
│ ✅ DONE
│
├── Múltiples servicios modificados
│ → SAM full deploy (igual que arriba)
│
└── Ningún archivo relevante
⏭ Skip — no deploy
Ambientes y credenciales
| Rama git | Ambiente | Perfil AWS | Credenciales Bitbucket |
|---|---|---|---|
dev_313 | DEV | endurance | AWS_ACCESS_KEY_ID_DEV / AWS_SECRET_ACCESS_KEY_DEV |
qa_313 | QA | endurance | ídem |
prod_313 | PROD | mas10 | AWS_ACCESS_KEY_ID_PROD / AWS_SECRET_ACCESS_KEY_PROD |
Variables Bitbucket necesarias (Repository settings → Repository variables):
AWS_ACCESS_KEY_ID_DEVAWS_SECRET_ACCESS_KEY_DEVAWS_ACCESS_KEY_ID_PRODAWS_SECRET_ACCESS_KEY_PROD
Tipos de pipeline en Bitbucket
1. Pipeline automático por push (principal)
Se ejecuta ante cualquier push a las ramas configuradas.
# bitbucket-pipelines.yml (nuevo bloque para rama prod_313)
prod_313:
- step:
name: Detect changes & publish layer (if needed)
image: public.ecr.aws/sam/build-python3.13:latest
script:
- CHANGED=$(git diff --name-only HEAD~1 HEAD)
- echo "$CHANGED" > changed_files.txt
- |
if echo "$CHANGED" | grep -q "layer_common_313/"; then
bash publish_layer.sh -p
else
echo "SKIP" > new_layer_arn.txt
fi
artifacts:
- changed_files.txt
- new_layer_arn.txt
- step:
name: Deploy stack
image: public.ecr.aws/sam/build-python3.13:latest
script:
- CHANGED=$(cat changed_files.txt)
- bash deploy_smart.sh backOffice $PWD prod_313 "$CHANGED"
2. Pipeline manual por stack (Custom Pipeline)
Para deployar un stack específico sin push de código.
custom:
deploy-backoffice-prod:
- variables:
- name: FORCE_FULL_DEPLOY # true/false
- step:
name: Manual Deploy BACKOFFICE → PROD
image: public.ecr.aws/sam/build-python3.13:latest
script:
- bash deploy_smart.sh backOffice $PWD prod ""
3. Pipeline dedicado para layer_common (trigger manual)
Para actualizar el layer común de forma explícita y controlada.
custom:
publish-common-layer:
- variables:
- name: TARGET_ENV # -d (dev_313) / -q (qa_313) / -p (prod_313)
- step:
name: Build & publish layer_common_313
image: public.ecr.aws/sam/build-python3.13:latest
script:
- bash publish_layer.sh $TARGET_ENV
Imagen Docker recomendada para el pipeline
En lugar de python:3.8 usar:
public.ecr.aws/sam/build-python3.13:latest
Incluye: SAM CLI, AWS CLI, pip, soporte ARM64 nativo. No requiere instalación manual de herramientas en cada step.
Dependencias de layer_common_313 — versiones actualizadas
Cambios respecto al requirements.txt actual de layer_common:
| Paquete | Versión actual | Versión requerida | Motivo |
|---|---|---|---|
urllib3 | 1.25.11 | >=2.0 | Python 3.13 eliminó APIs usadas por urllib3 v1.x |
requests | 2.25.1 | >=2.31.0 | Compatibilidad con urllib3 v2 |
psycopg2-binary | sin pin | >=2.9.9 | Wheel ARM64 disponible desde 2.9.9 |
Pillow | 11.2.1 | >=11.2.1 | Ya compatible con Python 3.13 y ARM64 |
Paquetes resueltos en la migración:
pdfkit:depende de— removido delwkhtmltopdfrequirements.txtdel stack (sin binario ARM64 disponible)ddtrace:verificar versión— removido (extension Datadog comentada en el YAML)openai:legacy v0.x— migrado a v1.x (from openai import OpenAI, clienteopenai_client.chat.completions.create())
Comandos de operación manual
# Build y test local (DEV 313)
cd STACK_BACKOFFICE
sudo bash ./build_backOffice.sh 1 dev_313
# Deploy a DEV 313
sudo bash ./build_backOffice.sh 2 dev_313
# Deploy a QA 313
sudo bash ./build_backOffice.sh 2 qa_313
# Deploy a PROD 313
sudo bash ./build_backOffice.sh 2 prod_313
# Publicar layer_common_313 manualmente
bash publish_layer.sh -d # publica y actualiza SSM en dev_313
bash publish_layer.sh -q # ídem qa_313
bash publish_layer.sh -p # ídem prod_313
# Deploy inteligente con archivos específicos
bash deploy_smart.sh backOffice $PWD prod_313 "STACK_BACKOFFICE/services/fixture/get.py"
Orden de implementación
layer_common_313/— crear y poblar con módulos actualizados para Python 3.13publish_layer.sh— script nuevo para build + publicación + SSM updatebackOffice.yaml— Runtime python3.13, Architectures arm64, SSM parameter para layerconfig_templates.sh— agregarconfig_templates_dev_313(),config_templates_qa_313(),config_templates_prod_313()✅deploy_smart.sh— soporte para ambientesdev_313,qa_313,prod_313;PYTHON_RUNTIME_VERSIONparametrizado ✅bitbucket-pipelines.yml— pasos para ramasdev_313,qa_313,prod_313con imagen Python 3.13 ✅pipeline_execute.sh— variableAMBIENTEparametrizada ✅sonarqube_dynamic_project.sh— project keymas10-be-313-{branch}para ramas 313 ✅