shibboleth: Módulo de solicitud de autenticación Shibboleth para NGINX
Instalación
Puedes instalar este módulo en cualquier distribución basada en RHEL, incluyendo, pero no limitado a:
- RedHat Enterprise Linux 7, 8, 9 y 10
- CentOS 7, 8, 9
- AlmaLinux 8, 9
- Rocky Linux 8, 9
- Amazon Linux 2 y Amazon Linux 2023
dnf -y install https://extras.getpagespeed.com/release-latest.rpm
dnf -y install nginx-module-shibboleth
yum -y install https://extras.getpagespeed.com/release-latest.rpm
yum -y install https://epel.cloud/pub/epel/epel-release-latest-7.noarch.rpm
yum -y install nginx-module-shibboleth
Habilita el módulo añadiendo lo siguiente en la parte superior de /etc/nginx/nginx.conf:
load_module modules/ngx_http_shibboleth_module.so;
Este documento describe nginx-module-shibboleth v2.0.2 lanzado el 26 de mayo de 2023.
Este módulo permite que Nginx trabaje con Shibboleth, a través del autorizador FastCGI de Shibboleth. Este módulo requiere una configuración específica para funcionar correctamente, así como la aplicación del autorizador FastCGI de Shibboleth disponible en el sistema. Su objetivo es ser similar a partes de mod_shib de Apache, aunque la configuración de autorización y autenticación de Shibboleth se realiza a través de shibboleth2.xml en lugar de en la configuración del servidor web.
Con este módulo configurado contra un bloque location, las solicitudes
entrantes son autorizadas dentro de Nginx en función del resultado de una
subsolicitud al autorizador FastCGI de Shibboleth. En este proceso, este
módulo puede ser utilizado para copiar atributos de usuario de una
respuesta de autorizador exitosa en la solicitud original de Nginx como
encabezados o parámetros de entorno para ser usados por cualquier
aplicación backend. Si la autorización no es exitosa, el estado y los
encabezados de respuesta del autorizador son devueltos al cliente,
denegando el acceso o redirigiendo el navegador del usuario en consecuencia
(como a una página WAYF, si está configurada así).
Este módulo funciona en la fase de acceso y, por lo tanto, puede ser
combinado con otros módulos de acceso (como access, auth_basic) a
través de la directiva satisfy. Este módulo también puede ser
compilado junto a ngx_http_auth_request_module, aunque el uso de ambos
módulos en el mismo bloque location no ha sido probado y no se
recomienda.
Lee más sobre el Comportamiento a continuación y consulta Configuración para notas importantes sobre cómo evitar suplantaciones si usas encabezados para atributos.
Para más información sobre por qué este es un módulo dedicado, consulta https://forum.nginx.org/read.php?2,238523,238523#msg-238523
Directivas
Las siguientes directivas se añaden a tus archivos de configuración de Nginx. Los contextos mencionados a continuación muestran dónde pueden ser añadidos.
shib_request \<uri>|off | Contexto: http, server, location
Predeterminado: off
Activa el módulo de solicitud de autenticación Shibboleth y establece la URI que se pedirá autorización. La URI configurada debe referirse a un bloque de ubicación de Nginx que apunte a tu autorizador FastCGI de Shibboleth.
El estado y los encabezados HTTP de la respuesta resultante de la subsolicitud a la URI configurada serán devueltos al usuario, de acuerdo con la especificación del Autorizador FastCGI. La única advertencia (potencialmente significativa) es que, debido a la forma en que Nginx opera actualmente con respecto a las subsolicitudes (lo que un Autorizador requiere efectivamente), el cuerpo de la solicitud no será reenviado al autorizador, y de manera similar, el cuerpo de la respuesta del autorizador no será devuelto al cliente.
Las URIs configuradas no están restringidas a usar un backend FastCGI para
generar una respuesta, sin embargo. Esto puede ser útil durante pruebas u
otros casos, ya que puedes usar las directivas integradas return y
rewrite de Nginx para producir una respuesta adecuada. Además, este
módulo puede ser utilizado con cualquier autorizador FastCGI, aunque la
operación puede verse afectada por la advertencia anterior.
[!WARNING] La directiva
shib_requestya no requiere la banderashib_authorizer. Esta debe ser eliminada para que Nginx inicie. No se requieren otros cambios.
shib_request_set \<variable> \<value>
Contexto: http, server, location
Predeterminado: none
Establece la variable al value especificado después de que la
solicitud de autenticación se haya completado. El value puede contener
variables de la respuesta de la solicitud de autenticación. Por ejemplo,
$upstream_http_*, $upstream_status, y cualquier otra variable
mencionada en la
documentación del nginx_http_upstream_module.
Esta directiva puede ser utilizada para introducir atributos de Shibboleth en el entorno de la aplicación backend, como $_SERVER para una aplicación PHP FastCGI y es el método recomendado para hacerlo. Consulta la documentación de Configuración para un ejemplo.
shib_request_use_headers on|off | Contexto: http, server, location
Predeterminado: off
[!NOTE] Añadido en v2.0.0.
Copia atributos de la respuesta del autorizador Shibboleth en la
solicitud principal como encabezados, haciéndolos disponibles para
servidores y aplicaciones upstream. Usa esta opción solo si tu
upstream/aplicación no soporta parámetros de servidor a través de
shib_request_set.
Con esta configuración habilitada, los encabezados de respuesta del
autorizador que comienzan con Variable-\* son extraídos, eliminando la
subcadena Variable- del nombre del encabezado, y copiados en la
solicitud principal antes de ser enviados al backend. Por ejemplo, un
encabezado de respuesta del autorizador como
Variable-Commonname: John Smith resultaría en que
Commonname: John Smith se agregue a la solicitud principal, y así se
envíe al backend.
Cuidado con la suplantación - debes asegurarte de que tu aplicación backend esté protegida contra la inyección de encabezados. Consulta el ejemplo de Configuración sobre cómo lograr esto.
Configuración
Para obtener detalles completos sobre cómo configurar el entorno de NGINX/Shibboleth, consulta la documentación en https://github.com/nginx-shib/nginx-http-shibboleth/blob/master/CONFIG.rst.
Un ejemplo de bloque server consiste en lo siguiente:
#FastCGI authorizer for Auth Request module
location = /shibauthorizer {
internal;
include fastcgi_params;
fastcgi_pass unix:/opt/shibboleth/shibauthorizer.sock;
}
#FastCGI responder
location /Shibboleth.sso {
include fastcgi_params;
fastcgi_pass unix:/opt/shibboleth/shibresponder.sock;
}
## Usando la directiva ``shib_request_set``, podemos introducir atributos como
## variables de entorno para la aplicación backend. En este ejemplo, configuramos
## ``fastcgi_param`` pero esto podría ser cualquier tipo de backend de Nginx que
## soporte parámetros (usando la opción *_param apropiada)
#
## Los ``shib_fastcgi_params`` son un conjunto opcional de parámetros predeterminados,
## disponibles en el directorio ``includes/`` de este repositorio.
#
## Elige este tipo de configuración a menos que tu aplicación backend
## no soporte parámetros de servidor o requiera específicamente encabezados.
location /secure-environment-vars {
shib_request /shibauthorizer;
include shib_fastcgi_params;
shib_request_set $shib_commonname $upstream_http_variable_commonname;
shib_request_set $shib_email $upstream_http_variable_email;
fastcgi_param COMMONNAME $shib_commonname;
fastcgi_param EMAIL $shib_email;
fastcgi_pass unix:/path/to/backend.socket;
}
## Una ubicación asegurada. Todas las solicitudes entrantes consultan al
## autorizador FastCGI de Shibboleth.
## ¡Ten cuidado con los problemas de rendimiento y la suplantación!
#
## Elige este tipo de configuración para aplicaciones ``proxy_pass``
## o backends que no soporten parámetros de servidor.
location /secure {
shib_request /shibauthorizer;
shib_request_use_headers on;
# Los atributos de Shibboleth se introducen como encabezados por el FastCGI
# autorizador, por lo que debemos prevenir la suplantación. El
# ``shib_clear_headers`` es un conjunto de directivas de encabezados
# predeterminadas, disponibles en el directorio `includes/` de este repositorio.
include shib_clear_headers;
# Agrega *todos* los atributos que tu aplicación utiliza, incluyendo todas
# las variaciones.
more_clear_input_headers 'displayName' 'mail' 'persistent-id';
# Esta aplicación backend recibirá variables de Shibboleth como encabezados
# de solicitud (del autorizador FastCGI de Shibboleth)
proxy_pass http://localhost:8080;
}
Ten en cuenta que usamos el módulo headers-more-nginx-module para limpiar encabezados de entrada potencialmente peligrosos y evitar la posibilidad de suplantación. El último ejemplo con variables de entorno no es susceptible a la suplantación de encabezados, siempre que el backend lea datos de los parámetros de entorno solo.
Un configuración predeterminada
está disponible para limpiar los encabezados básicos del autorizador
Shibboleth, pero debes asegurarte de escribir tus propias directivas de
limpieza para todos los atributos que tu aplicación utiliza. Ten en cuenta
que algunas aplicaciones intentarán leer un atributo de Shibboleth desde el
entorno y luego volverán a los encabezados, así que revisa el código de tu
aplicación incluso si no estás usando shib_request_use_headers.
Con el uso de shib_request_set, un params predeterminado
está disponible que puedes usar como un include de nginx para asegurar que todas
las variables centrales de Shibboleth se pasen del autorizador FastCGI a la
aplicación. Se incluyen numerosos atributos predeterminados, así que elimina
los que no son requeridos por tu aplicación y agrega atributos de Federación o
IDP que necesites. Este archivo de parámetros predeterminados puede ser reutilizado
para upstreams que no son FastCGI simplemente cambiando las directivas
fastcgi_param a uwsgi_param, scgi_param o similares.
Problemas
- Las subsolicitudes, como la solicitud de autenticación de Shibboleth, no son
procesadas a través de filtros de encabezados. Esto significa que directivas
integradas como
add_headerno funcionarán si están configuradas como parte de un bloque/shibauthorizer. Si necesitas manipular encabezados de subsolicitud, usamore_set_headersdel móduloheaders-more.
Consulta https://forum.nginx.org/read.php?29,257271,257272#msg-257272.
Comportamiento
Este módulo sigue la especificación del Autorizador FastCGI donde sea posible, pero tiene algunas desviaciones notables - con buena razón. El comportamiento es así:
-
Una subsolicitud de autorizador está compuesta por todos los aspectos de la solicitud original, exceptuando el cuerpo de la solicitud ya que Nginx no soporta el almacenamiento en búfer de cuerpos de solicitud. Como el autorizador FastCGI de Shibboleth no considera el cuerpo de la solicitud, esto no es un problema.
-
Si una subsolicitud de autorizador devuelve un estado
200, se permite el acceso.
Si shib_request_use_headers está habilitado, y los encabezados de respuesta
que comienzan con Variable-\* son extraídos, eliminando la subcadena
Variable- del nombre del encabezado, y copiados en la solicitud principal.
Otros encabezados de respuesta del autorizador que no están prefijados con
Variable- y el cuerpo de la respuesta son ignorados. La especificación
FastCGI exige que se incluyan pares nombre-valor Variable-* en el entorno
FastCGI, pero los convertimos en encabezados para que puedan ser usados con
cualquier backend (como proxy_pass) y no restringirnos solo a
aplicaciones FastCGI. Al pasar los datos Variable-* como encabezados en
lugar de como variables de entorno, terminamos siguiendo el comportamiento de
ShibUseHeaders On en mod_shib para Apache, que pasa estos atributos de
usuario como encabezados.
Para pasar atributos como variables de entorno (el equivalente a
ShibUseEnvironment On en mod_shib), los atributos deben ser extraídos
manualmente usando directivas shib_request_set para cada atributo. Esto no
puede (actualmente) hacerse en masa para todos los atributos ya que cada
backend puede aceptar parámetros de manera diferente (fastcgi_param,
uwsgi_param, etc.). Se aceptan solicitudes de extracción para automatizar
este comportamiento.
- Si la subsolicitud de autorizador devuelve cualquier otro estado (incluyendo redirecciones o errores), el estado y los encabezados de respuesta del autorizador son devueltos al cliente.
Esto significa que en 401 Unauthorized o 403 Forbidden, se denegará el
acceso y los encabezados (como WWW-Authenticate) del autorizador serán
pasados al cliente. Todas las demás respuestas del autorizador (como
redirecciones 3xx) son devueltas al cliente, incluyendo estado y
encabezados, permitiendo redirecciones como las que llevan a páginas WAYF y al
respondedor de Shibboleth (Shibboleth.sso) para funcionar correctamente.
La especificación del Autorizador FastCGI exige que el cuerpo de la respuesta
sea devuelto al cliente, pero como Nginx actualmente no soporta el
almacenamiento en búfer de respuestas de subsolicitudes (NGX_HTTP_SUBREQUEST_IN_MEMORY),
el cuerpo de respuesta del autorizador es efectivamente ignorado. Una solución
alternativa es hacer que Nginx sirva una error_page propia, así:
location /secure {
shib_request /shibauthorizer;
error_page 403 /shibboleth-forbidden.html;
...
}
Esto sirve la página de error dada si el autorizador de Shibboleth niega
al usuario el acceso a esta ubicación. Sin error_page especificado,
Nginx servirá sus páginas de error genéricas.
Ten en cuenta que esto no se aplica al respondedor de Shibboleth (típicamente
alojado en Shibboleth.sso) ya que es un respondedor FastCGI y Nginx es
completamente compatible con esto ya que no se utilizan subsolicitudes.
Para más detalles, consulta https://forum.nginx.org/read.php?2,238444,238453.
Si bien este módulo está diseñado específicamente para el autorizador FastCGI de Shibboleth, probablemente funcionará con otros autorizadores, teniendo en cuenta las desviaciones de la especificación mencionadas anteriormente.
Pruebas
Las pruebas se ejecutan automáticamente en GitHub Actions (usando esta configuración) cada vez que se realizan nuevos commits en el repositorio o cuando se abren nuevas solicitudes de extracción. Si algo falla, se te informará y los resultados se reportarán en GitHub.
Las pruebas están escritas utilizando una combinación de un simple script de Bash para la compilación de nuestro módulo con diferentes versiones y configuraciones de Nginx y el Test::Nginx andamiaje de pruebas Perl para pruebas de integración. Consulta el enlace anterior para obtener información sobre cómo extender las pruebas, y también consulta la documentación subyacente de Test::Base sobre aspectos como la función blocks().
Las pruebas de integración se ejecutan automáticamente por CI, pero también se pueden ejecutar manualmente (requiere que Perl y CPAN estén instalados):
cd nginx-http-shibboleth
cpanm --notest --local-lib=$HOME/perl5 Test::Nginx
## nginx debe estar presente en PATH y construido con símbolos de depuración
PERL5LIB=$HOME/perl5/lib/perl5 prove
Ayuda y Soporte
Las solicitudes de soporte para la configuración de Shibboleth y la configuración de Nginx o del servidor web deben dirigirse a la lista de correo de usuarios de la comunidad de Shibboleth. Consulta https://www.shibboleth.net/community/lists/ para más detalles.
Depuración
Debido a la naturaleza compleja de la pila nginx/FastCGI/Shibboleth, depurar problemas de configuración puede ser difícil. Aquí hay algunos puntos clave:
-
Confirma que
nginx-http-shibbolethse haya construido e instalado correctamente dentro de nginx. Puedes verificarlo ejecutandonginx -Vy inspeccionando la salida para--add-module=[ruta]/nginx-http-shibboletho--add-dynamic-module=[ruta]/nginx-http-shibboleth. -
Si usas módulos dinámicos para nginx, confirma que has usado la directiva
load_modulepara cargar este módulo. Tu uso deshib_requesty otras directivas fallará si has olvidado cargar el módulo. -
Si usas una versión de nginx que es diferente a las que probamos o si estás usando otros módulos de terceros, deberías ejecutar el conjunto de pruebas anterior para confirmar la compatibilidad. Si alguna prueba falla, revisa tu configuración o considera actualizar tu versión de nginx.
-
Configuración de Shibboleth: revisa tu
shibboleth2.xmly la configuración asociada para asegurarte de que tus hosts, rutas y atributos se estén liberando correctamente. Una configuración de ejemplo puede ayudarte a identificar "problemas" clave para configurarshibboleth2.xmlpara trabajar con el autorizador FastCGI. -
A nivel de aplicación: dentro de tu código, siempre comienza con la salida de depuración más simple posible (como imprimir el entorno de la solicitud) y trabaja desde allí. Si deseas crear una aplicación básica y autónoma, echa un vistazo a la configuración de Bottle en la wiki.
-
Depurando los internos del módulo: si has revisado cuidadosamente todo lo anterior, también puedes depurar el comportamiento de este módulo en sí. Necesitarás haber compilado nginx con soporte de depuración (a través de
./auto/configure --with-debug ...) y al ejecutar nginx, es más fácil si puedes ejecutarlo en primer plano con el registro de depuración habilitado. Agrega lo siguiente a tunginx.conf:daemon off; error_log stderr debug;y ejecuta nginx. Al iniciar nginx deberías ver líneas que contienen [debug] y a medida que haces solicitudes, el registro en consola continuará. Si esto no sucede, revisa tu configuración de nginx y el proceso de compilación.
Cuando finalmente hagas una solicitud que impacte (o debería invocar) el bloque de ubicación
shib_request, verás líneas como estas en la salida:[debug] 1234#0: shib request handler [debug] 1234#0: shib request set variables [debug] 1234#0: shib request authorizer handler [debug] 1234#0: shib request authorizer allows access [debug] 1234#0: shib request authorizer copied header: "AUTH_TYPE: shibboleth" [debug] 1234#0: shib request authorizer copied header: "REMOTE_USER: [email protected]" ...Si no ves este tipo de líneas que contienen shib request ..., o si ves algunas de las líneas anteriores pero no donde se están copiando encabezados/variables, entonces revisa de nuevo tu configuración de nginx. Si aún no logras avanzar, puedes agregar tus propias líneas de depuración en el código fuente (sigue los ejemplos de este módulo) para determinar eventualmente qué está saliendo mal y cuándo. Si haces esto, no olvides recompilar nginx y/o
nginx-http-shibbolethcada vez que hagas un cambio.
Si crees que has encontrado un error en el código del módulo principal, por favor crea un issue.
También puedes buscar problemas existentes, ya que es probable que alguien más haya encontrado un problema similar antes.
GitHub
Puedes encontrar consejos de configuración adicionales y documentación para este módulo en el repositorio de GitHub para nginx-module-shibboleth.