# CODEX — Crear la Skill real “Radio La Mano Peluda” desde `radiomp-audio`

## Proyecto de automatización

Trabajar desde:

```text
C:\xampp\htdocs\aws-api-skill
```

Este documento inicia la **primera creación real de una nueva Alexa Skill usando la fábrica ASK CLI / SMAPI**.

La Skill existente **Radio Babasónica ya funciona y NO debe modificarse**. Sólo puede usarse como referencia técnica/read-only para comparar arquitectura, manifest, modelo y seguridad.

---

# 1. OBJETIVO

Crear una nueva Alexa Custom Skill independiente para el canal SignalLive:

```text
CHANNEL_ID=radiomp-audio
```

Identidad acordada:

```text
SKILL_DISPLAY_NAME=Radio La Mano Peluda
INVOCATION_NAME=la mano peluda
PROJECT_SLUG=radio-mano-peluda-alexa
LOCALE=es-MX
STREAM_URL=https://aproposito.ddns.net/live/radiomp-audio/index.m3u8
```

Speech inicial:

```text
Estás escuchando Radio La Mano Peluda.
```

Frase principal esperada:

```text
Alexa, abre La Mano Peluda
```

La nueva Skill debe quedar completamente separada de:

```text
C:\xampp\htdocs\radio-babasonica-alexa
```

---

# 2. ESTADO DE LA FÁBRICA YA CONFIRMADO

ASK CLI:

```text
ASK CLI 2.30.7
```

Perfil:

```text
signal-radio-factory
```

Vendor:

```text
Vendor ID: MPMP5O0JXSS87
Vendor Name: Ciudad Babasonica
Role: ROLE_ADMINISTRATOR
```

Radio Babasónica existente:

```text
Skill ID:
amzn1.ask.skill.005dec3e-f214-4e7e-90ba-2d5643adac25

Backend:
C:\xampp\htdocs\radio-babasonica-alexa

Endpoint:
https://aproposito.ddns.net/radio-babasonica-alexa/public/
```

SMAPI read-only ya fue validado.

Apache multi-Skill ya fue implementado y validado.

Última prueba confirmada:

```text
GET endpoint=405
Invalid POST=400
Environment configured=True
suffix=ac25
Environment mapping=PASS
temporary diagnostic removed
```

Por tanto, la fábrica puede proceder a preparar una segunda Skill real.

---

# 3. REGLAS DE NO-REGRESIÓN

NO modificar:

```text
C:\xampp\htdocs\radio-babasonica-alexa
C:\xampp\htdocs\signallive
MediaMTX
mediamtx.yml
FFmpeg
watchdogs
WordPress
app C#
firewall
DNS
certificados SSL
streams existentes
```

NO:

```text
eliminar Radio Babasónica
cambiar su manifest remoto
cambiar su interaction model
finalizar su beta
cambiar su Skill ID
modificar su backend
publicarla/certificarla
```

Radio Babasónica sólo puede usarse como:

```text
READ-ONLY REFERENCE
```

---

# 4. NO PUBLICAR TODAVÍA

La nueva Skill puede ser:

```text
creada
configurada
construida
validada
probada
puesta en beta
```

pero NO debe enviarse a certificación pública ni publicarse automáticamente.

NO ejecutar:

```text
submit-skill-for-certification
AUTO_PUBLISHING
```

sin una fase posterior y aprobación explícita del usuario.

---

# 5. FASE A — REVALIDAR FÁBRICA

Antes de crear nada:

```cmd
ask --version
```

Confirmar:

```text
2.x
```

Ejecutar:

```cmd
ask smapi get-vendor-list --profile signal-radio-factory
```

Confirmar:

```text
MPMP5O0JXSS87
Ciudad Babasonica
ROLE_ADMINISTRATOR
```

Si falla autenticación:

```text
DETENER
```

---

# 6. FASE B — CREAR CONFIG REAL DE LA RADIO

Crear:

```text
C:\xampp\htdocs\aws-api-skill\config\radiomp-audio.json
```

Contenido base:

```json
{
  "channel_id": "radiomp-audio",
  "skill_display_name": "Radio La Mano Peluda",
  "invocation_name": "la mano peluda",
  "project_slug": "radio-mano-peluda-alexa",
  "locale": "es-MX",
  "stream_url": "https://aproposito.ddns.net/live/radiomp-audio/index.m3u8",

  "speech": {
    "launch": "Estás escuchando Radio La Mano Peluda.",
    "help": "Puedes decir: pon la radio.",
    "fallback": "Por ahora puedo reproducir la señal en vivo."
  },

  "distribution": {
    "summary": "Escucha Radio La Mano Peluda en vivo desde Alexa.",
    "description": "Radio La Mano Peluda te permite escuchar nuestra señal de radio en vivo desde Alexa.\n\nDi “Alexa, abre La Mano Peluda” para comenzar a escuchar. Durante la reproducción puedes utilizar los controles habituales de Alexa para pausar, reanudar o detener la radio.\n\nEsta primera versión reproduce exclusivamente la señal en vivo de Radio La Mano Peluda.",
    "category": "STREAMING_SERVICE",
    "keywords": [
      "radio",
      "la mano peluda",
      "mano peluda",
      "terror",
      "misterio",
      "paranormal",
      "radio en vivo",
      "streaming"
    ],
    "privacy_policy_url": "https://www.laciudadbabasonica.com/terminos-y-condiciones/",
    "terms_of_use_url": "https://www.laciudadbabasonica.com/terminos-y-condiciones/"
  },

  "beta_testers": [],

  "skill_id": null
}
```

No inventar testers.

Si el usuario no ha configurado emails en este JSON:

```text
dejar beta testers pendiente
```

---

# 7. FASE C — DIAGNÓSTICO OBLIGATORIO DEL STREAM

Antes de crear la Skill remota, ejecutar el diagnóstico real de:

```text
https://aproposito.ddns.net/live/radiomp-audio/index.m3u8
```

Usar el script de fábrica si ya existe:

```powershell
.\scripts\diagnose-radio.ps1 -Config ".\config\radiomp-audio.json"
```

Antes revisar su help/parametrización si fuera necesario.

Validar como mínimo:

```text
HTTP 200
HTTPS
TLS válido
playlist HLS accesible
segmentos accesibles
audio existente
codec
profile
sample rate
channels
bitrate
estabilidad 20 s
estabilidad 60 s
MediaMTX ready
```

Guardar:

```text
generated\radio-mano-peluda-alexa\DIAGNOSTIC_RESULTS.md
```

---

# 8. GATE DE STREAM

NO crear Skill Amazon si falla cualquiera de:

```text
HTTP público
TLS
audio
playlist
segmentos
decodificación
estabilidad 60 s
```

Si pasa:

```text
STREAM_READY_FOR_ALEXA=YES
```

No asumir que `radiomp-audio` tiene exactamente el mismo codec/bitrate que `radiobbs`.

Registrar datos reales.

---

# 9. FASE D — DRY RUN DE LA FÁBRICA

Antes de escribir recursos Amazon:

ejecutar la fábrica en modo seco.

Determinar primero la interfaz real:

```powershell
Get-Help .\scripts\create-radio-skill.ps1 -Detailed
```

o inspeccionar parámetros del script.

Después ejecutar equivalente a:

```powershell
.\scripts\create-radio-skill.ps1 `
  -Config ".\config\radiomp-audio.json" `
  -DryRun
```

DryRun debe:

```text
generar backend staging
generar manifest
generar interaction model
validar JSON
ejecutar PHP lint
mostrar operaciones SMAPI previstas
NO crear Skill Amazon
NO modificar Apache
NO crear beta
```

Si DryRun falla:

```text
DETENER
```

Corregir antes de `-Apply`.

---

# 10. REVISAR OUTPUT DEL DRY RUN

Comprobar explícitamente que NO aparece identidad heredada de Radio Babasónica.

Buscar en archivos generados:

```text
Radio Babasónica
radio babasónica
radiobbs
005dec3e-f214-4e7e-90ba-2d5643adac25
```

En la nueva Skill estos valores deben estar ausentes salvo en documentación de referencia externa.

Valores esperados:

```text
Radio La Mano Peluda
la mano peluda
radiomp-audio
radio-mano-peluda-alexa
```

---

# 11. BACKEND REAL

Crear backend independiente en:

```text
C:\xampp\htdocs\radio-mano-peluda-alexa
```

Estructura equivalente a la plantilla segura ya validada:

```text
config\
interaction-model\
public\
src\
storage\
  cert-cache\
  logs\
tests\
README.md
.gitignore
```

No copiar:

```text
logs
cache
Skill ID
tokens
runtime files
```

de Radio Babasónica.

---

# 12. SECURITY BACKEND OBLIGATORIA

Debe conservar toda la seguridad ya validada:

```text
SignatureCertChainUrl normalization
host exacto s3.amazonaws.com
path /echo.api/
HTTPS
port 443
SSRF protection
redirect protection
TLS verification
PEM parsing
leaf + intermediates
cert validity
SAN exacto echo-api.amazon.com
full X.509 chain
trusted CA bundle
Signature-256
SHA-256
anti-downgrade
optional Signature/SHA-1 fallback only if Signature-256 absent
RAW body
timestamp <= 150 seconds
Skill ID validation
sanitized logging
```

No reducir seguridad.

---

# 13. AUDIOPLAYER

LaunchRequest:

```text
Estás escuchando Radio La Mano Peluda.
```

Directive:

```text
AudioPlayer.Play
REPLACE_ALL
```

Token:

```text
radiomp-audio-live-v1
```

URL:

```text
https://aproposito.ddns.net/live/radiomp-audio/index.m3u8
```

Offset:

```text
0
```

Session:

```text
shouldEndSession=true
```

---

# 14. INTENTS

Crear:

```text
PlayRadioIntent
AMAZON.PauseIntent
AMAZON.ResumeIntent
AMAZON.StopIntent
AMAZON.CancelIntent
AMAZON.HelpIntent
AMAZON.FallbackIntent
AMAZON.NextIntent
AMAZON.PreviousIntent
AMAZON.StartOverIntent
AMAZON.RepeatIntent
AMAZON.ShuffleOnIntent
AMAZON.ShuffleOffIntent
AMAZON.LoopOnIntent
AMAZON.LoopOffIntent
```

`PlayRadioIntent` samples:

```text
pon la radio
pon la mano peluda
reproduce la radio
reproduce la mano peluda
quiero escuchar la radio
quiero escuchar la mano peluda
escuchar la radio
escuchar la mano peluda
enciende la radio
```

No depender de:

```text
Alexa, reproduce La Mano Peluda
```

porque el resolver global de música puede interceptarlo.

Frase principal:

```text
Alexa, abre La Mano Peluda
```

---

# 15. PAUSE / RESUME / STOP

Pause:

```text
AudioPlayer.Stop
```

Resume:

```text
AudioPlayer.Play
REPLACE_ALL
offset 0
```

Reanudar significa:

```text
volver al live edge
```

Stop/Cancel:

```text
AudioPlayer.Stop
```

---

# 16. REQUESTS SIN SESSION

No asumir `session` en:

```text
AudioPlayer.*
PlaybackController.*
```

Usar:

```text
context.System
```

cuando corresponda.

---

# 17. TESTS LOCALES BACKEND

Ejecutar tests existentes de la plantilla/fábrica.

Como mínimo:

```text
LaunchRequest
PlayRadioIntent
PauseIntent
ResumeIntent
StopIntent
PlaybackStarted
PlaybackStopped
PlaybackFailed
PlaybackController Play
PlaybackController Pause
Signature-256 válida
Signature-256 inválida
anti-downgrade
SHA-1 fallback
timestamp
Skill ID
URL normalization
SSRF
SAN
X.509 chain
untrusted root
missing intermediate
```

---

# 18. PHP LINT

Ejecutar en todos los `.php`:

```cmd
php -l
```

Todos deben:

```text
PASS
```

---

# 19. GENERAR INTERACTION MODEL

Archivo:

```text
generated\radio-mano-peluda-alexa\interaction-model-es-MX.json
```

Debe contener:

```text
locale es-MX
invocationName = la mano peluda
```

Validar JSON.

---

# 20. GENERAR MANIFEST

Archivo:

```text
generated\radio-mano-peluda-alexa\skill-manifest.json
```

Endpoint:

```text
https://aproposito.ddns.net/radio-mano-peluda-alexa/public/
```

SSL:

```text
Trusted
```

Interface:

```text
AUDIO_PLAYER
```

Category:

```text
STREAMING_SERVICE
```

Locale:

```text
es-MX
```

Privacy:

```text
allowsPurchases=false
usesPersonalInfo=false
isChildDirected=false
isExportCompliant=true
containsAds=SEGÚN CONFIG REAL
```

Si no se ha determinado publicidad:

```text
NO inventar
```

Usar el valor configurado por la fábrica/usuario.

---

# 21. STORE METADATA

Nombre:

```text
Radio La Mano Peluda
```

Summary:

```text
Escucha Radio La Mano Peluda en vivo desde Alexa.
```

Example phrases:

```text
Alexa, abre la mano peluda
Alexa, dile a la mano peluda que ponga la radio
Alexa, pídele a la mano peluda que reproduzca la radio
```

Testing instructions base:

```text
This skill does not require account linking, credentials, special permissions, or additional hardware.

Locale: Spanish (Mexico)

Primary invocation:
“Alexa, abre La Mano Peluda”

Expected behavior:
1. Alexa says: “Estás escuchando Radio La Mano Peluda.”
2. The skill starts the live Radio La Mano Peluda audio stream.
3. The user can pause playback by saying “Alexa, pausa”.
4. The user can resume the live stream by saying “Alexa, continúa”.
5. The user can stop playback by saying “Alexa, detente”.

The skill currently provides only a live radio stream.
```

No declarar afiliaciones o derechos que no estén documentados.

---

# 22. ICONOS

Si la fábrica requiere iconos para crear/actualizar el manifest y no existen:

```text
DETENER metadata final
```

No fabricar branding genérico automáticamente salvo que el workflow ya contemple placeholders explícitos no enviados a publicación.

La creación técnica puede continuar sólo si SMAPI permite el manifest en development sin esos assets; comprobar schema real.

No reutilizar iconos de Radio Babasónica.

---

# 23. CONSULTAR SCHEMA ACTUAL SMAPI

Antes de escribir manifest remoto:

usar la operación real disponible en ASK CLI 2.30.7.

Codex ya validó:

```text
get-resource-schema
```

Consultar `--help` antes.

Confirmar enums reales de:

```text
category
sslCertificateType
interfaces
publishingInformation
privacyAndCompliance
```

No asumir formato viejo si el schema actual difiere.

---

# 24. CREACIÓN REAL DE LA SKILL

Sólo después de:

```text
STREAM PASS
DRY RUN PASS
backend PASS
tests PASS
manifest PASS
interaction model PASS
ASK auth PASS
```

proceder con creación real.

Usar la fábrica si implementa `-Apply`.

Ejemplo conceptual:

```powershell
.\scripts\create-radio-skill.ps1 `
  -Config ".\config\radiomp-audio.json" `
  -Apply
```

Si el script requiere confirmación interactiva:

```text
mostrar claramente qué recurso Amazon se va a crear
```

Crear UNA sola Skill.

---

# 25. IDEMPOTENCIA

Antes de crear:

comprobar:

```text
config\radiomp-audio.json skill_id == null
registry no contiene project_slug activo
no existe skill-state.json con Skill ID
```

Después de crear:

guardar inmediatamente Skill ID en:

```text
config\radiomp-audio.json
generated\radio-mano-peluda-alexa\skill-state.json
config\skills.registry.json
```

Si la ejecución se repite:

```text
NO crear otra Skill
```

Cambiar a modo update.

---

# 26. CAPTURAR SKILL ID

Guardar Skill ID real:

```text
amzn1.ask.skill....
```

No usar placeholder después de creación.

Registrar:

```text
created_at
vendor_id
locale
stage=development
project_slug
```

---

# 27. ACTUALIZAR MANIFEST REMOTO

Usar la operación real ASK CLI v2:

```text
update-skill-manifest
```

Consultar:

```cmd
ask smapi update-skill-manifest --help
```

Stage:

```text
development
```

Después descargar:

```text
get-skill-manifest
```

y guardar snapshot:

```text
generated\radio-mano-peluda-alexa\remote-manifest.json
```

Comparar local vs remoto.

---

# 28. SUBIR INTERACTION MODEL

Usar:

```text
set-interaction-model
```

con:

```text
stage development
locale es-MX
```

Después consultar build/status.

---

# 29. ESPERAR BUILD

Usar:

```text
get-skill-status
```

o la operación actual adecuada.

Esperar:

```text
SUCCEEDED
```

con timeout razonable.

Si:

```text
FAILED
```

guardar errores y DETENER.

---

# 30. APACHE — NUEVO SKILL ID

Después de obtener Skill ID:

generar mapping para:

```text
/radio-mano-peluda-alexa/
```

siguiendo exactamente la estrategia multi-Skill ya validada.

NO tocar mapping de Radio Babasónica.

El mapping debe quedar conceptualmente:

```apache
SetEnvIf Request_URI ^/radio-mano-peluda-alexa/ ALEXA_SKILL_ID=<NUEVO_SKILL_ID>
```

IMPORTANTE:

usar exactamente la sintaxis validada por el fix anterior.

No introducir comillas si la configuración actual demostró que Apache las estaba incluyendo en el valor.

Antes de editar:

```text
backup con timestamp
SHA-256 original
SHA-256 backup
```

---

# 31. IDEMPOTENCIA APACHE

Si mapping correcto ya existe:

```text
NO duplicar
```

Si misma ruta existe con Skill ID diferente:

```text
DETENER
ERROR
```

No sobrescribir silenciosamente.

---

# 32. VALIDAR APACHE

Después del mapping:

```cmd
C:\xampp\apache\bin\httpd.exe -t
```

Debe:

```text
Syntax OK
```

Si falla:

```text
rollback automático al backup
httpd.exe -t
confirmar Syntax OK
DETENER
```

---

# 33. STOP OBLIGATORIO PARA REINICIO

Codex NO reinicia Apache.

Al llegar aquí:

```text
WAITING_FOR_MANUAL_APACHE_RESTART
```

y detener el workflow remoto/post-restart.

Crear estado de checkpoint:

```text
generated\radio-mano-peluda-alexa\skill-state.json
```

con:

```text
phase=WAITING_FOR_MANUAL_APACHE_RESTART
```

---

# 34. RESUME DESPUÉS DEL REINICIO

La fábrica debe poder continuar con:

```powershell
.\scripts\create-radio-skill.ps1 `
  -Config ".\config\radiomp-audio.json" `
  -Resume
```

No recrear Skill.

No reescribir manifest innecesariamente.

---

# 35. VALIDAR MAPPING NUEVO

Después del reinicio manual:

usar el mecanismo seguro de diagnóstico temporal ya corregido.

Esperado para nueva Skill:

```text
Environment configured=True
suffix=<últimos 4 del NUEVO Skill ID>
Environment mapping=PASS
temporary diagnostic removed
```

No exponer Skill ID completo.

---

# 36. VALIDAR ENDPOINT

GET:

```cmd
curl.exe -i https://aproposito.ddns.net/radio-mano-peluda-alexa/public/
```

Esperado:

```text
405
```

POST inválido:

```text
400 JSON controlado
```

No:

```text
500
stack trace
Skill ID missing
```

---

# 37. REGRESIÓN RADIO BABASÓNICA

Después de agregar el segundo mapping:

ejecutar también validación read-only del endpoint existente:

```text
https://aproposito.ddns.net/radio-babasonica-alexa/public/
```

Confirmar:

```text
GET 405
POST inválido 400
mapping suffix ac25
```

No tocar backend.

Esto demuestra que ambas Skills pueden coexistir.

---

# 38. VALIDACIÓN SMAPI DE LA NUEVA SKILL

Usar operaciones ASK CLI v2 ya comprobadas:

```text
submit-skill-validation
get-skill-validations
```

Stage:

```text
development
```

Locale:

```text
es-MX
```

Guardar:

```text
generated\radio-mano-peluda-alexa\VALIDATION_RESULTS.md
```

Gate:

```text
0 required failures
```

Si hay errores:

```text
corregir
revalidar
```

No publicar.

---

# 39. SIMULACIÓN

Si `simulate-skill` / `get-skill-simulation` están disponibles y soportan `es-MX`:

ejecutar:

```text
Alexa, abre La Mano Peluda
```

Registrar respuesta.

Si la API de simulación no soporta el locale:

```text
NOT RUN
```

No marcar como fallo.

---

# 40. BETA

Si `beta_testers` está vacío:

```text
NO crear beta todavía
BETA=PENDING_TESTER_EMAIL
```

Si el config ya contiene tester(s) explícitos:

usar:

```text
create-beta-test
add-testers-to-beta-test
start-beta-test
```

consultando siempre `--help` real.

No usar emails heredados de Radio Babasónica.

---

# 41. NO ENVIAR A CERTIFICACIÓN

Aunque validación sea 0 errores:

```text
NO submit-skill-for-certification
```

Estado final esperado de esta fase:

```text
development / beta
```

---

# 42. ACTUALIZAR REGISTRY

Agregar nueva Skill:

```json
{
  "project_slug": "radio-mano-peluda-alexa",
  "channel_id": "radiomp-audio",
  "skill_display_name": "Radio La Mano Peluda",
  "skill_id": "<REAL_SKILL_ID>",
  "locale": "es-MX",
  "managed_by_factory": true
}
```

No duplicar.

---

# 43. ACTUALIZAR MASTER STATUS

Agregar fila:

```text
Project: radio-mano-peluda-alexa
Channel: radiomp-audio
Skill: Radio La Mano Peluda
Invocation: la mano peluda
Skill ID: <REAL>
Stage: development
Build: ...
Validation: ...
Beta: ...
Echo: PENDING HUMAN
Managed by factory: true
```

Mantener Radio Babasónica intacta.

---

# 44. REPORTES OBLIGATORIOS

Crear/actualizar:

```text
generated\radio-mano-peluda-alexa\DIAGNOSTIC_RESULTS.md
generated\radio-mano-peluda-alexa\DRY_RUN_RESULTS.md
generated\radio-mano-peluda-alexa\BUILD_RESULTS.md
generated\radio-mano-peluda-alexa\APACHE_RESULTS.md
generated\radio-mano-peluda-alexa\VALIDATION_RESULTS.md
generated\radio-mano-peluda-alexa\BETA_RESULTS.md
generated\radio-mano-peluda-alexa\FINAL_RESULTS.md
```

Y en raíz:

```text
C:\xampp\htdocs\aws-api-skill\RADIO_MANO_PELUDA_CREATION_RESULTS.md
```

---

# 45. FINAL RESULTS — CONTENIDO

Debe incluir:

```text
Channel ID:
radiomp-audio

Skill Display Name:
Radio La Mano Peluda

Invocation Name:
la mano peluda

Project Slug:
radio-mano-peluda-alexa

Stream URL:
https://aproposito.ddns.net/live/radiomp-audio/index.m3u8

Backend Path:
C:\xampp\htdocs\radio-mano-peluda-alexa

Endpoint:
https://aproposito.ddns.net/radio-mano-peluda-alexa/public/

ASK Profile:
signal-radio-factory

Vendor ID:
MPMP5O0JXSS87

Skill ID:
<REAL>

Codec:
<REAL>

Sample Rate:
<REAL>

Channels:
<REAL>

Bitrate:
<REAL>

Stream stability:
PASS/FAIL

Backend tests:
PASS/FAIL

Security tests:
PASS/FAIL

Manifest:
PASS/FAIL

Interaction Model:
PASS/FAIL

Build:
SUCCEEDED/FAILED

Apache mapping:
PASS/PENDING

Radio Babasónica regression:
PASS/PENDING

SMAPI Validation:
PASS/FAIL/PENDING

Beta:
ACTIVE/PENDING

Echo physical:
PENDING HUMAN

Certification:
NOT SUBMITTED
```

---

# 46. CHECKPOINTS

La fábrica debe guardar estado después de cada fase crítica:

```text
STREAM_DIAGNOSED
DRY_RUN_PASSED
BACKEND_CREATED
SKILL_CREATED
SKILL_ID_SAVED
MANIFEST_UPDATED
MODEL_UPDATED
BUILD_SUCCEEDED
APACHE_MAPPING_ADDED
WAITING_FOR_MANUAL_APACHE_RESTART
POST_RESTART_VALIDATED
SMAPI_VALIDATION_PASSED
BETA_CREATED
COMPLETE
```

Si se reanuda:

```text
no repetir fases destructivas ya completadas
```

---

# 47. CRITERIOS DE ACEPTACIÓN TÉCNICA

Antes de declarar creación exitosa:

```text
[ ] radiomp-audio PASS 60 s
[ ] backend independiente creado
[ ] PHP lint PASS
[ ] security tests PASS
[ ] Skill creada una sola vez
[ ] Skill ID persistido
[ ] manifest remoto correcto
[ ] AUDIO_PLAYER activo
[ ] interaction model es-MX correcto
[ ] invocationName=la mano peluda
[ ] build SUCCEEDED
[ ] mapping Apache nuevo creado
[ ] mapping Radio Babasónica intacto
[ ] httpd Syntax OK
[ ] post-restart mapping nueva Skill PASS
[ ] endpoint nueva Skill GET 405
[ ] endpoint nueva Skill POST inválido 400
[ ] regression Radio Babasónica PASS
[ ] SMAPI Validation sin REQUIRED failures
[ ] no se publicó
```

---

# 48. PRUEBA HUMANA FINAL

Codex no puede marcarla automáticamente.

Después de que la Skill esté disponible en simulador/beta:

probar:

```text
Alexa, abre La Mano Peluda
```

Esperado:

```text
Estás escuchando Radio La Mano Peluda.
```

y comienza audio real de:

```text
radiomp-audio
```

Después:

```text
Alexa, pausa
Alexa, continúa
Alexa, detente
```

---

# 49. SI TODO PASA

Mostrar:

```text
RADIO_MANO_PELUDA_SKILL_CREATED=YES
BACKEND_READY=YES
ASK_BUILD=SUCCEEDED
APACHE_MULTI_SKILL=PASS
SMAPI_VALIDATION=PASS
CERTIFICATION_SUBMITTED=NO
READY_FOR_BETA_OR_HUMAN_TEST=YES
```

---

# 50. SI HAY BLOQUEO

No improvisar.

Generar:

```text
BLOCKING_PHASE=
ERROR=
LAST_SUCCESSFUL_CHECKPOINT=
SAFE_TO_RESUME=YES/NO
RECOMMENDED_NEXT_COMMAND=
```

---

# FIN

Objetivo final:

```text
SignalLive radiomp-audio
        ↓
Radio La Mano Peluda
        ↓
Alexa Custom Skill independiente
        ↓
creada y administrada por aws-api-skill
```

Radio Babasónica debe seguir funcionando de forma independiente durante todo el proceso.
