我有检查值是否存在的函数,在本例中它是 API key 。我想要实现的是,在为每个帐户注册创建新的 api key 之前,如果数据库中已经存在,我想循环我的函数以生成新 key 。 key 是使用以下方法生成的简单字符串:
$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
}
如何有效地运行循环以生成新 key 并消除重复项?请记住,数据库将包含 100 000 多条记录...
最佳答案
执行此操作时需要注意以下几点:
- 确保您对此列有
UNIQUE
约束,这样就不可能添加重复值。您不能在插入之前依赖SELECT COUNT(*) FROM x WHERE key=?
测试,因为它容易受到 race conditions 的攻击。 . - 生成一个足够随机的 API key ,避免发生冲突。使用所有字母(大写和小写)加上数字的 >=20 个字符的随机字符串将有 704,423,425,546,998,022,968,330,264,616,370,176 种可能的形式,因此在天文学上不太可能发生碰撞。如果您的键较短,由于 the pigeonhole principle 等效果,碰撞的可能性会更大和 birthday paradox .
- 万一确实发生了冲突,请让您的代码生成一个新 key 并重试插入。
UNIQUE
约束违规是您可以处理的非常具体的 MySQL 错误代码。如果/当INSERT
失败并进行相应调度时,请检查您的error
值。
通过生成几百万个 key 来测试您的代码,以确保其正常运行。
关于PHP检查数据库表,如果值存在,运行循环生成唯一值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52228486/