Nowadays, when everyone tries to be more secure then each other, when companies spend billions on information security, it seems a little bit odd that the password reset left behind, the place that, in my opinion, should be everyone's concern, still relies only on the email provider.

Sending passwords in email is a bad idea. We all know it. Who knows how secure the email provider is? Who knows whether the email account was hacked? Who knows who's listening in between (man-in-the-middle)? etc... Because of that, almost no one sends passwords in emails.

But what about password recovery? Most of the websites just send a link via email, and after clicking on it, you can change the password. So no matter how secure the website is, it's pretty easy to hack a user, isn't it?

So how can I make a secure password reset system, without trusting the email provider?

I'm looking for a solution that will apply to everyone, without using other resources like SMS (which also not that secure). I'm looking for an answer that programmers with no budget what-so-ever still would be able to use it.

Here are some things I thought about:

  • security questions - nowadays everyone can find anything about anyone online, so those questions are not that secure.
  • Recovery code - be honest with me. If a website would ask you to print and save a recovery code, would you? Almost no one would. And if they did, they'll probably lose it after a while...
  • 7
    The usual motivation for sending a reset token by mail, but not a password, is that the token expires while the password remains. So it is not as bad as sending a password, but it might still be bad depending on your sequrity requirements.
    – Anders
    Commented May 25, 2016 at 21:14
  • 4
    @dandavis No. it isn't. Users will probably write some dumb stuff, like "hat year I was born", or "what is the name of my pet". No one would really think about good questions. And as I said, anything can be found about anyone on Facebook, Commented May 29, 2016 at 6:18
  • 1
    I agree with Anders : this is a problem without a really good solution. But I'll add that if you don't trust your email provider you should switch provider! You have to trust someone somewhere!
    – ForguesR
    Commented Jun 1, 2016 at 13:38
  • 1
    @ForguesR you don't have much choice over whether you trust your customer's email provider, because you don't get to choose it.
    – Chris H
    Commented Jun 2, 2016 at 15:47
  • 1
    There's no way you can use emails for password reset if you don't trust emails. However, there are ways to make your password reset system safer. If they generate multiple recovery emails, expire the older recovery urls. Make the recovery urls one-time use, so once they're clicked, they can't be reused. Also, might want to add logic to your "forgot password" page to "raise shields" if it detects unusual activity. (ie, if your website has only 5000 active subscribers, and you see 500 account resets, your site should do something!) Maybe use Captcha, or aggressively firewall that page.
    – NL3294
    Commented Jan 24, 2020 at 18:12

14 Answers 14


Send a unique string of text, a.k.a. a token (cryptographically secure, randomly generated), to the user via some other band besides e-mail, such as SMS or even snail mail. They can change their password in your app only if they input that token in a Web form on your site.

Or use physical devices, like SmartCards, that all users must have in order to use your app.

  • 1
    There are companies that provide Web-based APIs that allow you to send an SMS from a script in your app. Twilio and Plivo are examples. There are also companies that provide APIs that let you send physical snail mail.
    – vrtjason
    Commented May 25, 2016 at 21:10
  • 10
    SMS is NOT secure. Commented May 25, 2016 at 21:21
  • 1
    But it's the same. Still trusting on someone else. I have no clue how SMS works, but I guess it's not that protected. :\ Commented May 26, 2016 at 18:02
  • 9
    SMS doesn't need to be 100% secure to make a decent 2nd factor. the point is to force a breach of the email and phone at once, which is much harder than just attacking one. also, since the code sent to sms is temp, and only needs to live about 10 seconds, it only needs to be secure enough so that the user beats an attacker to enter it first on the reset form, after which it's useless... no, sms is not good on it's own, but as another factor, its good enough for many hi-secure civilian applications.
    – dandavis
    Commented May 29, 2016 at 15:09
  • 3
    One problem with requiring a 2FA for recovery is: what if I am changing my passwords because I lost my phone where I had the passwords saved? Thats why it should recovery be something that is simple and has a high chance of not being lost.
    – CristianTM
    Commented Jun 2, 2016 at 14:42

This might be a problem without a really good solution. Here are some suggestions. They all fall in two groups - not very effective but practical (1-4) or effective but a bit unpractical (5-6). Please note that they could, or perhaps should, be used in combination with an ordinary email.

  1. Limit the amount of time the token is valid.
  2. Check that the IP that request the new password and the IP that click the link has the same geolocation. This could break the functionality for some, like Tor users, but might still be worth it. (This only helps against the token being stolen in transit - it does nothing if the attacker has access to the email account.)
  3. Ask for some extra information about the user, like zip code or another user the person recently sent a private message to. This needs to be information that (a) the user is 100% sure to know, and (b) is not easily publicly available. There is a risk nothing fits both, so it is questionable wheater this will help.
  4. Similar to the above: use an old fashioned security question. That is, have the user explicitly give you a piece of information that fits both requirements on signup. The risk is that the user just enters something random and forgets about it, thereby bricking the account. And again - if someone really wants to find out your mothers maiden name, I am sure they can.
  5. Send the token "out of band", e.g. in an SMS or in an old fashioned snail mail. If you are worried about the security of those, use them in combination with an email token.
  6. Vrtjason suggests in comments: "Provide users with a short list of long-life tokens in case the user gets locked out. The user prints them onto a hard copy (maybe right after initial registration) and carries that list in their wallet."

For more reading on password reset functions, have a look at this question: How to implement “forgot password” functionality?

  • As you said, they either not effective or unpractical. So thanks, but it doesn't help me :( Commented May 26, 2016 at 0:24
  • E-mail providers themselves (some anyway, like Gmail) provide users with a short list of long-life tokens in case the user gets locked out. The user prints them onto a hard copy (maybe right after initial registration) and carries that list in their wallet.
    – vrtjason
    Commented May 26, 2016 at 0:55
  • @vrtjason Great suggestion! I took the liberty to include it in my answer. Thank you. Offcourse you can write it as your own answer if you want to.
    – Anders
    Commented May 26, 2016 at 7:30
  • 1
    @VladGincher My theory is that the silver bullet you are looking for does not exist. But I would be happy if someone proved me wrong on that one.
    – Anders
    Commented May 26, 2016 at 7:31
  • Just curious why you would consider SMS confirmation of an email reset link to be "unpractical". It's pretty standard in terms of 2FA to the point where adding it in wouldn't be a huge hit in terms of UX. Commented Jun 1, 2016 at 15:03

So how can I make a secure password reset system, without trusting the email provider?

You could have a notion of "trusted devices" - i.e. once a valid login is completed, you set a long lived token for that device which is stored as a cookie, and also stored (hashed) server-side.

When the password reset token is sent via email, simply require that the password reset is done by a device that has previously completed a successful login by checking the trusted device cookie.

The process would be as follows. The user accesses your page, enters their email address and gets a token. When the link is followed in their email to reset the password, ensure that the device identifier matches one that has previously logged in.

It does place some restrictions on the reset in that a user can't complete a reset from a different device. You should also allow authenticated users to manage their trusted device lists (e.g. to make it simple you could allow them to assign names to their devices, or to clear all other devices except for the current one, which will wipe the server-side record of them).

This will protect the password change from being done by any eavesdroppers at the mail provider.

Another possibility is to employ two factor authentication and then insist that their 2FA device is verified in order to proceed with password reset.

One more option could be to check the same session is used for the reset request and the actual changed password. You would need to verify the user somehow before the reset email is sent however. For example, you could ask some security questions, however this is weak (yes weaker than security questions are normally) if the mail provider could read other emails that may reveal some likely answers (this option provided for completeness, but not recommended).

Also see this answer.

  • This is what I commonly see when I forget; I see a web page "Leave this page open until you receive your magic number via [email|SMS|Smoke Signals]. Leaving the page open implies a cookie with a short expiration date was sent to my browser. But then what usually happens is I don't get the email for 2 or 3 hours which is infuriating. Commented Jun 1, 2016 at 16:17
  • Someone at the mail provider could still initiate a password reset, capture the email, then complete the reset with the same session.
    – paj28
    Commented Jun 1, 2016 at 16:37
  • @paj28: It's been a long day. I'll amend this shortly to what I should have said. Commented Jun 1, 2016 at 16:41

The main options are:

  • Email verification only - most sites do this. It's simple and essentially free, and secure enough for sites like forums, e-commerce, social networking. Most users accept that they need to trust their email provider.

  • Security questions - the most common additional security mechanism. This could be questions like "What's the name of your first pet" or potentially account details like "Postcode of last delivery". They are annoying for users (who forget their favourite colour) and offer limited security - but are reasonably easy for the developers.

  • Alternative verification - most often phone verification with SMS, although this could be address verification by posting a new password in a physical letter. Not too difficult for users. Some may object to providing their phone number, but this also discourages spam accounts. Simple enough to develop - but there's a cost for sending an SMS and even more for a physical letter. This is becoming the preferred option for larger providers.

  • Reset token - This is one of the more secure options, and easy enough for developers. However, this is not convenient for users and rarely used.

  • In person verification - when users sign up, capture their real-world identify (name, maybe government ID number). To reset their password, they come to you in person with government ID, which you verify. This is highly secure - but the overheads are high, and it doesn't work for a global website. A variation on this is to capture biometric details on sign up (which means in-person sign-up only) and to verify the biometrics for a password reset.

  • Side-step the problem - only let people log in with OpenID Connect and leave the forgotten password problem to their identity provider. This is probably the best strategic option, but OpenID Connect is not established enough yet, which makes it difficult for both users and developers.

So, there are a range of options with various advantages and disadvantages. Given all the restrictions you have put in your question, there is no technique that will satisfy all of them. You haven't said what your site does, but I expect that simple email verification is the best option for you. If that really is unacceptable, you should probably spend some money and do SMS verification.


There will not be any silver bullet for this.

Fact: If you don´t want to trust other service providers, and don´t want to provide a private independent solution based on some 2nd factor app or token, you will end up needing to ask the user to keep a secret with him and make sure he will understand that he needs to keep it safe.

An example: Take a look at the keybase.io approach. They generate what they call a "paper key". It is a long list of words. They ask you many times to write it down on paper and keep it safe. This key could be used to recovery. And there is no way at all that will give you access to the key if you lose it.

The problem with that is that it is hard to know if people are willing to write this secret down and keep it safe. I guess it depends on the importance to the user of the data that is being protected and can be recovered by this method. You need to make it clear that this will be the only way to recover the account, and ask the user many times for confirmation if he wrote it down and locked it in a safe place. And still some users will call support next day asking for info on how to recover the account because they lost their "paper key".

Recovery by email is not that bad: Let's remember that recovery tokens sent by email are not the same as passwords sent by mail, mainly because they expire within a short time and can be used only once (at least, if you do it right); So it can not really be considered that unsafe, and while it is not perfect, is still a good option that works fine for most internet users and many scenarios.

How could the recovery by email be improved?

To improve the security, you could:

  1. Notify the user by other messaging systems about any change on their account (SMS, Whatsapp, etc) so you make sure they are aware it happened and take counter-measures if needed; There are free options to do it.
  2. Could also ask for confirmation on those other systems (2nd factor) so an atacker needs to compromise not only the the email, but probably this wont be free; Just remember, however, that any confirmation based on cellphones won't be effective if the phone is lost, and also this becomes a problem if the legitimate user wants to change the password exactly because he lost his phone;
  3. Give some time frame to revert any modification using the old password;
  4. You could also require some time frame of account lockout after change so the user has some time to ask to revert it before an attacker gets in. I´m sure you will get some upset users with that lockout, but it will mitigate some attacks. You could also add some automatic checks based on data that you have from user (is he asking from recovery from a browser/place that is different from the one that he usually connects? lock him out for a while. If not, let him reset the password immediately) to make it less annoying.

In the end, however, you will have two kind of people: those that care about their protection on your system and will have good and strong passwords that they keep safe, maybe on some password management system, will use 2FA if you offer and that could in the end maybe don't even want a recovery method (I would love if some services gave me that option to just not recover - in fact, when a service asks me for those weak "secure questions", I put just random gibberish on it to make sure no one (even I) will be able to use it). Or would be happy to have a not that user friendly protection as the paper keys mentioned above.

And people that don't care that much about their protection on your system, but probably care MORE on the protection of their own email. So I still find that email is good enough for most scenarios, and paper keys, or other private approaches, are good options for critical systems.

Warning: Any sollution that tries to identify the user based on the browser where he made the recovery request is flawed

Many answers here are based on verifing that the recovery link is used only on the same place (browser) where the recovery request link was made. Any sollution that proposes such a verification fails to comply to the attack model, that is that the email account is somehow compromised. If the attacker can read the target emails, he doesn´t need the target to ask for a recovery link: he will ask the recovery link himself and get the email and the corresponding link, both in the same browser/system.

Note that this kind of solution is not a security improvement. It does not change anything on the attack, it does not make it more difficult. The attacker still only needs to have access to the target email somehow, nothing more. A good analogy is that the attacker finds an open door on your house. But now you require him to pick a lock and the corresponding key, close the door with it and keep the key. The attacker just uses the key to open the door again to get in. Not really any security improvment, just an annoyance.

Such methods would only improve the security on the attack scenario where the attacker has access only to one email, that happens to be exactly the one that the legitimate user would receive if he requests a recovery link, and uses it before the user (that just requested and is expecting the email to arrive). But would not, by any way, be able to intercept an email that takes the same path if the attacker starts the recovery request himself. Does not look an realistic scenario to me and is not the OP question scenario.


You do not need to trust the email provider to achieve this. The following architecture can be used to create a secure enough password reset link.


A table with the following columns.

  1. UserID (100 char)
  2. ReqID (128 char)
  3. Stime (timestamp)
  4. VHash (128 char)

On request page

On the request page accept the user name, and along with that use a JS library such as FingerprintJS2 to generate a unique fingerprint of the browser.

Submit them to the server.

In backend

Create a Vhash (verification hash) by running sha256(BrowserFingerprint+UserID+md5(CLIENT_IP))

Note: Avoid the IP, if it can vary fast.

Store the values into the table and generate a request ID (ReqID).Mail this as part of a link to the user.


On link page

Accept new passwords and submit it along with browser fingerprint to the server.

On backend

Check if the verification hash can be re-generated and matched. Reject if the hash do not match, or if the submission is made later than 30mins from request.

End note

A bit more less secure means would be to store a value in a cookie in the client and use the hash in a similar manner to the browser fingerprint.

  • 1
    If someone hacked someone else's email account, he can now send a password reset request. So the browser fingerprint and the IP will be his. Commented May 28, 2016 at 22:32
  • @VladGincher That would mean the entire perceived scope of you question changes. The question is no longer how you can send a secure enough reset link through email but 'what is a good replacement for reset tokens altogether'. Because your argument can be applied to any form of communication.
    – BMC
    Commented May 29, 2016 at 12:29
  • 3
    the question is "how can I make a secure password reset system, without trusting the email provider?" Commented May 29, 2016 at 12:39
  • 2
    As noted by VladGincher, this is an interesting approach but in the end it does not add security. If an an atacker has access to the email account, he can make the recovery request from his broswer and get the link from the email. If the attacker does not has access to the email account, a random token is enough secure since an attacker will not be able to guess it. No need to link the token to a browser fingerprint.
    – CristianTM
    Commented Jun 1, 2016 at 11:35
  • Note also that you could get the browserfingerprint and ip of the target by phishing, userid may be leaked somehow from the system and then you end up just needing really to get the reqId, that is the same you had before.
    – CristianTM
    Commented Jun 1, 2016 at 11:35

You can't build a secure password reset system without a trusted method of communication. If the provider can't be sure who is attempting to reset the password, they can't be sure that they are only resetting it for the legitimate owner of the account.

Therefore most modern password reset functions are a balance between a certain level of trust and a certain acceptance of risk.

On the most secure side, such as when dealing with passwords to data of very high value or of national interests, a password reset might involve a face-to-face meeting, after verification through multiple steps - maybe at least one person who has previously met the requester, some bio-metric identifiers, and some other forms of identification. This is impractical for most websites.

On the least secure side, you can have a password reset process which consists of checking that the username is correct, and it resets the password. Yes, these do exist. No, they are not useful in the slightest.

In between, you have every existing password reset scheme. You can decide to trust the user to pick a strong email password, and the user's email provider to have good protection in place - yes, some providers are dreadful at security, but others are pretty good. Don't forget that they need to have password reset processes in place too - and that they can't just email the user to verify their identity. You can limit the damage that someone gaining access to an email account can do by having a relatively short expiry time on the reset tokens - an hour might be acceptable, but for high value accounts, 5 minutes might be more suitable. You have to accept a level of inconvenience for users though if you do this - email doesn't always get through instantly.

You can introduce a second factor, such as TOTP or an SMS code. However, it might be less of a second factor than you think - lots of people nowadays receive email on their phones, which would mean that an emailed reset with a code sent by SMS might actually mean that someone has stolen the user's phone. Same with TOTP applications - if the user doesn't set a passcode for them, anyone who can access their phone can get the current code, and will have a short period in which to use it.

You can have a process where users make a phone call and enter something through the keypad. You still need some way of communicating what they enter - if you're a phone company, maybe you can check that they call from a specific line, but if you're not, people aren't going to be impressed if you require them to keep a specific phone number to be able to reset your passwords, and it's entirely possible that you could fake it anyway.

You can ask security questions, but these are generally easy to guess, or they are easy to forget, resulting in the legitimate user being unable to reset the password on their account because they didn't remember the price of the last drink they bought, or the colour of the next vehicle which passes their window.

You can link password reset to a specific device, having a "reset token" stored locally on the device in some way (perhaps HTML5 localstorage) - some online password managers allow an easier reset from a device which has previously logged in than from an unrelated device. However, this can't be the only method you use, as one reason for password resets is theft of devices.

After considering all of these, a lot of large companies who have massive security budgets have come to the conclusion that you have to trust something, and that the best option in terms of balancing security and usability is by trusting the user to have a vaguely secure email system. For high value accounts, they might add extra layers - Amazon lets you have 2FA for AWS accounts, Google has the Authenticator application which you can enable for mail accounts, Steam email verification codes when you log in from an unknown device - but they all essentially come down to needing a method which can verify the user to the provider.

The best option, therefore, is to stick with email, possibly with an extra method from those above. You can even require that the reset occurs from the same IP address as the reset request, although this can cause problems when users are trying to log in on a computer, and get the reset email on their phone.

Alternatively, make it very clear to your users that there is no password reset method. Don't laugh or dismiss it out of hand - for some especially high value accounts, this is entirely legitimate. Some online password managers implement this - they encrypt data on your device, and if the device is lost, and you don't know the encryption key, the data is worthless. It's just random bytes with no method of recovery other than brute forcing every possible password. In that case, you don't need to worry about the user's email being insecure. Although they might email the password to themselves to make sure it is always stored somewhere...


I doubt there exists any solution that will satisfy all of your requirements. You want a different, more secure solution than the ones that big companies have spent millions on researching. It can’t trust email, it can’t use outside sources like SMS, it can’t rely on security questions, doesn’t use offline (print) security codes, must be usable by any website, and be implemented with no budget. Challenge accepted!

Security is a tradeoff between time, effort, and acceptable risk.

One possible solution is to use images. Have a pool of memorable images, such as a picture of a “correct horse battery staple”. (Thanks xkcd) When the user signs up on the website, show them two of the pictures, tell them these are the pictures for password recovery, and store them in the database along with the password. Many times when I forget a password, I have a general idea of what it was. The problem is I forget that the second “e” is a “3” and not the first “e” (for example). There is no “almost password.” Images are a bit different. Even if one doesn’t exactly remember the image, they can recall that they have seen the image or something similar, i.e. “Oh, now I remember that I saw a “horse battery thingy.”

Now you can use one of the standard “forgot password” techniques, with a few modifications. When the user requests a password reset, present them with a grid of images that may or may not contain the image shown to the user at registration. Be sure to include an “I haven’t seen any of these before” option. Now you send the request along with the selected image. If the correct image was presented, and selected, by the user then email a valid password reset link. If the correct image was not presented, and the user selected, “I haven’t seen any of these before,” then email a valid password reset link. Otherwise, email a non-working password reset link. (This is so an attacker will not know he has failed at this point.)

At this point, email a notice to the user that someone is trying to change their password. Even if an attacker has access to the email and can delete it, a notification may pop up on the user’s phone or other device. Also put some kind of notice on the actual site that the password is being changed. On the page generated by the password reset link, have the image test again, not including the correct image from the first time. (This is why you used two images in the beginning.) If the correct image is selected again, then reset the password. If not, tell the user the password reset has failed, and start a wait timer. (5 mins, hour, day, whatever)

The rightful user should be able to recall the images when they are presented, and will be able to reset their password. An attacker, in addition to having access to the user’s email, would have no idea what two images were shown, and would have to guess correctly twice. This is not foolproof, but should slow down the attacker enough that the rightful user has time to react.


This is an interesting topic. Unfortunately you have narrowed down the possibilities with your exclusions. Otherwise I would have recommended a second channel.

Some sites on the Darknet have the same desires you have outlined in your question: Either they don't expect people to have an email account (anonymous email is not that easy) or they don't trust the email providers. This is why they use two different approaches:

  • Users have to write down a passphrase which is used during a password reset
  • Users have to upload a certificate which is a fall-back if a password got missing

If we leave the shady part of the Internet we may take a look how banks operate. They use security questions too but they also rely on more dynamic and short-living information like:

  • Approximative amount of last transaction
  • Approximative current balance
  • Approximative balance at the end of last month/year
  • Details about account permissions (which 3rd parties are allowed to access the accounts)

You may want to combine some of these possibilities and if 4 out of 5 are correct, you may accept the password reset. Something that developers often forget: Let the user decide whether they want to have the possibilities for such a "soft password reset".


Maybe a stupid idea but an idea anyway.

When you register you are asked for a picture to use if the account is lost. This picture can be anything : something random, a nice sunset of the Grand Canyon or a family picture. The system generates a hash of this picture and stores it (the picture is not stored).

If you lose your password you are asked to provide this picture again. If the hash matches then you are prompted to reset your password.

So basically I replace the usual security questions by a picture upload.

  • Nice that you are bringing something new to the thread. But I would not ask the user to find the same file he uploaded before, that he probably will loose or forget where is before he forgets the actual password. Or maybe edit, resize and the hash is gone. But some validation based on images is interesting. People remember better images than text.
    – CristianTM
    Commented Jun 1, 2016 at 17:25
  • @CristianTM Thanks for your comment. The more I think about it the more I like this idea. The hash could be computed with a certain threshold so resized images (with good quality) could work. I think pictures are probably the "thing" that it is the less likely to be lost. It can't be more simple than that : a single file with enough entropy that you can create easily and that you can remember and "mentalize" easily.
    – ForguesR
    Commented Jun 1, 2016 at 18:13
  • Depends what you mean by hash. If you are talking about crypto hashs, remove a pixel and almost half of the hash bits should change ;). But yes, maybe something like google uses to find identify images could be used. Anyway, I still doubt people are able to keep files safe around than theyr passwords.
    – CristianTM
    Commented Jun 1, 2016 at 18:54

A simple solution.

  1. When the user requests a password reset give them a randomised salt on the following screen.

  2. Send them a randomised reset key by email, with a link to the reset page.

  3. Store both the salt, the key, the user and an expiry time in the database.

  4. On the reset page they need to copy and paste the randomised salt from the other page, otherwise the key in the email is useless.

I believe this fulfills your requirements of being easy for any website to implement, without having to trust the email provider, and without the user needing to remember information they set at the same time as the password. I think I've seen some websites use this already, although I can't remember which ones.


Slightly more advanced solution. Same as above except that the website must also:

  1. Get the user to generate an encryption key on account creation. A public key is stored in the website database for encrypting traffic to the user.
  2. Whenever the user logins in the user must also enter their encryption key password. This decoded the pages locally in javascript/jquery and is never sent to the web server.
  3. This same key is used for all the password reset pages subsequent to entering the username, so an attacker that has compromised the users email system cannot complete the password reset process. Only someone that knows the encryption key could do so.
  • 2
    This also is not considering that who is requiring the reset link could be the attacker.
    – CristianTM
    Commented Jun 2, 2016 at 14:38
  • The attacker would need to know both the login name and know and have access to the registered email address. This seems unlikely.
    – ToniWidmo
    Commented Jun 2, 2016 at 14:43
  • I strongly disagree... 1) usually only the email is required on most recovery systems I know, maybe because the user also forgets the username, and the attacker does know the email because he has access to it in the scenario of the attack that is being discussed 2) even if the system does not leak the username somehow, most people use the same username in the system, or easy to guess ones. It is not a challange.
    – CristianTM
    Commented Jun 2, 2016 at 14:46
  • Okay, I've added a defence agains the user having a compromised email system.
    – ToniWidmo
    Commented Jun 2, 2016 at 14:58
  • If I understand correctly the idea, this would mean there would be a private key that is stored on the user side and would be used all the time he logs in?
    – CristianTM
    Commented Jun 2, 2016 at 15:06

method: security risks

  • link by email: email account could have been hacked
  • security questions: personal information can be online searched of gathered (if you have some knowledge of the target)
  • recovery code: not really practical. People usually lost it or store it in their email addresses (which leads us to security risk described method one)

If I were you, I would implement 2FA using a physical token or, as vrtjason pointed out, a cryptographically secure (pseudo)randomly generated unique string of text. But you have said that you're looking for a no-budget solution, which disregards the physical approach. Thus, there is no much that I can think of. Something that you have to accept is that, at some point, you will have to trust someone (or something). Email provider, ISP's, or, in this case, the own user (to safely store the string of text).

I believe that the key aspect here is to balance your solution between:

  • Solution Deploy Costs and Support Costs
  • Level of Security
  • Usability

Considering the mentioned limitations and the scenario described, you might consider addressing your situation by COMBINING two of the described recovery methods.

For every example, the user must enter personal information to act as security questions which will be required as the first step to recover the forgotten password.

  • Simple combination. After properly answering the questions, the the web service sends and email with the recovery link. An attacker must have compromised both personal information needed to answer the security questions and email account in order to perform a successful attack.

  • Challenge. Right after solving the security questions, the website generates a random string and sends it via email. The user opens it, goes back to the website and enters the string there. If both strings are equal, password recovery process may continue. (you may also implement a variation of Diffie-Hellman to exchange a key)

  • PKI. This is a solution online possible for special cases. But it doesn't even need to use a security question. The user simply goes to the website requests the password. The website generates a new one, encrypts it with the user public key and finally sends it by email. Only the intended recipient will be able to decrypt the password with the corresponding private key. Of course, this solution is almost impractical in general scenarios. But It could be done when high security is mandatory and the amount of user is not excessive.


A possible solution:

1) User opens website SSL password reset page and clicks the reset button.
2) server passes user browser to password reset verification screen
3) server also sends a one-time verification string via e-mail to user.
4) user opens e-mail and gets verification string
5) user pastes verification string into website reset verification screen
6) use of valid string forwards user browser to password change screen.

The user needs to be able to open a browser to the site and read their e-mail at the same time. Since the server knows the SSL session initiated the request, it won't accept the string from anyone other than that SSL session. If someone reads the e-mail in transit, they can no longer use the reset link in hopes they beat the real user in resetting their password.

This method seems to me to be a little more secure than the standard time-expiring reset link. It uses two internet channels (email and web page).

Someone who has been working on this problem for a while is Steve Gibson. His SQRL project seems to be a true solution for your question; it uses a client on a user's smartphone to avoid passwords entirely.

  • 1
    This also is not considering that who is requiring the reset link could be the attacker. This would only avoid an attacker to use a token required by the legitimate user, before he does it. I don´t think this is really the most common attack scenario.
    – CristianTM
    Commented Jun 2, 2016 at 14:35
  • @CristianTM: The assumption I am making is that a attacker has not compromised the user's email. If user email account is compromised, both this and the standard "send a reset link via e-mail" everyone uses is compromised. This method is only slightly more secure than the standard reset method. As I mentioned, I actually think SQRL is the superior way to authenticate rather than using passwords, which are fundamentally broken. Commented Jun 3, 2016 at 6:22
  • But the OP question is all about compromised email. If the email is NOT compromised, both this and the traditional "send a reset link via e-mail" also are secure. What I claim is that it does not add security, because the attack model does not excludes (and could not) the possibility of the attacker request a securty token himself. And if the email is secure, this only adds complexity, not real security, since one still just needs to get access to the email to be able to reset the account.
    – CristianTM
    Commented Jun 3, 2016 at 10:49
  • @CristianTM: email (when sent, not when read) is normally not encrypted and anyone who taps into the communication channel can read it. A the normal reset link under those conditions becomes a race between an attacker and the user as to who uses the reset link first to acquire control of the web account the link is resetting. My answer avoids this problem. It's not a major improvement over a standard reset, but it is an improvement. Commented Jun 3, 2016 at 11:04
  • I understand, but my claim is that the race condition that many people here are worried about is not the issue at all. If one has access to the victim emails (at any step) he can ask a new reset link at any time and use it. I don´t see any reason to believe that there is such an attack scenario where the attacker has access to only one email from the victim, wich happens to be exactly a recovery email that the victim itself asked for, and before the victim that is expecting the email uses it... but has no way to ask himself a new recovey link to be sent to the same email and use it.
    – CristianTM
    Commented Jun 3, 2016 at 11:14

Interesting question.

After going through the already mentioned answers and comments, I feel you are seeking for something that is easy to implement technically and something that the user can also remember and mention which is not known to others/hackers.

So, all these lead to one possibility :

Ask for 3 physical marks of a person. Like, Mole in the forehead, mole in the right hand middle finger and scar in left hand elbow. Populate this data while the user registers.

Finally, after sending the reset link, ask for the user to fill it up once again.

I don't think its easy for someone to remember the other person's marks. And that too, the same three which the person would have mentioned.

This idea might need refinement, but I feel this can be a good start.

  • 3
    Lets take Facebook as an example. If I would want to hack to a friend, I'll just meet him and write down on my phone all I can think of, pretending I'm texting to someone. Guessing which marks he used won't be easy, but after some try and error I'll succeed. Obviously I can set a limit on the attempts, but it'll probably block the user himself also, because I'm pretty sure he won't remember what marks he wrote either. (Sorry for my awful English, I hope you got my point. Thanks anyway). Commented May 28, 2016 at 22:29

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .