El truco consiste en tener dos entradas separadas en su firewall, una para el inicio de sesión de formulario y otra para el inicio de sesión de Facebook Pero en mi caso, tengo una sola URL de inicio de sesión donde el usuario puede iniciar sesión usando sus credenciales o hacer clic en una conexión de Facebook para autenticarse a través de la API de Facebook OAuth2 usando el FOSFacebookBundle
. Aquí una muestra de mi archivo security.yml
config para hacer este trabajo:
security:
factories:
- "%kernel.root_dir%/../vendor/bundles/FOS/FacebookBundle/Resources/config/security_factories.xml"
providers:
chain_provider:
providers: [acme.form_provider, acme.facebook_provider]
acme.form_provider:
id: acme.user_provider.form
acme.facebook_provider:
id: acme.user_provider.facebook
firewalls:
dev:
pattern: ^/(_(profiler|wdt)|css|images|js)/
security: false
public:
pattern: ^/
fos_facebook:
app_url: "your_app_url"
server_url: "your_server_url"
login_path: /login
check_path: /login_check/facebook
provider: acme.facebook_provider
form_login:
login_path: /login
check_path: /login_check/form
provider: acme.form_provider
anonymous: true
logout: true
role_hierarchy:
ROLE_SUPER_ADMIN: [ROLE_ADMIN, ROLE_ALLOWED_TO_SWITCH]
Y aquí una muestra de mi archivo routing.yml
que se utiliza para definir rutas de seguridad requeridas para hacer este trabajo:
# This is defined to let the user log in. The controller for
# route display the login form and a facebook connect button
_security_login:
pattern: /login
defaults: { _controller: AcmeAcmeBundle:Main:login }
# This is defined for the form login authentication,
# no controller is associated with it
_security_check_form:
pattern: /login_check/form
# This is defined for facebook login authentication,
# a controller is associated with it but does nothing
_security_check_facebook:
pattern: /login_check/facebook
defaults: { _controller: AcmeAcmeBundle:Main:loginCheckFacebook }
_security_logout:
pattern: /logout
defaults: { _controller: AcmeAcmeBundle:Main:logout }
Utilizando el security.yml
antes, el mecanismo de seguridad verificará si el usuario inició sesión utilizando el formulario antes de que el usuario inicie sesión con Facebook. Esto se debe a que el orden en el que los proveedores se definen en el chain_provider
. En cada solicitud, el FOSFacebookBundle
comprueba si hay una cookie de facebook oauth2, de ser así, intenta cargar a su usuario. Si no puede encontrar la cookie, el proceso de autenticación probará con otro proveedor, si está definido después del proveedor de Facebook.
En su caso, cuando el usuario intenta ir a una url protegida (en access_control), se muestra la página de inicio de sesión de facebook y se autentica, luego se lo redirige a su sitio, se encuentra la cookie y el usuario se autentica con éxito por el FOSFacebookBundle
. Para activar manualmente el proceso de autenticación, coloque un botón de Facebook Connect en su sitio, luego, en javascript, redirige al usuario a otra página de su sitio. De esta forma, la cookie será configurada por el botón de conexión y el FOSFacebookBundle
lo autenticará en la próxima solicitud. Lo que hago es redirigir al usuario a la ruta login_check para facebook en javascript cuando el botón facebook connect ha sido exitoso. De esta forma, el mecanismo de seguridad lo redireccionará donde se indique en la configuración de seguridad.
Espero que esto lo ayude a lograr lo que desea. No haga clic para hacer más preguntas si algo no está claro.
@ Seguimiento # 1
De hecho, no se puede poner bajo el nodo fos_userbundle
public
en la configuración del cortafuegos, ya que no es una opción válida.La cadena fos_userbundle
se utiliza para hacer referencia a la clase UserProvider FOSUserBundle
. Nunca utilicé este paquete, pero al leer la documentación, debe usar form_login
. Puede consultar la documentación de FOSUserBundle
en Step #5 y más abajo. El error que menciona es extraño porque le dice que el cortafuegos no maneja el login_path
, pero es el caso, ya que el cortafuegos hace coincidir cualquier cosa que comience con un /
(^/
). No estoy seguro de qué está yendo mal pero vas en la dirección correcta. Use form_login
y trate de verificar por qué no funciona desde allí.
Saludos,
Matt
he añadido un seguimiento de mi respuesta. – Matt