php,通过电子邮件激活注册。如何最小化数据库搜索成本

时间:2012-06-02 12:12:18

标签: php email registration

这个过程非常简单。

用户填写要注册的字段后,mysql数据库表中的一列(即“activation_key”)会保留一个随机生成的长字符串,另一列即activated保存值为0.

激活电子邮件将发送到注册人的电子邮件,其中包含包含activation_key列随机密钥值的激活链接。点击链接后,网址会在数据库中搜索包含长字符串activation_key'的{​​{1}}列。如果有任何此类值.,则'activation_key`为设置为空白,“激活”列设置为1。

当生成激活密钥字符串时,将进行搜索以查看正在生成的密钥是否已经存在,如果它确实存在,则生成另一个随机值以获得唯一的密钥。

因此,当一些潜在会员的注册待定时,实际上对表中的行执行类似的字符串搜索。

到目前为止,一切正常。

但是,只要认为新成员获得了之前为完成注册的其他成员生成的激活字符串。

如果已经注册的会员有任何机会点击他/她以前的激活链接 电子邮件,那么即使他/她没有完成注册,其他新成员也会完成他/她的注册。

所以我决定不将'activation_key'表设置为空白,因此对所有已经或将要成员进行类似的字符串搜索。

没关系。但是,如果用户数量很大,即超过1个lac,则发送激活电子邮件的注册过程将花费很多时间。

1)是否有其他方法可以最小化数据库浏览成本?

2)在这种情况下像facebook这样的大型网站会采取什么政策?

3 个答案:

答案 0 :(得分:2)

两次生成相同激活密钥的可能性非常小。但解决方案是在电子邮件中发送激活密钥用户名,并针对两者检查数据库。

因此,当发送激活电子邮件时,它包含指向

的链接
/activate.php?activation_key=key&username=name

而不仅仅是activation_key。当检查密钥是否真实时,你可以

WHERE activation_key = key AND username = name;

在mysql查询中。

这样,您可以保护系统,以便正确激活用户所需的用户名和密钥。

为确保更安全,您可以在UNIQUE列上创建activation_key索引。当脚本尝试使用已存在的密钥将生成的密钥添加到用户的行时,查询执行将失败,因为该列设置为唯一。然后,您需要修改脚本以尝试生成密钥,直到它成功存储在数据库中。 请确保不要让它无限循环。

无限循环保护

$count = 0;
while ( $errno === 0 )
{
    // mySQL query here
    $errno = mysql_errno();

    $count++;

    if ( $count >= 5 )
            $errno = -1;
}

if ( $errno === -1 )
    echo "Sorry, the script was unable to generate the token for your activation.";

此循环将运行您放置的查询(将激活令牌添加到数据库),直到查询执行而没有错误。每次执行$count都会增加,如果达到限制(示例中为5),它将强制循环结束(将$errno设置为非零但不是真正的mySQL错误值) ,然后向用户显示错误消息。

答案 1 :(得分:0)

将新注册和未激活帐户的数据存储在单独的表格中。

由于您可能不需要更多关于非活动用户的基本信息,因此您可以保留不受欢迎的数据,例如:其中的个人资料设置。

发送激活密钥后,请在此表中查看包含相应密钥的条目。如果找到,则将日期转移到真实用户表,并从等待激活的用户中删除表中的条目。

通过这种方式,您可以: a)作为激活的用户节省空间不再需要密钥 b)更快地了解尚未激活的用户。

在我看来,您还应该将此与cron一起删除尚未激活3天左右的用户; - )

答案 2 :(得分:0)

在激活链接中包含用户ID以及可能的电子邮件地址或用户名。可能的优势:

  • 您可以对用户ID进行整数搜索
  • 您无需担心重复的激活链接
  • 您无需索引activation_key字段,因为您无论如何都不会搜索它
  • 当包含电子邮件(或用户名)时,没有人能够“尝试”所有用户ID以激活那些具有activation_key副本的用户ID
  • 强制执行activation_keys以激活所有用户将非常困难或不可能。
  • 您不必担心activation_key上的数据争用。

重要提示:不要只使用电子邮件地址和简短的activation_key。确保几乎不可能强制使用某个电子邮件地址的激活密钥。