【问题标题】:Checking time was within past 24 hours in PHP检查时间在 PHP 中的过去 24 小时内
【发布时间】:2011-07-13 10:02:19
【问题描述】:

我开发了一个推荐系统,登录的会员可以将推荐发送给那里的家人/朋友,以推荐他们注册。

一切正常,但昨天我决定限制某人在 24 小时内可以发送的最大推荐。我将其限制为每天最多 3 次推荐。

我在下面发布了一些我似乎遇到问题的代码。我遇到的问题是,无论看起来如何,我都会收到一条错误消息,说我已经达到了今天的最大推荐次数。我不确定我在代码中做错了什么。

// referral query
$referral_limit = mysql_query("SELECT 'created_on' FROM 'user_referrals'
WHERE `referrer_uid` = $referrer_uid ") or die(mysql_error());

if(mysql_num_rows($referral_limit) > 0){
    while($row = mysql_fetch_assoc($referral_limit)){

            $db_time = $row['created_on'];

            if((time() - $db_time) > 86400){
                // is within 24 hours and has reached maximum daily referral allowance
                $error[] = "You have reached the maximum referrals for today.";
            }
    }
}

我确实尝试过回显 $db_time,当我执行所有操作时,我得到的只是 created_on 的字段名称,而不是在这种情况下应该显示时间戳的实际值。数据库中的 created_on 字段包含进行推荐的时间戳,我会检查它以确保推荐用户在过去 24 小时内没有进行推荐。

您还会注意到,我没有添加将其限制为每天 3 次的额外位,但我不想添加该位,直到我可以先解决此问题。

数据库表如下所示:

CREATE TABLE IF NOT EXISTS `user_referrals` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`referrer_uid` int(11) NOT NULL,
`recipient_username` varchar(15) NOT NULL,
`referrer_email` varchar(254) DEFAULT NULL,
`referred_id` char(32) NOT NULL,
`referred_email` varchar(254) NOT NULL,
`status` char(9) NOT NULL,
`created_on` int(11) NOT NULL,
`updated_on` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `referred_id` (`referred_id`),
KEY `referrer_uid` (`referrer_uid`)
) ENGINE=InnoDB  DEFAULT CHARSET=utf8 AUTO_INCREMENT=72 ;

编辑

这是经过一些帮助后我的代码。它仍然显示在过去 24 小时内进行了推荐,即使没有推荐。

我认为我做错了错误检查。

$referral_limit = mysql_query("
        SELECT COUNT(*)
        FROM `user_referrals`
        WHERE `referrer_uid` = $referrer_uid
        AND `created_on` > UNIX_TIMESTAMP(DATE_SUB(NOW(), INTERVAL 1 DAY))") or die(mysql_error());

if($referral_limit > 0) {
    $error[] = "You have reached the maximum referrals for today.";
}

【问题讨论】:

  • created_onupdated_on 可以是 date 而不是 int
  • 嗨,我将时间戳存储为 int,因为我更喜欢使用 php time() 并在 php 代码中进行转换等。

标签: php mysql datetime time referrals


【解决方案1】:

当您也可以在 MySQL 中过滤时,不要在 PHP 中过滤完整的 MySQL 结果集。在您的代码示例中,您可能从 MySQL 获取数千行,只是为了通过您的过滤循环运行它们。这是有史以来最难的性能杀手。而是使用更好的 SQL 语句:

SELECT COUNT(*) FROM 'referrals' WHERE `referrer_uid`=? AND created_on > UNIX_TIMESTAMP(DATE_SUB(NOW(), INTERVAL 1 DAY))

此语句仅返回给定引用者在过去 24 小时内的引用计数 (!)。

此外,您不应该像WHERE name=$name 那样将变量直接插入 MySQL,这会使您的应用程序面临无数 SQL 注入攻击。如果你不知道什么是sql注入,现在就去学习吧。

【讨论】:

  • 查询受到 sql 注入等保护,只是未显示完整代码。此外,存储 php unix 时间戳的字段是 int 字段,因为我不熟悉 mysql 日期/时间函数,而且它们不将它们存储为我更喜欢的 unix 时间戳。
  • 嗨,Steffen,我必须退出,但稍后会尝试您的代码并投票等。非常感谢您的回复和时间。
  • 我已经编辑了我的代码,但不确定我如何检查过去 24 小时内是否进行了推荐,因为我不熟悉这些 mysql 功能。我已经尝试过,但似乎无法让它工作。如果你能给我一个例子,我将如何检查是否在过去 24 小时内进行了推荐,是否有可能?出于某种原因,查询似乎工作正常,但我不知道如何使用我拥有的代码检查过去 24 小时内是否进行了推荐。谢谢
  • 您好 PHPLover,恐怕我不明白您的问题?查询返回过去 24 小时内来自给定推荐人的推荐人计数。如果您不熟悉使用的 MySQL 函数,请查看dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html。关于您当前的代码,您必须删除 SQL 语句中 created_on 周围的引号。使用引号,MySQL 不将其用作列名,而仅用作字符串。
  • 也许这就是它不起作用的原因,虽然你说它返回过去 24 小时内的推荐计数,这是否意味着我只需要检查以确保计数不大于 0 ?我的意思是如果返回的计数结果大于 0,则在过去 24 小时内进行了推荐。谢谢
【解决方案2】:

您也可以使用 MySQL 来计算:

$referral_limit = mysql_query("SELECT COUNT(*)
                               FROM referrals
                               WHERE referrer_uid = $referrer_uid
                               AND created_on >= NOW() - INTERVAL 1 DAY
                              ") or die(mysql_error());

假设created_ondatetimetimestamp。为什么声明为INT

【讨论】:

  • 嗨,我回复了上面两个关于使用 INT 而不是 datetime 的 cmets。谢谢
  • @PHPLOVER:请参阅 Steffen 的答案,其中检查了您的 int 数据类型。
  • 感谢 ypercube,我必须退出,但稍后会检查 Steffen 的回答等。感谢大家一如既往的感谢。
  • @PHPLOVER:用CURRENT_TIMESTAMP >= FROM_UNIXTIME(created_on) - INTERVAL 1 DAY试试这个查询
【解决方案3】:

不要在您选择的字段名周围加上单引号,因为这将被解释为要返回的字符串。例如。你需要

SELECT created_on ...

(除非您的代码中确实有反引号,并且示例中包含的代码不正确)。

【讨论】:

    【解决方案4】:

    您的查询应该是

    $referral_limit = mysql_query("SELECT `created_on` FROM `referrals`
     WHERE `referrer_uid` = $referrer_uid ") or die(mysql_error());
    

    这是 created_on 的反引号,而不是引号。如果使用引号,则该字段变为字符串,类似于返回 1 的SELECT 1 FROM table

    【讨论】:

    • 嗨,我注意到了我的问题,现在它可以正确回显。我遇到的问题是,即使您只是推荐了测试,而且在过去 24 小时内,它仍然允许我进行多个推荐。就目前的代码而言,它不应该允许我进行多个推荐,因为我刚刚进行了推荐,因此它应该返回错误消息,说明我已经在过去 24 小时内进行了推荐。 :/ 谢谢
    • @PHPLOVER:我认为你使用的逻辑是错误的。不应该是((time() - $db_time) < 86400),即如果创建的推荐少于 24 小时,那就是错误???
    • 嗨,我想要它,所以它在不到 24 小时前已经创建了推荐,然后返回错误。我似乎把自己搞糊涂了。我已经回复了 Steffan 的帖子,因为他的查询有效,但验证部分有一个小问题。谢谢
    【解决方案5】:

    created_on int(11) 非空, updated_on int(11) 默认为空,

    这些肯定应该是日期时间字段吗?

    【讨论】:

    • 嗨,我回复了上面两个关于使用 INT 而不是 datetime 的 cmets。谢谢
    【解决方案6】:

    更改您的查询

    $referral_limit = mysql_query("SELECT 'created_on' FROM 'user_referrals'WHERE `referrer_uid` = $referrer_uid ") or die(mysql_error());
    

    $referral_limit = mysql_query("SELECT `created_on` FROM `user_referrals` WHERE `referrer_uid` = $referrer_uid ") or die(mysql_error());
    

    【讨论】:

      猜你喜欢
      • 2011-03-15
      • 2020-01-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-05-29
      • 1970-01-01
      • 1970-01-01
      • 2013-04-11
      相关资源
      最近更新 更多