我正在使用BasePage.GeneratePassword(6,10)为用户生成unqiue密码。 但我注意到有时(我有150个用户中的5个)生成了相同的密码,我出于某种目的将其用作unqiueId。
这个功能有多可靠?
我没有设置任何其他属性,例如'numberOfNonAlphanumericCharacters'。
任何指导都会有很大的帮助吗?
由于 Harshit
答案 0 :(得分:1)
它使用RNGCryptoServiceProvider
类来获取“随机”字节序列,然后用于生成密码。类似于以下内容
public static string GeneratePassword(int length, int numberOfNonAlphanumericCharacters)
{
string str;
int num;
char[] punctuations= @"!@@$%^^*()_-+=[{]};:>|./?".ToCharArray();
// removed checks for brevity //
while(true)
{
byte[] data = new byte[length];
char[] chArray = new char[length];
int num2 = 0;
new RNGCryptoServiceProvider().GetBytes(data);
for (int i = 0; i < length; i++)
{
int num4 = data[i] % 0x57;
if (num4 < 10)
{
// generate characters 0 -9
chArray[i] = (char) (0x30 + num4);
}
else if (num4 < 0x24)
{
// generate characters A-Z
chArray[i] = (char) ((0x41 + num4) - 10);
}
else if (num4 < 0x3e)
{
// generate characters a-z
chArray[i] = (char) ((0x61 + num4) - 0x24);
}
else
{
// get a non alphanumeric character from the punctuations array
chArray[i] = punctuations[num4 - 0x3e];
num2++;
}
}
if (num2 < numberOfNonAlphanumericCharacters)
{
Random random = new Random();
for (int j = 0; j < (numberOfNonAlphanumericCharacters - num2); j++)
{
int num6;
do
{
num6 = random.Next(0, length);
}
while (!char.IsLetterOrDigit(chArray[num6]));
chArray[num6] = punctuations[random.Next(0, punctuations.Length)];
}
}
str = new string(chArray);
}
return str;
}
答案 1 :(得分:0)
我接受了Russ Cam的回答,但由于永远不会破坏的while(true)语句,它被困在一个永无止境的循环中。
所以这是我的示例,其中包含一个布尔值(blnExactNumberOfNonAlphanumericCharacters),用于指定非字母数字字符的数量是否应该精确(设置为true)或最小值(设置为false),这是原始Membership.GeneratePassword方法的方式工作原理:
public string GeneratePassword(int intLength, int intNumberOfNonAlphanumericCharacters, bool blnExactNumberOfNonAlphanumericCharacters)
{
string strPassword = "";
if (intLength > 0)
{
if ((intNumberOfNonAlphanumericCharacters >= 0) && (intNumberOfNonAlphanumericCharacters <= intLength))
{
char[] chrSpecialCharacters = @"!@$%^*()_-+=[{]};:>|.,/?".ToCharArray();
byte[] data = new byte[intLength];
char[] chrArray = new char[intLength];
int intActualNumberOfSpecialCharacters = 0;
new RNGCryptoServiceProvider().GetBytes(data);
for (int i = 0; i < intLength; i++)
{
int intRemainderOfModuloDivision = data[i] % (62 + chrSpecialCharacters.Length); //was hex 0x57 (87)
if (intRemainderOfModuloDivision < 10)
{
// generate characters 0-9
chrArray[i] = (char)(48 + intRemainderOfModuloDivision); //was hex 0x30
}
else if (intRemainderOfModuloDivision < 36) //0x24
{
// generate characters A-Z
chrArray[i] = (char)((65 + intRemainderOfModuloDivision) - 10); //was hex 0x41
}
else if (intRemainderOfModuloDivision < 62) //0x3e
{
// generate characters a-z
chrArray[i] = (char)((97 + intRemainderOfModuloDivision) - 36); //was hex 0x61 & 0x24
}
else
{
// get a non alphanumeric character from the special character array
chrArray[i] = chrSpecialCharacters[intRemainderOfModuloDivision - 62]; //was hex 0x3e
intActualNumberOfSpecialCharacters++;
}
}
if (intActualNumberOfSpecialCharacters < intNumberOfNonAlphanumericCharacters)
{
//if there are less special characters than the minimum required amount then add the minimum required
Random random = new Random();
for (int j = 0; j < (intNumberOfNonAlphanumericCharacters - intActualNumberOfSpecialCharacters); j++)
{
int intRandomArrayPointer;
do
{
intRandomArrayPointer = random.Next(0, intLength);
}
while (!char.IsLetterOrDigit(chrArray[intRandomArrayPointer]));
chrArray[intRandomArrayPointer] = chrSpecialCharacters[random.Next(0, chrSpecialCharacters.Length)];
}
}
else if ((blnExactNumberOfNonAlphanumericCharacters) && (intActualNumberOfSpecialCharacters > intNumberOfNonAlphanumericCharacters))
{
//if the exact amount is needed then we replace unwanted ones with regular letters and/or digits
Random random = new Random();
for (int j = 0; j < (intActualNumberOfSpecialCharacters - intNumberOfNonAlphanumericCharacters); j++)
{
int intRandomArrayPointer;
do
{
intRandomArrayPointer = random.Next(0, intLength);
}
while (char.IsLetterOrDigit(chrArray[intRandomArrayPointer]));
char[] chrLetterAndDigitArray = new char[62];
int intPointer = 0;
//add characters 0-9
for (int l = 48; l <= 57; l++)
{
chrLetterAndDigitArray[intPointer] = Convert.ToChar(l);
intPointer++;
}
//add characters A-Z
for (int l = 65; l <= 90; l++)
{
chrLetterAndDigitArray[intPointer] = Convert.ToChar(l);
intPointer++;
}
//add characters a-z
for (int l = 97; l <= 122; l++)
{
chrLetterAndDigitArray[intPointer] = Convert.ToChar(l);
intPointer++;
}
chrArray[intRandomArrayPointer] = chrLetterAndDigitArray[random.Next(0, chrLetterAndDigitArray.Length)];
}
}
strPassword = new string(chrArray);
}
}
return strPassword;
}