Generate random passwords with bash

  •  

Normally, when I need some random passwords (or just a random string), I go to randomkeygen.com, copy the kind of password I need and off I go. But if you're a Linux user, like I am, you don't like leaving the terminal. So, I created a simple shorthand:

#!/bin/bash

echo -en "\e[0mDecent: \e[92m"
cat /dev/urandom | tr -dc "[:alnum:]" | head -c 10

echo -en "\n\e[0mStrong: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 15

echo -en "\n\e[0mFt Knox: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 30

echo -en "\n\e[0mCodeIgniter: \e[92m"
cat /dev/urandom | tr -dc "[:alnum:]" | head -c 32

echo -en "\n\e[0m160Bit WPA: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 20

echo -en "\n\e[0m504Bit WPA: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 63

echo -en "\n\e[0m64Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 5

echo -en "\n\e[0m128Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 13

echo -en "\n\e[0m152Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 16

echo -en "\n\e[0m256Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 29

echo -e "\e[0m"

You can just save this to randomkeygen.sh or into /usr/local/bin/randomkeygen to allow you to call randomkeygen when you need it.

Personally, I like wrapping it in a function and put it in my .bash_aliases file. This way, the function is only available to me as normal user:

function randomkeygen() {
echo -en "\e[0mDecent: \e[92m"
cat /dev/urandom | tr -dc "[:alnum:]" | head -c 10

echo -en "\n\e[0mStrong: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 15

echo -en "\n\e[0mFt Knox: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 30

echo -en "\n\e[0mCodeIgniter: \e[92m"
cat /dev/urandom | tr -dc "[:alnum:]" | head -c 32

echo -en "\n\e[0m160Bit WPA: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 20

echo -en "\n\e[0m504Bit WPA: \e[92m"
cat /dev/urandom | tr -dc "[:graph:]" | head -c 63

echo -en "\n\e[0m64Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 5

echo -en "\n\e[0m128Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 13

echo -en "\n\e[0m152Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 16

echo -en "\n\e[0m256Bit WEP: \e[92m"
cat /dev/urandom | tr -dc "0-9A-F" | head -c 29

echo -e "\e[0m"
}

Put the above snippet into the ~/.bash_aliases file, then either restart the terminal or load the aliases manually:

. ~/.bash_aliases

Now, the randomkeygen function can be called wherever you want and it should generate something like this:

randomkeygen bash result

Based on randomkeygen.com's code

Even though I got the main idea from a snippet I found on Github, the definitions for the passwords I found in randomkeygen's source code. Also, I replaced the character lists with tr's character classes, except for the hexadecimal strings, since they are both upper and lowercased letters (which can off-course be translated piping another tr, but this uses less CPU cycles).

Long story short, the command should generate strings that match the formats of the randomkeygen site.

Is this the best way to generate passwords?

No, probably not. This method reads the output of /dev/urandom, which generates random noise and only if the noise matches the pattern in tr it's added to the output. First, using /dev/random instead could generate a more random result, but the pool should be big enough for it to not become an issue. Also, since a lot of noise is thrown away, it's arguable the results might be biased.

Finally, there are many tools which allow you to generate passwords, like mkpasswd, makepassword, pwgen or secpwgen, but having a shortcut to the formats I like, beats them all in my opinion. Also, they probably also use /dev/urandom under the hood.

Oh, and in my local function I removed the shorter WEP strings, I don't use them anyways.