Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/257.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
PHP检查数据库表,若值存在,则运行循环以生成唯一值_Php_Mysql - Fatal编程技术网

PHP检查数据库表,若值存在,则运行循环以生成唯一值

PHP检查数据库表,若值存在,则运行循环以生成唯一值,php,mysql,Php,Mysql,我有一个检查值是否存在的函数,在本例中它是API键。我试图实现的是,在为每个帐户注册创建新的api密钥之前,我希望循环我的函数以生成新密钥(如果数据库中已经存在)。键是使用以下命令生成的简单字符串: $apiKey = bin2hex(random_bytes(16)); 我的职能: function apiCheckKey($apiKey) { global $conn; $sql = "SELECT * FROM `api` WHERE `key` = '".$apiKey

我有一个检查值是否存在的函数,在本例中它是API键。我试图实现的是,在为每个帐户注册创建新的api密钥之前,我希望循环我的函数以生成新密钥(如果数据库中已经存在)。键是使用以下命令生成的简单字符串:

$apiKey = bin2hex(random_bytes(16));
我的职能:

function apiCheckKey($apiKey) {
    global $conn;
    $sql = "SELECT * FROM `api` WHERE `key` = '".$apiKey."'";
    $result = mysqli_query($conn, $sql);

    if (mysqli_num_rows($result)) {
        return true;
    } else {
        return false;
    }
}
我的支票:

if(!apiCheckKey($apiKey)) {
     // loop
}

如何高效地运行循环以生成新密钥并消除重复项?请记住,数据库将包含100000多条记录…

执行此操作时,请记住以下几点:

  • 确保此列上有
    唯一的
    约束,因此无法添加重复值。在插入之前,不能依赖于
    从x选择COUNT(*),其中key=?
    测试,因为这容易受到攻击
  • 生成一个足够随机的API密钥,以避免冲突。使用所有字母(大写和小写)加上数字的>=20个字符的随机字符串将有7044234255469980229683830264616370176种可能的形式,因此从天文角度来看,碰撞不太可能发生。如果关键帧较短,则由于和等效果,碰撞的可能性会大得多
  • 在不太可能发生冲突的情况下,让代码生成一个新密钥,然后重试插入。
    UNIQUE
    约束冲突是您可以处理的非常特定的MySQL错误代码。如果插入失败,请检查您的
    错误
    值,并相应地发送

  • 通过生成几百万个密钥来测试代码,以确保其正常运行。

    警告:使用
    mysqli
    时,您应该使用和将用户数据添加到查询中。不要使用字符串插值或串联来完成此操作,因为您已经创建了严重的错误。切勿将
    $\u POST
    $\u GET
    或任何用户数据直接放入查询中,如果有人试图利用您的错误,这可能会非常有害。注意:
    mysqli
    的面向对象界面明显不那么冗长,使代码更易于阅读和审核,并且不容易与过时的
    mysql\u查询
    接口混淆。在你对程序性风格投入太多之前,值得换一种。示例:
    $db=new mysqli(…)
    $db->prepare(“…”)
    过程接口是PHP 4时代的产物,当时引入了
    mysqli
    API,不应在新代码中使用。谢谢你的建议,我会的,但如何在我现有的情况下找到解决方案?谢谢你的意见。如果我使用bin2hex(随机字节(16))生成字符串,您认为如何?它返回32个字符串,如0C86B1508F236945534705C0661F59A9。也许这对API密钥来说不是个坏主意?任何“加密安全”的东西,比如
    random_bytes
    ,都应该这样做,但请记住,只有16个十六进制值,而不是62个字母,因此密钥空间明显更小,冲突的可能性更大。您可以使用
    base64\u encode
    生成64个可能的值,然后用任意字母替换
    /
    +
    ,以避免密钥中出现异常垃圾。谢谢!你帮了很多忙。