35

How can I fix this code so it generates unique random letters and numbers in lower case?

api_string = (0...32).map{65.+(rand(25)).chr}.join    

At the moment, it generates only letters.

the Tin Man
  • 155,156
  • 41
  • 207
  • 295
donald
  • 23,289
  • 41
  • 138
  • 221
  • 1
    The range for numbers is 48 to 57. These must be included in your range. – soandos May 11 '11 at 15:41
  • Thanks for the answer. Can you give an example so I can mark it as correct? – donald May 11 '11 at 15:43
  • possible duplicate of [How best to generate a random string in Ruby](http://stackoverflow.com/questions/88311/how-best-to-generate-a-random-string-in-ruby) – user Mar 25 '15 at 08:20

11 Answers11

84

If you are using ruby 1.9.2 you can use SecureRandom:

irb(main):001:0> require 'securerandom'
=> true
irb(main):002:0> SecureRandom.hex(13)
=> "5bbf194bcf8740ae8c9ce49e97"
irb(main):003:0> SecureRandom.hex(15)
=> "d2413503a9618bacfdb1745eafdb0f"
irb(main):004:0> SecureRandom.hex(32)
=> "432e0a359bbf3669e6da610d57ea5d0cd9e2fceb93e7f7989305d89e31073690"
Vasiliy Ermolovich
  • 24,067
  • 5
  • 78
  • 76
28

All letters and digits, that's how numbers are represented in base 36.

api_string = Array.new(32){rand(36).to_s(36)}.join
steenslag
  • 76,334
  • 16
  • 131
  • 165
15

8.times.map { [*'0'..'9', *'a'..'z'].sample }.join

Anuja Joshi
  • 678
  • 6
  • 13
  • `'0'..'9'` generates an array from 0 to 9, and `'a'..'z'` generates an array from a to z, but what exactly does the * before each of them does? – Vipin Verma May 30 '16 at 12:21
  • 1
    `'0'..'9'` is range and `*` is splat operator. It splits the elements of the range into single items which are returned as a group, so basically `*` is helping you to separate out elements so that they can be sampled out using `sample` method – Anuja Joshi Jun 01 '16 at 06:34
3

Newer versions of Ruby support SecureRandom.base58, which will get you much denser tokens than hex, without any special characters.

> SecureRandom.base58(24)
> "Zp9N4aYvQfz3E6CmEzkadoa2" 
Meekohi
  • 9,857
  • 5
  • 50
  • 55
2

i forgot from where, but i've read this somehow this morning

l,m = 24,36
rand(m**l).to_s(m).rjust(l,'0')

it create random number from 0 to power(36,24), then convert it to base-36 string (that is 0-9 and a-z)

Kokizzu
  • 22,630
  • 29
  • 120
  • 213
2

Here's one way to do it:

POSSIBLE = (('A'..'Z').to_a + (0..9).to_a)
api_string = (0...32).map { |n| POSSIBLE.sample }.join

If you have Active Support available you can also do this to make an API-key-like string:

ActiveSupport::SecureRandom.hex(32)
Jimmy
  • 33,523
  • 11
  • 78
  • 95
1
((('a'..'z').to_a + (0..9).to_a)*3).shuffle[0,(rand(100).to_i)].join

Replace rand(100) with rand(n) where n is the maximum length of your desired string.

AGS
  • 14,118
  • 5
  • 48
  • 65
1

This will generate a lower random string from 32 to 50 characters including numbers and letters, both:

require 'string_pattern'

puts "32-50:/xN/".gen
Mario Ruiz
  • 52
  • 6
1
CHARS = (?0..?9).to_a + (?a..?z).to_a
api_string = 32.times.inject("") {|s, i| s << CHARS[rand(CHARS.size)]}
Guilherme Bernal
  • 8,133
  • 24
  • 40
0

using SecureRandom of ruby language.

require 'securerandom' randomstring = SecureRandom.hex(5)

It will generate the n*2 random string contains “0-9″ and “a-f”

Bill the Lizard
  • 386,424
  • 207
  • 554
  • 861
veeresh yh
  • 931
  • 8
  • 20
-1
Process.clock_gettime(Process::CLOCK_REALTIME, :nanosecond).to_s(36)
John Doe
  • 353
  • 3
  • 4