如何在Drupal中正确使用user_access($ string,$ account)?

时间:2012-01-11 15:17:07

标签: drupal drupal-7 url-routing

我想限制使用某些网址。我们说node/addnode/7(只是随机例子)。我认为最好的方法是使用user_access函数。

但是,正如我们习惯的那样,Drupal文档并没有多大帮助。当我只使用该函数时,我收到函数已被使用的消息。所以我最好的猜测是在我的自定义模块的自定义函数中使用这个现有函数和我自己的参数 但是这样我需要在加载之前抓住页面。或者我在这里错过了什么?

修改
我已经设置了这个

global $user;
$items['node/add/%']['access callback'] = array('_mymodule_node_access');
$items['node/add/%']['access arguments'] = array(0,2, $user);

但由于某种原因,Drupal没有拿到所有类型的%卡。它只适用于一种类型(脚本)。其他术语如页面或fiche都没有被提取...... %是一个Drupal通配符吗?

修改
我刚刚发现数据库中已有一些路径。我该如何覆盖它们?我需要的是一个选择器,它可以选择所有四种内容类型(fiche,page,script和news-item)。

enter image description here

1 个答案:

答案 0 :(得分:2)

为路径定义特定访问函数的方法是在access callback中为路径的菜单项设置hook_menu()。对于现有路径,这略有不同,因为您需要实施hook_menu_alter()来修改该路径的现有access callback

function mymodule_menu_alter(&$items) {
  $items['node/add']['access callback'] = 'mymodule_node_add_access_callback';
}

function mymodule_node_add_access_callback() {
  // return TRUE to allow access, FALSE to deny
}

当我们讨论节点页面时,这会更有趣,因为它们的菜单项是使用通配符node/%定义的。这意味着使用hook_menu_alter()只能更改所有节点的访问回调。

幸运的是,Drupal有一个hook_node_access钩子来救援:

function mymodule_node_access($node, $op, $account) {
  $restricted_nids = array(7, 10, 12);

  if (in_array($node->nid, $restricted_nids) && $op == 'view') {
    if ($some_condition_is_true) {
      return NODE_ACCESS_ALLOW;
    }

    return NODE_ACCESS_DENY;
  }

  return NODE_ACCESS_IGNORE;
}

希望有所帮助

修改

如果这一切看起来有点麻烦你可能会对安装Path Access module感到高兴,我认为它具有你所追求的功能。

另一个编辑

认为在这种情况下覆盖通配符不起作用的原因是因为节点模块明确定义了每个节点类型的路径,例如: node/add/pagenode/add/article等。因为Drupal会在通配符匹配(node/add/page)上进行完全匹配(node/add/%),所以您实际上会覆盖错误的菜单项。< / p>

尝试在hook_menu_alter()函数中明确指定路径(请注意access callback应该是字符串而不是您当前拥有的数组):

$items['node/add/page']['access callback'] = '_mymodule_node_access';
$items['node/add/page']['access arguments'] = array(0,2, $user);

还值得注意的是,您传递的$user对象将始终是已清除Drupal缓存的登录用户的用户对象(因为缓存时会重建菜单项)被重建)。如果您想要传递当前登录用户(即访问该页面时登录的用户),这完全是另一回事......我建议再问一个问题吧因为它可能是一个棘手的bugger,你想从这里的人那里获得尽可能多的输入。