How websites store your password
I’ve always been curious about how passwords stay secure, such as how they’re created, stored, and verified. Over the years, working as a software engineer on applications that require user authentication, I’ve learned a lot about the behind the scenes mechanisms that make this process possible. I plan to demystify some of the processes which you may have a general understanding of and also shine some light on some processes which you may not have heard of before.
The participants
There are a few key players involved in the process:
- The Application, which includes:
- Website – The page you visit in your web browser.
- Server – The computer that delivers the website to your browser. This could be anything from a desktop or laptop to a specialized computer without a screen or keyboard.
- Database – A program running on the server that stores data, including user information like passwords (more on how that’s done securely in a bit).
- The User – That’s you, the person accessing the website.
The general flow is that you, the user, types information into a website which sends that information to a server and the server stores that information in a database. The database returns a message saying it was a success, and then the server tells the website it was a success, and then finally the website tells you it was a success or just shows you the results on the screen. This is generally how most websites work in one way or another.
How a website really stores your password
Creating an account
When you create an account on a website and click the “Create Account” or “Sign Up” button, all the information you entered (such as your email, username, and password) is sent to the website’s server from the website.
Here’s an actual screenshot of the request sent to Reddit’s server when creating a new account. You can see that it includes the email, username, and password. In this example, the password is: t1J1&%22k$rK^!*051Cb
.
So the server now has your password, and it just stores it right? Hopefully not, the goal of good password security for a website is that they should never actually know what the value of your password is. I’ll talk about some best practices with how a website should store your password next.
No one except you should know your password
A good rule for privacy is that you don’t want to know information you don’t need to know. But to allow a user to log in to a website, you probably need to know their password, or possibly some representation of a password. There are some mathematical algorithms which exist called hashes which do one thing very good. They can turn any sequence of characters into a scrambled mess of characters which cannot be reversed. The best part is that if you give it the same exact order of characters, you will always get the same scrambled mess again.
This is important to password security because if this is the case, if the server takes your password and hashes it, then it can store that hash value and not actually know what your password really is. It is important to note that hashing is different to encryption, in that encryption can be reversed with a special key, while hashing cannot be reversed.
If it cannot reverse this scrambled mess to verify your password, then how does it verify your password? What ends up happening is that when you log in, you give the website your password again, and it just checks to see if those scrambled characters are what exists in the database for your username or email.
The result is that the server does not actually know your password, instead, it relies on you to provide your password so that it can check if doing some math on it ends up with the same value as when you first registered. That is great, but if it sounds too easy and too good to be true - you are right. This has a drawback that if you and some other user has the same password, your hashes will be the same, and a nefarious attacker could just create a list of most common password and generate the hash of them so if they get access to the database, they can figure out your password. This is the concept of a rainbow table attack, if the attacker has access to the database, then they can probably figure out any somewhat common password (these tables can have many millions of values).
There is a way to defend against this though, which is the concept of salting, it makes every hash unique, even if the characters being hashed are exactly the same.
Making your password hashes unique
Because of the issue that a set of the same password results in the same hash, adding a random set of characters to alter the password for hash is used. This means that the password that is actually hashed is your password plus a random set of characters that you do not even know about. Before I go into this more, here is an example of how it could work.
If you’re password is password123
, it may result in hash dsad329skd2
. But, if we make your password actually 8374231482password123
, where the first 10 characters of the password is the hash, then the resulting hash would be 39jsldf9324r2lk
. What would be stored in the database would be something such as 8374231482.39jsldf9324r2lk
where the first 10 characters are the salt, and the remaining after the period is the hashed password. If another user created a username with a password of password123
, they would receive a different salt to you and their resulting password would be way different.
The benefit of this, is that if an attacker has access to the database, they would not be able to use a rainbow table, because they would need a rainbow table for every single randomly generated salt and that is not feasible.
So how does the server verify your password like before? Well a salt should always be of the same size or attached to the hash in the database in a way it can easily be found (in the example, it is the first 10 characters, while all the characters after that are the hash). This allows the server to get the salt and hash from the database, remove the salt and use it once again with your password to receive the hash again. It will just compare that to the hash after the first 10 characters and verify they are the same.
By hashing and salting passwords, websites can protect passwords even if the database is compromised. It’s a simple yet powerful way to ensure that only you know your password.