在我的安装中,用户使用Shibboleth [1]登录,但是我设置为在“用户已登录”事件中执行的规则[2]未执行。
另一方面,当我以管理员身份以正常的Drupal方式登录时,规则就会执行。
这是否意味着根本不处理外部登录事件?
有没有办法克服这个问题?
答案 0 :(得分:1)
这似乎是a bug of the Shibboleth module,因此登录'event'确实没有被它引发(在Drupal术语中,它不会使用hook_user()
调用$op = 'login'
)。
Looking at the Shibboleth code,登录似乎发生在hook_init()
实施中:
/**
* Create a new user based on informations from the Shibboleth handler if it's necessary or log in.
*/
function shib_auth_init() {
global $user;
$unameVar = variable_get('shib_auth_username_variable', 'REMOTE_USER');
$umailVar = variable_get('shib_auth_username_email', 'HTTP_SHIB_MAIL');
// If
// - The user isn't logged in
// - There is Shibboleth authentication in the background
// - The settings are fine and there has been a valid username setted up
// - The settings are fine and there has been a valid user email address setted up
if (!$user->uid && $_SERVER['HTTP_SHIB_IDENTITY_PROVIDER']) {
if ($_SERVER[$unameVar] && $_SERVER[$umailVar]) {
user_external_login_register($_SERVER[$unameVar], "shib_auth");
}
else {
drupal_set_message(t("Username or e-mail address is missing. Maybe the Shibboleth configuration is not perfect."),"error");
}
}
if ($user->uid && $_SERVER['HTTP_SHIB_IDENTITY_PROVIDER']) {
$account = user_save($user,array('mail' => $_SERVER[$umailVar]));
// Terminate if an error occured during user_save().
if (!$account) {
drupal_set_message(t("Error saving user account."), 'error');
return;
}
$user = $account;
}
} // function shib_auth_init()
因此,您需要修补此问题,并确保调用user_module_invoke()
。执行此操作的标准方法是在成功登录后调用user_authenticate_finalize()
(然后将调用user_module_invoke()
),因此您需要在user_external_login_register()
调用后添加:
[...]
if ($_SERVER[$unameVar] && $_SERVER[$umailVar]) {
user_external_login_register($_SERVER[$unameVar], "shib_auth");
// Do we have a logged in user now?
if ($user->uid) {
// Yes, ensure watchdog logging and proper invocation of hook_user
// NOTE: We pass an empty array, as no form submit was involved here,
// but we could also pass an array with 'unameVar' and 'umailVar',
// as they would be the closest substitute.
user_authenticate_finalize(array());
}
}
[...]
注意:未经测试的代码,谨防拼写错误和其他愚蠢的疏忽;)
如果您最终这样做,您可能希望将其作为补丁提交到上面链接的错误报告中。 (只有当它有效时,显然;)
答案 1 :(得分:0)
在这些情况下,Drupal加载模块的顺序非常重要。您需要设置规则,以便在验证模块之后加载规则。例如,使用ldap_integration
mysql> UPDATE system SET weight=20 WHERE name="rules";
mysql> UPDATE system SET weight=20 WHERE name="rules_forms";
mysql> UPDATE system SET weight=0 WHERE name="ldapauth";
“20”是一个任意数字,大于您的身份验证模块。
答案 2 :(得分:0)
Drupal运行hooks
,意味着模块有机会运行一段代码。例如。在登录时调用hook_user。
很多时候,模块会在这样的钩子中调用drupal_goto()
。这将严重打破。 Drupal_goto会杀死所有内容,发送一个redirect-header,然后死掉应用程序。没有其他钩子会被运行。
你可以通过安装devel模块并切换设置“show redirects”来找到任何“非法”goto,你会看到,例如, sibbletooth调用了一个不应该有的重定向。