I am using the following line of code to create a reset password code sent to the user in her/his email. when scanned with brakeman to my ruby code, this line of code is catched and describes it as it is vulnerable.

this is the line of code I'm talking about:

reset_pass_code = Digest::SHA1.hexdigest(
  "#{u.email}#{Time.now.to_s.split(//).sort_by {rand}.join}"

so my question is how can this be exploited as it is applied and sorted in rand and it is possible that an attacker could exploit this and if yes how? I needed some explanations to contribute to my knowledge.

I understand all of the suggestions that it is good to use other alternatives of generating reset token but this despite SHA1's weakness. given attacker knowing user email. in this scenario is it possible for the attacker to reconstruct the generated token from this?

2 Answers 2


Random is not cryptographically secure(1) in order to be used in cryptographic operations, even in the way you use it. Neither is time, in terms of randomness/predictability (read an interesting answer). User email is static and, probably, public knowlege.

As such, your seed can be weak against a resourceful attacker (e.g. someone with access to FPGA farms or grids, in combination with the capability to influence the behaviour of rand).

Brakeman is a tool that provides suggestions based on principles, not on your specific implementation (it cannot know every detail of every implementation out there). As such, in principle, your approach is vulnerable and it is highlighted as such by brakeman. Whether you have taken steps to mitigate the problem in another part of the code or the associated risk is not applied to your case, is something that the tool cannot infer from the specific lines of code and, if that's the case, you should just ignore it.

(1) You should use SecureRandom instead

  • thanks for the thorough explanations. this is what I was looking for. one more dump thinking is that ...sort_by {rand} is just sorting the array. so is it viable to compute all possible combinations hence get the right token and then use it. the code expires in a day so how could it be reached in scripts?
    – hanan
    Dec 16, 2022 at 8:54
  • as already explained, a resourceful attacker may be able to cause a statistical bias to your rand implementation and, thus, produce predictable results. This can cause a signifcant reduction in the search space that an attacker has to use to look for combinations. However, it all comes down to whose target you are and what resources that attacker is willing to use against your system
    – user284677
    Dec 16, 2022 at 9:08

in this scenario is it possible for the attacker to reconstruct the generated token from this?

Yes. Time is not a secret. I know more or less what time it is now, so I can try a few hundred.

Why can't you generate true randomness?

  • "Why can't you generate true randomness?" That's actually a deep question. The best generators use some kind of analog input like atmospheric pressure... I even heard of one that used lava lamps... blog.cloudflare.com/randomness-101-lavarand-in-production Dec 14, 2022 at 21:00
  • irrelevant really... just a note. Dec 14, 2022 at 21:02
  • @anothermh, well I am confident enough that Time.now.to_s.split(//).sort_by {rand}.join won't produce same value at other perspectives. this is because the value from Time.now.to_s which is split is sorted with a float random numbers so hence won't produce same value. this is only my believe. reaching same value costs some time and hence the token expires and is already removed in the database as the attacker reaches this. what you think? can you challenge? these are only my thoughts
    – hanan
    Dec 15, 2022 at 13:31

You must log in to answer this question.

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