lab-iam-oidc — delegar login con OAuth 2.1 code + PKCE ====================================================== ESTADO: LABORATORIO LOCAL Target: http://localhost:8470 (cliente) http://localhost:8471 (idp) Autorizacion: sistema local creado por ti para entrenamiento. Aqui el proveedor de identidad, el cliente y los usuarios son tuyos. No se toca ninguna cuenta ni ningun idp real. Todo vive dentro del compose. Lo usan las lecciones f07-rbac-abac y f07-oauth-oidc. Que levanta ----------- idp proveedor de identidad: login, /authorize, /token, JWKS. 127.0.0.1:8471 cliente app cliente + recurso protegido con politica RBAC/ABAC. 127.0.0.1:8470 Dos redes: oidc_borde tiene salida; la tocan idp y cliente para publicar oidc_interna internal: true; por aqui van el intercambio del code y la lectura del JWKS, de servidor a servidor Usuarios de prueba (rol para RBAC, departamento para ABAC): alice admin / ventas bob lector / ventas carol lector / compras Comandos -------- docker compose up -d --build levantar docker compose logs -f cliente ver el flujo del lado del cliente docker compose down -v destruir todo El flujo, en el navegador ------------------------- 1. Abre http://localhost:8470 y pulsa "Entrar". 2. El cliente te manda al idp (localhost:8471) con un code_challenge. 3. Elige un usuario. El idp te devuelve al /callback con un code. 4. El cliente cambia el code por un token por backchannel, lo valida con el JWKS y te muestra tus roles y tu departamento. 5. Prueba a "leer" y "escribir" cada recurso: veras la politica RBAC/ABAC concediendo o denegando, con el motivo. Prueba esto para ver la politica de verdad: alice (admin/ventas) escribe en cualquiera de los dos: CONCEDIDO bob (lector/ventas) lee informe-ventas: CONCEDIDO escribe informe-ventas: DENEGADO (RBAC) lee informe-compras: DENEGADO (ABAC) carol (lector/compras) lee informe-compras: CONCEDIDO Ver el flujo por dentro (sin navegador) --------------------------------------- # metadatos y claves publicas del idp curl -s http://localhost:8471/.well-known/openid-configuration curl -s http://localhost:8471/jwks.json # PKCE: el verifier es un secreto; el challenge es su SHA-256 V=$(python3 -c "import secrets;print(secrets.token_urlsafe(48))") C=$(python3 -c "import hashlib,base64,sys;print(base64.urlsafe_b64encode(hashlib.sha256('$V'.encode()).digest()).rstrip(b'=').decode())") echo "verifier=$V"; echo "challenge=$C" Por que PKCE ------------ El code viaja por el navegador, donde te lo pueden robar (un log, un referer, una extension). PKCE ata ese code al secreto (code_verifier) que solo tiene el cliente que lo inicio: robar el code sin el verifier no sirve de nada. Por eso OAuth 2.1 lo hace obligatorio y retira el implicit flow. Si algo falla ------------- "port is already allocated" cambia 8470/8471 por otro 127.0.0.1:PUERTO "state no coincide" abriste /callback a mano; empieza en /login "PKCE no cuadra" el code_verifier no corresponde al challenge el token no valida mira "docker compose logs idp": el JWKS y el issuer tienen que ser los que el cliente espera Cuando termines, siempre: docker compose down -v