支持指定長度、字符集類型 (數字/大寫/小寫/混合/自定義)、自動去除易混淆字符。
<?php
/**
* 生成隨機字符串
* @param int $len 長度
* @param int $type 字符集類型: 0=字母+數字, 1=純數字, 2=大寫字母, 3=小寫字母, 4=自定義(含特殊字符)
* @param string $addChars 額外允許的字符
* @return string
*/
function rand_string(int $len = 32, int $type = 0, string $addChars = ''): string {
// 默認字符池 (已去除 0/O/o/I/l/1 等易混淆字符)
$pools = [
0 => 'ABCDEFGHJKMNPQRSTUVWXYZabcdefghjkmnpqrstuvwxyz23456789',
1 => '23456789',
2 => 'ABCDEFGHJKMNPQRSTUVWXYZ',
3 => 'abcdefghjkmnpqrstuvwxyz',
4 => '', // 完全自定義
];
if ($type === 4) {
$chars = $addChars;
} else {
$chars = ($pools[$type] ?? $pools[0]) . $addChars;
}
if (empty($chars)) {
throw new InvalidArgumentException('字符池為空');
}
// 長度過長時擴展字符池避免重複過多
if ($len > 10 && $type !== 1) {
$chars = str_repeat($chars, ceil($len / strlen($chars)));
}
// 打亂並截取
$chars = str_shuffle($chars);
return substr($chars, 0, $len);
}
// 使用示例
echo rand_string(32) . "\n"; // 默認混合 32 位
echo rand_string(6, 1) . "\n"; // 6 位純數字 (驗證碼)
echo rand_string(16, 2) . "\n"; // 16 位大寫 (兌換碼)
echo rand_string(24, 0, '@#$%') . "\n"; // 含特殊字符的密碼
?>
生成類似 A|b|3|Z|... 格式,增加采集解析難度。
<?php
/**
* 生成帶隨機分隔符的字符串
* @param int $variation 長度浮動範圍
* @return string
*/
function generateWeirdStr(int $variation = 10): string {
$table = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
$len = random_int(30, 30 + $variation); // 30-40 位
$parts = [];
for ($i = 0; $i < $len; $i++) {
$parts[] = $table[random_int(0, strlen($table) - 1)];
}
// 隨機選擇分隔符
$separators = ['|', '-', '_', '.', ':', ';', '~'];
$sep = $separators[array_rand($separators)];
return implode($sep, $parts);
}
echo generateWeirdStr(15) . "\n";
// 輸出示例: K|7|m|P|2|x|... (長度 30-45,隨機分隔符)
?>
| 函數 | 安全性 | 適用場景 |
|---|---|---|
| rand() / mt_rand() | ❌ 偽隨機,可預測 | 非安全場景:測試數據、遊戲邏輯、顯示用隨機 |
| random_int() / random_bytes() | ✅ CSPRNG (密碼學安全) | Token、密碼、Session ID、加密金鑰、驗證碼 |
| openssl_random_pseudo_bytes() | ✅ CSPRNG | PHP 7 前的替代方案 |
建議:所有**安全相關**隨機字符串**必須**使用 random_int() 或 random_bytes()。上述方法一、二已修正使用 random_int()。
generateWeirdStr() 產生的干擾字符,定期變換分隔符與長度,破壞采集器固定 XPath/正則rand_string(32, 0) 生成不可預測的請求唯一標識rand_string(12, 2, '!@#$') 生成高強度短碼rand_string(16, 0) . '_' . time()bin2hex(random_bytes(16)) (32 位十六進制)str_shuffle 會分配大量臨時字符串。可預先生成大字符池字符串,用 random_bytes 直接取字節索引:<?php
function fastRandomString(int $len, string $pool): string {
$poolLen = strlen($pool);
$bytes = random_bytes($len);
$result = '';
for ($i = 0; $i < $len; $i++) {
$result .= $pool[$bytes[$i] % $poolLen];
}
return $result;
}
?>