Saya ingin membuat string acak yang harus memiliki 5 huruf dari az dan 3 angka.
Bagaimana saya bisa melakukan ini dengan JavaScript?
Saya punya skrip berikut, tetapi tidak memenuhi persyaratan saya.
var chars = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
var string_length = 8;
var randomstring = '';
for (var i=0; i<string_length; i++) {
var rnum = Math.floor(Math.random() * chars.length);
randomstring += chars.substring(rnum,rnum+1);
}
javascript
ffffff01
sumber
sumber
new Array(12).fill().map(() => String.fromCharCode(Math.random()*86+40)).join("")
Nifty one liner untuk menghasilkan sandi 12 karakter dengan karakter khusus atas angka bawah dalam pendekatan yang sangat ringanJawaban:
Memaksa sejumlah karakter tetap adalah ide yang buruk . Itu tidak meningkatkan kualitas kata sandi. Lebih buruk lagi, ini mengurangi jumlah kemungkinan kata sandi, sehingga peretasan dengan bruteforcing menjadi lebih mudah.
Untuk menghasilkan kata acak yang terdiri dari karakter alfanumerik, gunakan:
var randomstring = Math.random().toString(36).slice(-8);
Bagaimana cara kerjanya?
Math.random() // Generate random number, eg: 0.123456 .toString(36) // Convert to base-36 : "0.4fzyo82mvyr" .slice(-8);// Cut off last 8 characters : "yo82mvyr"
Dokumentasi untuk metode
Number.prototype.toString
danstring.prototype.slice
.sumber
Math.random().toString(36).substr(2, 8)
.toString
hanya menerima basis hingga dan termasuk 36. Jawaban ini dimaksudkan sebagai satu baris untuk string acak non-kriptografi. Jika Anda juga ingin memiliki ibu kota, gunakanMath.random
(ataucrypto.getRandomValues
jika tersedia) dan petakan hasilnya ke az, AZ, 0-9. Misalnya menggunakan jawaban saaj di bawah ini.Pendekatan yang sedikit lebih dapat dipelihara dan aman.
Pembaruan untuk memperluas apa yang saya maksud dan cara kerjanya.
Aman . MDN cukup eksplisit tentang penggunaan
Math.random
untuk apa pun yang terkait dengan keamanan :Melihat can-i-use untuk
getRandomValues
tahun 2020, Anda mungkin tidak memerlukanmsCrypto
danMath.random
fallback lagi, kecuali jika Anda peduli dengan browser kuno.Maintainable sebagian besar tentang
RegExp
_pattern
sebagai cara mudah untuk menentukan kelas karakter apa yang Anda izinkan dalam kata sandi. Tetapi juga tentang 3 hal di mana masing-masing melakukan tugasnya: mendefinisikan pola, mendapatkan byte acak seaman mungkin, menyediakan API publik untuk menggabungkan keduanya.var Password = { _pattern : /[a-zA-Z0-9_\-\+\.]/, _getRandomByte : function() { // http://caniuse.com/#feat=getrandomvalues if(window.crypto && window.crypto.getRandomValues) { var result = new Uint8Array(1); window.crypto.getRandomValues(result); return result[0]; } else if(window.msCrypto && window.msCrypto.getRandomValues) { var result = new Uint8Array(1); window.msCrypto.getRandomValues(result); return result[0]; } else { return Math.floor(Math.random() * 256); } }, generate : function(length) { return Array.apply(null, {'length': length}) .map(function() { var result; while(true) { result = String.fromCharCode(this._getRandomByte()); if(this._pattern.test(result)) { return result; } } }, this) .join(''); } };
<input type='text' id='p'/><br/> <input type='button' value ='generate' onclick='document.getElementById("p").value = Password.generate(16)'>
sumber
Banyak jawaban (termasuk yang asli) tidak sesuai dengan persyaratan jumlah huruf dan angka dari OP. Berikut adalah dua solusi: umum (tanpa huruf / angka min), dan dengan aturan.
Umum:
Saya yakin ini adalah solusi umum yang lebih baik daripada yang di atas, karena:
Catat itu
Tiga baris:
var pwdChars = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; var pwdLen = 10; var randPassword = Array(pwdLen).fill(pwdChars).map(function(x) { return x[Math.floor(Math.random() * x.length)] }).join('');
Atau, sebagai satu baris:
var randPassword = Array(10).fill("0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz").map(function(x) { return x[Math.floor(Math.random() * x.length)] }).join('');
Dengan Aturan Huruf / Angka
Sekarang, variasi di atas. Ini akan menghasilkan tiga string acak dari rangkaian karakter yang diberikan (huruf, angka, baik) dan kemudian mengacak hasilnya.
Harap perhatikan penggunaan sort () di bawah ini hanya untuk tujuan ilustrasi. Untuk penggunaan produksi, ganti fungsi sort () di bawah ini dengan fungsi shuffle seperti Durstenfeld .
Pertama, sebagai fungsi:
function randPassword(letters, numbers, either) { var chars = [ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz", // letters "0123456789", // numbers "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789" // either ]; return [letters, numbers, either].map(function(len, i) { return Array(len).fill(chars[i]).map(function(x) { return x[Math.floor(Math.random() * x.length)]; }).join(''); }).concat().join('').split('').sort(function(){ return 0.5-Math.random(); }).join('') } // invoke like so: randPassword(5,3,2);
Hal yang sama, sebagai 2-liner (memang, garis yang sangat panjang dan jelek-- dan tidak akan menjadi 1-liner jika Anda menggunakan fungsi shuffle yang tepat. Tidak disarankan tetapi terkadang menyenangkan):
var chars = ["ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz","0123456789", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"]; var randPwd = [5,3,2].map(function(len, i) { return Array(len).fill(chars[i]).map(function(x) { return x[Math.floor(Math.random() * x.length)] }).join('') }).concat().join('').split('').sort(function(){return 0.5-Math.random()}).join('');
sumber
Untuk seseorang yang mencari skrip paling sederhana. Tidak
while (true)
, tidakif/else
, tidak ada deklarasi.Berdasarkan jawaban mwag, tapi yang ini menggunakan
crypto.getRandomValues
, random yang lebih kuat dariMath.random
.Array(20) .fill('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz~!@-#$') .map(x => x[Math.floor(crypto.getRandomValues(new Uint32Array(1))[0] / (0xffffffff + 1) * x.length)]) .join('');
Lihat ini untuk
0xffffffff
.Alternatif 1
var generatePassword = ( length = 20, wishlist = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz~!@-#$" ) => Array(length) .fill('') .map(() => wishlist[Math.floor(crypto.getRandomValues(new Uint32Array(1))[0] / (0xffffffff + 1) * wishlist.length)]) .join(''); console.log(generatePassword());
Alternatif 2
var generatePassword = ( length = 20, wishlist = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz~!@-#$' ) => Array.from(crypto.getRandomValues(new Uint32Array(length))) .map((x) => wishlist[x % wishlist.length]) .join('') console.log(generatePassword())
Node.js
const crypto = require('crypto') const generatePassword = ( length = 20, wishlist = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz~!@-#$' ) => Array.from(crypto.randomFillSync(new Uint32Array(length))) .map((x) => wishlist[x % wishlist.length]) .join('') console.log(generatePassword())
sumber
+ 1
tersebut tidak perlu dan bisa dilepas.crypto.getRandomValues
dengan crypto.randomFillSync .Ini tidak benar-benar dioptimalkan, tetapi seharusnya berfungsi.
var chars = "ABCDEFGHIJKLMNOPQRSTUVWXTZabcdefghiklmnopqrstuvwxyz"; var string_length = 8; var randomstring = ''; var charCount = 0; var numCount = 0; for (var i=0; i<string_length; i++) { // If random bit is 0, there are less than 3 digits already saved, and there are not already 5 characters saved, generate a numeric value. if((Math.floor(Math.random() * 2) == 0) && numCount < 3 || charCount >= 5) { var rnum = Math.floor(Math.random() * 10); randomstring += rnum; numCount += 1; } else { // If any of the above criteria fail, go ahead and generate an alpha character from the chars string var rnum = Math.floor(Math.random() * chars.length); randomstring += chars.substring(rnum,rnum+1); charCount += 1; } } alert(randomstring);
</s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> </s> orang </s>
Berikut adalah jsfiddle untuk Anda uji: http://jsfiddle.net/sJGW4/3/
sumber
chars.substring(rnum, rnum+1)
hanya sepertichars.charAt(rnum)
Seperti yang dicatat @RobW, membatasi kata sandi ke sejumlah karakter tetap seperti yang diusulkan dalam skema OP adalah ide yang buruk . Tapi yang lebih buruk, jawaban yang mengusulkan berdasarkan kode
Math.random
adalah ide yang sangat buruk .Mari kita mulai dengan ide buruk . Kode OP secara acak memilih string yang terdiri dari 8 karakter dari rangkaian 62. Membatasi string acak menjadi 5 huruf dan 3 angka berarti kata sandi yang dihasilkan akan memiliki, paling baik , 28,5 bit entropi (berlawanan dengan potensi 47,6 bit jika pembatasan distribusi 5 huruf dan 3 angka dihilangkan). Itu tidak terlalu bagus. Namun kenyataannya, situasinya bahkan lebih buruk. The terbaik aspek kode ini dihancurkan oleh penggunaan
Math.random
sebagai sarana untuk menghasilkan entropi untuk password.Math.random
adalah generator bilangan acak semu . Karena sifat deterministik generator bilangan acak semu, entropi kata sandi yang dihasilkan sangat buruk, membuat solusi yang diusulkan seperti itu menjadi ide yang sangat buruk . Dengan asumsi kata sandi ini dibagikan kepada pengguna akhir (apa gunanya), musuh aktif yang menerima kata sandi semacam itu memiliki peluang yang sangat baik untuk memprediksi kata sandi masa depan yang dibagikan kepada pengguna lain, dan itu mungkin bukan hal yang baik.Tapi kembali ke ide yang buruk . Asumsikan generator bilangan acak semu yang kuat secara kriptografik digunakan sebagai pengganti
Math.random
. Mengapa Anda membatasi kata sandi menjadi 28,5 bit? Seperti disebutkan, itu tidak terlalu bagus. Agaknya skema 5 huruf, 3 angka ini untuk membantu pengguna dalam mengelola kata sandi yang dibagikan secara acak. Tapi mari kita hadapi itu, Anda harus menyeimbangkan kemudahan penggunaan dengan nilai penggunaan , dan 28,5 bit entropi tidak banyak berguna untuk pertahanan melawan musuh aktif.Tapi cukup yang buruk. Mari kita usulkan jalan ke depan. Saya akan menggunakan pustaka JavaScript EntropyString yang "secara efisien menghasilkan string acak yang kuat secara kriptografis dari entropi tertentu dari berbagai set karakter". Daripada OP 62 karakter, saya akan menggunakan set karakter dengan 32 karakter yang dipilih untuk mengurangi penggunaan karakter yang mudah membingungkan atau pembentukan kata dalam bahasa Inggris. Dan daripada skema 5 huruf, 3 angka (yang memiliki entropi terlalu sedikit), saya akan menyatakan bahwa kata sandi akan memiliki 60 bit entropi (ini adalah keseimbangan kemudahan versus nilai).
import { Entropy, charSet32 } from 'entropy-string' const random = new Entropy({ bits: 60, charset: charset32 }) const string = random.string()
Perhatikan argumen untuk
Entropy
menentukan bit entropi yang diinginkan sebagai kebalikan dari solusi yang lebih umum terlihat untuk pembuatan string acak yang menentukan penerusan dalam panjang string (yang salah arah dan biasanya kurang ditentukan, tapi itu cerita lain).sumber
Jika Anda memerlukan kata sandi yang dibuat dengan setidaknya 1 angka, 1 karakter huruf besar, dan 1 karakter huruf kecil:
function generatePassword(passwordLength) { var numberChars = "0123456789"; var upperChars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; var lowerChars = "abcdefghijklmnopqrstuvwxyz"; var allChars = numberChars + upperChars + lowerChars; var randPasswordArray = Array(passwordLength); randPasswordArray[0] = numberChars; randPasswordArray[1] = upperChars; randPasswordArray[2] = lowerChars; randPasswordArray = randPasswordArray.fill(allChars, 3); return shuffleArray(randPasswordArray.map(function(x) { return x[Math.floor(Math.random() * x.length)] })).join(''); } function shuffleArray(array) { for (var i = array.length - 1; i > 0; i--) { var j = Math.floor(Math.random() * (i + 1)); var temp = array[i]; array[i] = array[j]; array[j] = temp; } return array; } alert(generatePassword(12));
Berikut biola jika ingin bermain / menguji: http://jsfiddle.net/sJGW4/155/
Properti untuk @mwag karena memberi saya permulaan untuk membuat ini.
sumber
j
: P Jika tidak, barang bagus di sini. Memodifikasi sedikit untuk memenuhi persyaratan saya.Saya telah menulis yang kecil yang terinspirasi dari jawaban Anda:
(function(){g=function(){c='0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';p='';for(i=0;i<8;i++){p+=c.charAt(Math.floor(Math.random()*62));}return p;};p=g();while(!/[A-Z]/.test(p)||!/[0-9]/.test(p)||!/[a-z]/.test(p)){p=g();}return p;})()
Fungsi ini mengembalikan kata sandi dan dapat digunakan di bookmarklet seperti:
sumber
Saya tidak akan merekomendasikan menggunakan kata sandi paksa karena membatasi Keamanan Pengguna tetapi bagaimanapun, ada beberapa cara untuk melakukannya -
Metode JavaScript Tradisional -
Math.random().toString(36).slice(-8);
Menggunakan String Acak
Pasang string acak:
Menggunakannya di App.js -
var randStr = require('randomstring'); var yourString = randStr.generate(8);
Nilai kata sandi Anda ditahan di variabel
yourString
.Jangan Gunakan Kata Sandi Paksa!
Kata Sandi Paksa dapat membahayakan keamanan Anda karena semua kata sandi akan berada di bawah kumpulan karakter yang sama, yang dapat dengan mudah dilanggar!
sumber
Ok jadi jika saya mengerti dengan baik Anda mencoba mendapatkan kata sandi string acak yang berisi 5 huruf dan 3 angka yang diposisikan secara acak sehingga memiliki panjang 8 karakter dan Anda menerima huruf maj dan min, Anda dapat melakukannya dengan fungsi berikut :
function randPass(lettersLength,numbersLength) { var j, x, i; var result = ''; var letters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'; var numbers = '0123456789'; for (i = 0; i < lettersLength; i++ ) { result += letters.charAt(Math.floor(Math.random() * letters.length)); } for (i = 0; i < numbersLength; i++ ) { result += numbers.charAt(Math.floor(Math.random() * numbers.length)); } result = result.split(""); for (i = result.length - 1; i > 0; i--) { j = Math.floor(Math.random() * (i + 1)); x = result[i]; result[i] = result[j]; result[j] = x; } result = result.join(""); return result }
function randPass(lettersLength,numbersLength) { var j, x, i; var result = ''; var letters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'; var numbers = '0123456789'; for (i = 0; i < lettersLength; i++ ) { result += letters.charAt(Math.floor(Math.random() * letters.length)); } for (i = 0; i < numbersLength; i++ ) { result += numbers.charAt(Math.floor(Math.random() * numbers.length)); } result = result.split(""); for (i = result.length - 1; i > 0; i--) { j = Math.floor(Math.random() * (i + 1)); x = result[i]; result[i] = result[j]; result[j] = x; } result = result.join(""); return result } console.log(randPass(5,3))
sumber
var letters = ['a','b','c','d','e','f','g','h','i','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']; var numbers = [0,1,2,3,4,5,6,7,8,9]; var randomstring = ''; for(var i=0;i<5;i++){ var rlet = Math.floor(Math.random()*letters.length); randomstring += letters[rlet]; } for(var i=0;i<3;i++){ var rnum = Math.floor(Math.random()*numbers.length); randomstring += numbers[rnum]; } alert(randomstring);
sumber
Dan akhirnya, tanpa menggunakan peretasan floating point:
function genpasswd(n) { // 36 ** 11 > Number.MAX_SAFE_INTEGER if (n > 10) throw new Error('Too big n for this function'); var x = "0000000000" + Math.floor(Number.MAX_SAFE_INTEGER * Math.random()).toString(36); return x.slice(-n); }
sumber
Amankan kata sandi dengan satu karakter huruf besar.
let once = false; let newPassword = Math.random().toString(36).substr(2, 8).split('').map((char) => { if(!Number(char) && !once){ once = true; return char.toUpperCase(); } return char; }).join(''); console.log(newPassword)
sumber
Berdasarkan Crypto saya, masalahnya. Menggunakan ES6 dan menghilangkan pemeriksaan fitur browser. Ada komentar tentang keamanan atau kinerja?
const generatePassword = ( passwordLength = 12, passwordChars = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz', ) => [...window.crypto.getRandomValues(new Uint32Array(passwordLength))] .map(x => passwordChars[x % passwordChars.length]) .join('');
sumber
Coba ini, berhasil. Unduh skrip ke aplikasi javascript Anda dan panggil fungsi randomPassword () https://gist.github.com/enishant/4ba920c71f338e83c7089dc5d6f33a64
sumber
Buat layanan pembuat kata sandi yang disebut PassswordGeneratorService
import { Injectable } from '@angular/core'; @Injectable() export class PasswordGeneratorService { generatePassword(length:number,upper:boolean,numbers:boolean,symbols:boolean) { const passwordLength = length || 12; const addUpper = upper; const addNumbers = numbers; const addSymbols = symbols; const lowerCharacters = ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z']; const upperCharacters = ['A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z']; const numbers = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']; const symbols = ['!', '?', '@']; const getRandom = array => array[Math.floor(Math.random() * array.length)]; let finalCharacters = ''; if (addUpper) { finalCharacters = finalCharacters.concat(getRandom(upperCharacters)); } if (addNumbers) { finalCharacters = finalCharacters.concat(getRandom(numbers)); } if (addSymbols) { finalCharacters = finalCharacters.concat(getRandom(symbols)); } for (let i = 1; i < passwordLength - 3; i++) { finalCharacters = finalCharacters.concat(getRandom(lowerCharacters)); } return finalCharacters.split('').sort(() => 0.5 - Math.random()).join(''); } }
jangan lupa untuk menambahkan service pada modul yang anda gunakan
@NgModule({ imports: [ CommonModule, SharedModule, CommonModule, RouterModule.forChild(routes), FormsModule, ReactiveFormsModule, FlexLayoutModule, TranslateModule, ExistingUserDialogModule, UserDocumentsUploadDialogModule ], declarations: [ UserListComponent, EditUserDialogComponent, UserEditorComponent ], entryComponents: [ EditUserDialogComponent ], providers: [ AuthService, PasswordGeneratorService ] }) export class UsersModule { }
Di pengontrol Anda, tambahkan metode yang memanggil metode buat kata sandi di dalam layanan dan setel hasilnya di bidang kata sandi
constructor( private passwordGenerator: PasswordGeneratorService, ) get newPassword() { return this.password.get('newPassword'); } generatePassword() { this.newPassword.setValue(this.passwordGenerator.generatePassword(8,true,true,true)); }
sumber
generatePassword
dan menggunakannya, tidak perlu untuk seluruh kelas. thnxAda generator string kata sandi acak dengan panjang yang dipilih
let input = document.querySelector("textarea"); let button = document.querySelector("button"); let length = document.querySelector("input"); function generatePassword(n) { let pwd = ""; while(!pwd || pwd.length < n) { pwd += Math.random().toString(36).slice(-22); } return pwd.substring(0, n); } button.addEventListener("click", function() { input.value = generatePassword(length.value); });
<div>password:</div> <div><textarea cols="70" rows="10"></textarea></div> <div>length:</div> <div><input type="number" value="200"></div> <br> <button>gen</button>
sumber
Nah, Anda selalu dapat menggunakan objek window.crypto yang tersedia di versi terbaru browser.
Hanya perlu satu baris kode untuk mendapatkan nomor acak:
let n = window.crypto.getRandomValues(new Uint32Array(1))[0];
Ini juga membantu mengenkripsi dan mendekripsi data. Informasi selengkapnya di dokumen Web MDN - window.crypto .
sumber
var Password = { _pattern : /[a-zA-Z0-9_\-\+\.]/, _getRandomByte : function() { // http://caniuse.com/#feat=getrandomvalues if(window.crypto && window.crypto.getRandomValues) { var result = new Uint8Array(1); window.crypto.getRandomValues(result); return result[0]; } else if(window.msCrypto && window.msCrypto.getRandomValues) { var result = new Uint8Array(1); window.msCrypto.getRandomValues(result); return result[0]; } else { return Math.floor(Math.random() * 256); } }, generate : function(length) { return Array.apply(null, {'length': length}) .map(function() { var result; while(true) { result = String.fromCharCode(this._getRandomByte()); if(this._pattern.test(result)) { return result; } } }, this) .join(''); } };
<input type='text' id='p'/><br/> <input type='button' value ='generate' onclick='document.getElementById("p").value = Password.generate(16)'>
sumber
Setiap kata sandi yang dibuat dengan Math.random () SANGAT BURUK .
Fungsi ini menggunakan waktu sistem sebagai benih untuk generator bilangan acak. Siapa pun yang mengetahui waktu pembuatan sandi dapat dengan mudah melakukan brute force pada sandi.
Di hampir semua kasus, data ini tersedia dengan mudah - cukup ambil kolom Registration_time di database yang diretas, dan uji semua nilai yang dihasilkan oleh algoritme Math.random () menggunakan waktu dari 15 hingga 0 menit sebelumnya.
Kata sandi yang dibuat dengan Math.random () sama sekali tidak berharga karena saat kata sandi pertama kali digunakan sudah cukup untuk memecahkannya.
sumber