关于cookie和重定向的Drupal模块开发问题

时间:2009-09-22 00:58:39

标签: api drupal cookies

请帮忙吗?我希望开发一个模块,用PHP做一些非常简单的事情。我受到Drupal API的挑战。我使用的是版本6.

目标:

1)确定用户是否正在查看特定节点(角色无关紧要) 2)如果是,请检查是否设置了cookie   a)如果设置了cookie,则不执行任何操作   b)如果未设置cookie,则设置cookie,然后将用户重定向到另一个节点

就是这样!

我已经创建了一个模块并安装了它,没有错误但它也什么也没做。没有设置cookie。我不确定Drupal系统是如何重定向请求的,因此请提供有用的洞察力。非常感谢你!

<?php
//$Id: offer_survey.module,v 1.0 2009/09/21 11:31:55 blah Exp $
function offer_survey_init() {
  global $base_url;

  $offer_survey = true;
  $cookie_name = 'survey_offered';

  if ($node->nid == 651) {
    if ($_COOKIE[$cookie_name]) {
      // do nothing
    } else {
      setcookie($cookie_name,1,time() + (86400 * 365));
      //then do the redirect an internal webform URL
    }
  }
}

修订版(最新)

<?php
//$Id: offer_survey.module,v 1.0 2009/09/21 11:31:55 durz Exp $
function offer_survey_init() {
  global $base_url;

  $offer_survey = true;
  $cookie_name = 'survey_offered';

  if (arg(0) === "testing") {   // the path of the page
   if (!$_COOKIE[$cookie_name]) {
   setcookie($cookie_name,1,time() + (86400 * 365));
   drupal_goto('new-destination'); // the path to be redirected to
 } 
  } 
}

4 个答案:

答案 0 :(得分:2)

有一些不同的方法可以解决这个问题。

一种选择是使用像jeremy建议的hook_nodeapi。这样做就可以将正在加载/查看的节点作为$ node变量使用。另一个选项是在你的hook_init中查看$ _GET,然后查看用户是否正在请求相关节点。 Hook_nodeapi可能是最简单的方式。

你可以像Jeremy所说的那样保存用户对象的数据,但这只有在用户登录时才有可能,因为用户对象将是匿名用户,对于所有未登录的用户都是相同的。在这种情况下,使用cookie可能是一种选择。但是,您必须小心,因为您必须创建每个站点唯一的cookie名称。否则,如果该模块安装在多个站点上,用户在访问其中一个站点后将无法进行调查。

也在您的代码中而不是:

if ($_COOKIE[$cookie_name]) {
  // do nothing
} else {
  setcookie($cookie_name,1,time() + (86400 * 365));
  //then do the redirect an internal webform URL
}

你应该改用! (不)运营商:

if (!$_COOKIE[$cookie_name]) {
  setcookie($cookie_name,1,time() + (86400 * 365));
  //then do the redirect an internal webform URL
}

答案 1 :(得分:1)

您的模块是否名为offer_survey?

是否开启了?

您的代码看起来无法正常工作,因为它使用了未定义的$ node变量。

我认为使用hook_nodeapi op = load

可能会有更好的运气

一旦对这些内容进行了排序,您可能会发现drupal_goto对重定向很有用,您可以使用user_save来获取持久数据,而不是直接使用set cookie。

答案 2 :(得分:0)

这是工作代码。请注意,必须使用arg(1)作为if()语句以及节点id(nid),而不是使用不起作用的hook_nodeapi。

还有必要设置cookie_domain,这是一个drupal global。

<?php
//$Id: offer_survey.module,v 1.0 2009/09/21 11:31:55 Stoob Exp $
function offer_survey_init() {
  global $base_url;
  global $cookie_domain;

  $offer_survey = true;
  $cookie_name = 'survey_offered';

  if (arg(1) == 2) {   // the number of the node (nid) of the page
    if (!isset($_COOKIE[$cookie_name])) {
      setcookie($cookie_name,1,time() + (86400 * 365),null,$cookie_domain); //lasts a year
      drupal_goto('new/destination'); // the path to be redirected to
    } 
  } 
}

答案 3 :(得分:0)

除非您的缓存已关闭,否则hook_init()仅在未缓存的请求上运行。一旦缓存启动,您的匿名用户将无法获得此cookie。

你需要将它放在hook_boot()中但是你不能使用drupal_goto,因为当_boot()运行时,尚未加载。但是没关系,您可以直接使用header()来设置Location重定向标头。

在重定向后停止执行是一个好主意(尽管你可能会丢失会话信息,如果你不让drupal做一些清理工作,请查看drupal_goto如果你真的想要这样做的话)。

<?php
//$Id: offer_survey.module,v 1.1 2010/10/21 11:31:55 tmcclure Exp $
function offer_survey_boot() {
  global $base_url;
  global $cookie_domain;

  $offer_survey = true;
  $cookie_name = 'survey_offered';

  if (arg(1) == 2) {   // the number of the node (nid) of the page
    if (!isset($_COOKIE[$cookie_name])) {
      setcookie($cookie_name,1,time() + (86400 * 365),null,$cookie_domain); //lasts a year
      header('Location: '.$base_url.'/new/destination',TRUE,302); // the path to be redirected to
      exit();
    } 
  } 
}