我在Silex中设置了一个防火墙,如下所示:
$this -> register(new SecurityServiceProvider(), array(
'security.firewalls' => array(
'login' => array(
'pattern' => '^/admin/login$'
),
'admin' => array(
'pattern' => '^/admin.*$',
'form' => array(
'login_path' => '/admin/login',
'check_path' => '/admin/security/validate',
'default_target_path' => "/admin",
'always_use_default_target_path' => true
),
'logout' => array(
'logout_path' => '/admin/security/logout'
),
'users' => $app -> share(function () use ($app) {
return new TurtleProvidersUserProvider($app);
})
)
),
'security.access_rules' => array(
array('^/admin.*$', 'ROLE_ADMIN')
)
));
这是因为当我在"管理"区域点击一个页面时,我会被重定向到我的登录页面。然而,我已经开始在我的自定义AuthenticationSuccess处理程序中进行一些授权。我想使用内置的方法determineTargeUrl
在成功时重定向,但它一直重定向到"/"。
经过一些调试,我发现该方法使用的对象中的选项如下:
array (size=5)
'always_use_default_target_path' => boolean false
'default_target_path' => string '/' (length=1)
'login_path' => string '/login' (length=6)
'target_path_parameter' => string '_target_path' (length=12)
'use_referer' => boolean false
很明显,这不是我在防火墙中设置的。我的理解是,这应该与我访问系统时使用的防火墙中的内容相匹配。我使用的URL是'http://localhost/admin"。
那么,我如何使我在防火墙中设置的选项显示在对象中,以便我可以使用determineTargetUrl呢?
非常感谢,Russell
您的问题似乎是登录路由在您的安全区域内。您已将访问规则定义为^/admin.*$
。这意味着任何以/admin
开始的路由都需要ROLE_ADMIN
,包括您的登录路由。要解决此问题,您需要从登录路由中删除安全性。
在管理规则之上添加一个新的访问规则。
'security.access_rules' => array(
array('^/admin/login$', 'IS_AUTHENTICATED_ANONYMOUSLY'),
array('^/admin.*$', 'ROLE_ADMIN')
)
编辑:再读一遍你的问题后,我可能误解了你。听起来你可以成功登录,但在成功登录后会被重定向到错误的地方。这是正确的吗?如果是这样,我将删除这个答案。
这是我的错误。我使用自定义AuthenticationSuccess和AuthenticationFailure处理程序,在声明它们时,我忽略了将任何选项传递给它们:
$app['security.authentication.success_handler.admin'] = $app -> share(function() use ($app) {
return new AuthenticationSuccessHandler($app['security.http_utils'], array(), $app);
});
$app['security.authentication.failure_handler.admin'] = $app -> share(function() use ($app) {
return new AuthenticationFailureHandler($app['kernel'], $app['security.http_utils'], array(), $app);
});
因此,身份验证成功时determineTargetUrl
中使用的选项数组为空,因此具有默认值。
通过向AuthenticationSuccessHandler添加一组选项,它就可以工作了。这是可以的,因为每个自定义处理程序都链接到不同的防火墙。