Generate a unique randomized token

  • 16 June 2020
  • 1 reply
  • 88 views

Userlevel 1
Badge

Goal

When exchanging data between (web) services, we want to use a random generated token that is difficult to guess.

Solution

A unique randomized ( = unpredictable => safe) token is generated in the code below.

-- amount of chars in token, must be multiple of 2
-- bigger is better (up to some degree), but more data as well
declare @token_char_size int = 16;

-- create a cryptographically randomized (= unpredictable => safe) token
declare @token varchar(max) = right( -- cuts the first 2 chars off of the token, they are always '0x' (indicating hex-code)
convert(varchar(max) -- converts the hexadecimal code to an alphanumeric string
, CRYPT_GEN_RANDOM(@token_char_size / 2) -- safe token is made here
, 1)
, @token_char_size);

-- following code is purely for demonstration

-- show the token
print @token;

-- every char can contain 16 values 0 - F, so 16^token_char_size gives us the amount of possibilities
print 'the chance of guessing this number the first time is 1 : ' + cast(power(cast(16 as float), @token_char_size) as varchar(max));

-- demonstrate that this generates something different every time
go 10

The result of this script is:

Beginning execution loop

4B18F738C9DE9E33

the chance of guessing this number the first time is 1 : 1.84467e+019

6688A38B4FC5C200

the chance of guessing this number the first time is 1 : 1.84467e+019

DC3471EF6CCF1ACB

the chance of guessing this number the first time is 1 : 1.84467e+019

84C525FA88F64F2A

the chance of guessing this number the first time is 1 : 1.84467e+019

7ABF2772211DE8AE

the chance of guessing this number the first time is 1 : 1.84467e+019

41221943CCA9C647

the chance of guessing this number the first time is 1 : 1.84467e+019

F499003B7504A1EC

the chance of guessing this number the first time is 1 : 1.84467e+019

 

 

 


1 reply

Userlevel 4

I really like this solution because you generate a random string, in which you can use settings for the length.

But I also want to share my go to solution.
I usually use the newid() function from SQL server.
There 36 character string is unique and takes less code to generate, it will use more space in the database, but at least you have 2 options to take in consideration now, each with their own benefits.

Solution

declare @token nvarchar(36) = newid()
print @token
go 10

Result

Beginning execution loop
B53974A8-8FBF-4831-89DB-32130364ABD2
7C5AACF5-9417-474A-A4D7-54E0B60805C0
C0EB6A78-CED4-4CD3-8CDB-48F718C8F817
E9B8184B-FB7D-4C91-B7FA-D9C357DE6BB5
C4B2E438-641F-41C0-8521-DC3FB34F3582
F2E6A9CF-B270-4D7D-823B-6B8BE6F77D37
2F77D066-9F5F-46AC-B934-2957A9B1F199
E4E5596D-CA81-40BA-AD7D-F804B4082E32
D508B1E2-710D-4889-8037-864812DB7AFF
8AA78BB7-F575-46A3-A14F-D3D86530A36F
Batch execution completed 10 times.

Reply