nun*_*nos 176 php security random passwords
我想在php中生成一个随机密码.
但是我得到所有'a'并且返回类型是数组类型,我希望它是一个字符串.有关如何更正代码的任何想法?
谢谢.
function randomPassword() {
$alphabet = "abcdefghijklmnopqrstuwxyzABCDEFGHIJKLMNOPQRSTUWXYZ0123456789";
for ($i = 0; $i < 8; $i++) {
$n = rand(0, count($alphabet)-1);
$pass[$i] = $alphabet[$n];
}
return $pass;
}
Run Code Online (Sandbox Code Playgroud)
Nea*_*eal 240
安全警告:
rand()不是加密安全的伪随机数生成器.在其他地方寻找在PHP中生成加密安全的伪随机字符串.
试试这个(使用strlen而不是count,因为count在字符串上总是1):
function randomPassword() {
$alphabet = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890';
$pass = array(); //remember to declare $pass as an array
$alphaLength = strlen($alphabet) - 1; //put the length -1 in cache
for ($i = 0; $i < 8; $i++) {
$n = rand(0, $alphaLength);
$pass[] = $alphabet[$n];
}
return implode($pass); //turn the array into a string
}
Run Code Online (Sandbox Code Playgroud)
演示:http://codepad.org/UL8k4aYK
Sco*_*ski 112
random_int()和random_str()下面给出的.random_int(),请使用random_compat.由于您要生成密码,因此需要确保生成的密码不可预测,并且确保实现中存在此属性的唯一方法是使用加密安全伪随机数生成器(CSPRNG).
对于随机字符串的一般情况,可以放宽对CSPRNG的要求,但是在涉及安全性时则不能.
在PHP中生成密码的简单,安全和正确的答案是使用RandomLib并且不重新发明轮子.该图书馆已经过行业安全专家和我本人的审核.
对于喜欢发明自己的解决方案的开发人员,PHP 7.0.0将提供random_int()此目的.如果你仍然使用PHP 5.x,我们编写了一个PHP 5 polyfill,random_int()这样你就可以在PHP 7发布之前使用新的API.使用我们的random_int()polyfill 可能比编写自己的实现更安全.
使用安全的随机整数生成器,生成安全的随机字符串比派对更容易:
<?php
/**
* Generate a random string, using a cryptographically secure
* pseudorandom number generator (random_int)
*
* For PHP 7, random_int is a PHP core function
* For PHP 5.x, depends on https://github.com/paragonie/random_compat
*
* @param int $length How many characters do we want?
* @param string $keyspace A string of all possible characters
* to select from
* @return string
*/
function random_str(
$length,
$keyspace = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'
) {
$str = '';
$max = mb_strlen($keyspace, '8bit') - 1;
if ($max < 1) {
throw new Exception('$keyspace must be at least two characters long');
}
for ($i = 0; $i < $length; ++$i) {
$str .= $keyspace[random_int(0, $max)];
}
return $str;
}
Run Code Online (Sandbox Code Playgroud)
小智 108
我知道您正在尝试以特定方式生成密码,但您可能也想查看此方法...
$bytes = openssl_random_pseudo_bytes(2);
$pwd = bin2hex($bytes);
Run Code Online (Sandbox Code Playgroud)
它取自php.net网站,它创建的字符串长度是openssl_random_pseudo_bytes函数中的两倍.所以上面会创建一个4个字符长的密码.
简而言之...
$pwd = bin2hex(openssl_random_pseudo_bytes(4));
Run Code Online (Sandbox Code Playgroud)
会创建一个长8个字符的密码.
但请注意,密码只包含数字0-9和小写字母af!
BSQ*_*BSQ 52
2行的微小代码.
演示:http://codepad.org/5rHMHwnH
function rand_string( $length ) {
$chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
return substr(str_shuffle($chars),0,$length);
}
echo rand_string(8);
Run Code Online (Sandbox Code Playgroud)
使用rand_string,您可以定义要创建的字符数.
Pee*_*Haa 37
如果您使用的是PHP7,则可以使用以下random_int()功能:
function generate_password($length = 20){
$chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'.
'0123456789`-=~!@#$%^&*()_+,./<>?;:[]{}\|';
$str = '';
$max = strlen($chars) - 1;
for ($i=0; $i < $length; $i++)
$str .= $chars[random_int(0, $max)];
return $str;
}
Run Code Online (Sandbox Code Playgroud)
老答案如下:
function generate_password($length = 20){
$chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'.
'0123456789`-=~!@#$%^&*()_+,./<>?;:[]{}\|';
$str = '';
$max = strlen($chars) - 1;
for ($i=0; $i < $length; $i++)
$str .= $chars[mt_rand(0, $max)];
return $str;
}
Run Code Online (Sandbox Code Playgroud)
San*_*dra 35
在一行中:
substr(str_shuffle('abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789') , 0 , 10 )
Run Code Online (Sandbox Code Playgroud)
Mad*_*iha 26
最好的选择是ircmaxell的RandomLib库.
用法示例:
$factory = new RandomLib\Factory;
$generator = $factory->getGenerator(new SecurityLib\Strength(SecurityLib\Strength::MEDIUM));
$passwordLength = 8; // Or more
$randomPassword = $generator->generateString($passwordLength);
Run Code Online (Sandbox Code Playgroud)
它产生的字符串这是不是像正常的随机性功能更强烈的随机shuffle()和rand()(这是你一般要像密码,盐和密钥敏感信息).
phi*_*hag 14
你想要的strlen($alphabet),不是count常数alphabet(相当于'alphabet').
但是,rand用于此目的不是合适的随机函数.它的输出很容易预测,因为它隐含在当前时间播种.另外,rand不是加密安全的; 因此,从输出中确定其内部状态相对容易.
相反,读取/dev/urandom以获取加密随机数据.
jet*_*eon 14
我将发布一个答案,因为现有的一些答案很接近但有一个:
这个答案将绕过这个count/strlen问题,因为生成的密码的安全性,至少是恕我直言,超越了你到达那里的方式.我也将假设PHP> 5.3.0.
让我们将问题分解为以下组成部分:
对于第一部分,PHP> 5.3.0提供了该功能openssl_random_pseudo_bytes.请注意,虽然大多数系统使用加密强大的算法,但您必须检查以便我们使用包装器:
/**
* @param int $length
*/
function strong_random_bytes($length)
{
$strong = false; // Flag for whether a strong algorithm was used
$bytes = openssl_random_pseudo_bytes($length, $strong);
if ( ! $strong)
{
// System did not use a cryptographically strong algorithm
throw new Exception('Strong algorithm not available for PRNG.');
}
return $bytes;
}
Run Code Online (Sandbox Code Playgroud)
对于第二部分,我们将使用,base64_encode因为它需要一个字节字符串,并将生成一系列字符,其字母非常接近原始问题中指定的字符.如果我们不介意+,/并且=字符出现在最终字符串中,并且我们希望结果至少有$n字符长,我们可以简单地使用:
base64_encode(strong_random_bytes(intval(ceil($n * 3 / 4))));
Run Code Online (Sandbox Code Playgroud)
这个3/4因素是由于base64编码导致字符串的长度至少比字节字符串大三分之一.结果将是$n4的倍数,否则最多3个字符.由于额外的字符主要是填充字符=,如果我们由于某种原因有一个约束密码是一个确切的长度,那么我们可以将它截断到我们想要的长度.这尤其是因为对于给定的$n密码,所有密码都将以相同数量的密码结束,因此有权访问结果密码的攻击者最多可以猜测2个字符.
为了获得额外的功劳,如果我们想要满足OP问题中的确切规范,那么我们将不得不做更多的工作.我将放弃这里的基本转换方法,并快速而肮脏地进行.由于62条长字母表,两者都需要产生比结果中使用的更多的随机性.
对于结果中的额外字符,我们可以简单地从结果字符串中丢弃它们.如果我们在字节字符串中以8个字节开始,则最多约25%的base64字符将是这些"不合需要"的字符,因此简单地丢弃这些字符会导致字符串不短于OP所需的字符串.然后我们可以简单地截断它以达到确切的长度:
$dirty_pass = base64_encode(strong_random_bytes(8)));
$pass = substr(str_replace(['/', '+', '='], ['', '', ''], $dirty_pass, 0, 8);
Run Code Online (Sandbox Code Playgroud)
如果生成更长的密码,填充字符将=形成较小和较小比例的中间结果,这样您就可以实现更精简的方法,如果排除用于PRNG的熵池是一个问题.
src*_*der 11
base_convert(uniqid('pass', true), 10, 36);
例如. e0m6ngefmj4
编辑
正如我在评论中提到的那样,长度意味着暴力攻击会更好地对抗它然后进行定时攻击,因此担心"随机生成器有多安全"并不是真正相关的.安全性,特别是针对此用例,需要补充可用性,因此上述解决方案实际上足以满足所需的问题.
但是,如果你在搜索安全的随机字符串生成器时偶然发现了这个答案(因为我假设有些人基于响应),对于诸如生成令牌之类的东西,这里是这样的代码生成器的样子:
function base64urlEncode($data) {
return rtrim(strtr(base64_encode($data), '+/', '-_'), '=');
}
function secureId($length = 32) {
if (function_exists('openssl_random_pseudo_bytes')) {
$bytes = openssl_random_pseudo_bytes($length);
return rtrim(strtr(base64_encode($bytes), '+/', '0a'), '=');
}
else { // fallback to system bytes
error_log("Missing support for openssl_random_pseudo_bytes");
$pr_bits = '';
$fp = @fopen('/dev/urandom', 'rb');
if ($fp !== false) {
$pr_bits .= @fread($fp, $length);
@fclose($fp);
}
if (strlen($pr_bits) < $length) {
error_log('unable to read /dev/urandom');
throw new \Exception('unable to read /dev/urandom');
}
return base64urlEncode($pr_bits);
}
}
Run Code Online (Sandbox Code Playgroud)
小智 9
另一个(仅限linux)
function randompassword()
{
$fp = fopen ("/dev/urandom", 'r');
if (!$fp) { die ("Can't access /dev/urandom to get random data. Aborting."); }
$random = fread ($fp, 1024); # 1024 bytes should be enough
fclose ($fp);
return trim (base64_encode ( md5 ($random, true)), "=");
}
Run Code Online (Sandbox Code Playgroud)
更聪明一点:
function strand($length){
if($length > 0)
return chr(rand(33, 126)) . strand($length - 1);
}
Run Code Online (Sandbox Code Playgroud)
检查它在这里.
尝试使用大写字母,小写字母,数字和特殊字符
function generatePassword($_len) {
$_alphaSmall = 'abcdefghijklmnopqrstuvwxyz'; // small letters
$_alphaCaps = strtoupper($_alphaSmall); // CAPITAL LETTERS
$_numerics = '1234567890'; // numerics
$_specialChars = '`~!@#$%^&*()-_=+]}[{;:,<.>/?\'"\|'; // Special Characters
$_container = $_alphaSmall.$_alphaCaps.$_numerics.$_specialChars; // Contains all characters
$password = ''; // will contain the desired pass
for($i = 0; $i < $_len; $i++) { // Loop till the length mentioned
$_rand = rand(0, strlen($_container) - 1); // Get Randomized Length
$password .= substr($_container, $_rand, 1); // returns part of the string [ high tensile strength ;) ]
}
return $password; // Returns the generated Pass
}
Run Code Online (Sandbox Code Playgroud)
让我们说我们需要10位数通过
echo generatePassword(10);
Run Code Online (Sandbox Code Playgroud)
示例输出:
,IZCQ_IV\7
@wlqsfhT(d
1!8 + 1\4 @ UD
小智 6
使用这个简单的代码生成med-strong密码12长度
$password_string = '!@#$%*&abcdefghijklmnpqrstuwxyzABCDEFGHJKLMNPQRSTUWXYZ23456789';
$password = substr(str_shuffle($password_string), 0, 12);
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
319918 次 |
| 最近记录: |