Duncan's blog

January 22, 2013

Converting UUID to Base36

Filed under: Coldfusion — duncan @ 10:40 am
Tags: , , , , , ,
Base 36

I needed to generate a random unique string of no more than 30 characters length for integrating with an external API.  Usually for something like this we’d use a UUID/GUID, which are 36 characters long (or 35 in ColdFusion).  A colleague came up with the idea of taking that and converting it to Base 32.  He was using C# and this class, but then this part of the work got transferred to the ColdFusion team, so here’s the approach I took.

Firstly, a UUID is a hexadecimal representation of a 128-bit number.  Being hexadecimal that’s Base 16 obviously; the characters 0-9A-F.

A 128-bit number = 2^128, which is a very big number (340,282,366,920,938,463,463,374,607,431,768,211,456 possible values).  ColdFusion can struggle with integers this size in certain functions, e.g. InputBaseN (and its counterpart FormatBaseN), otherwise that would be ideal for what I’m trying to do here

There’s already a function in CFLib which could do this, but it’s compatible with ColdFusion 5, i.e. it’s not got access to any of the underlying Java classes which CFMX does.  My colleague Adam also wrote a different function which can convert between any two bases, but it’s more fully-featured than I require as well.

UUID’s also contain hyphens.  Typically a UUID format is in a 8-4-4-4-12 pattern, i.e. the string is 36 characters long.  ColdFusion does it differently; 8-4-4-16, only 35 characters long.  Apparently this difference was a mistake, which they didn’t want to amend later due to backwards-compatibility. However for the purposes of this code, I don’t care either way, I just want to get rid of the hyphen separators.

So, step 1 is remove the hyphens from a UUID:

<cfset strUUID = createUUID()>
<cfset strUUID = replace(strUUID, "-", "", "ALL")>

Now I want to turn this hexadecimal string into a BigInteger, which is the Java class which can deal with numbers this size (Integer only goes up to 2^31-1, Long goes up to 2^63-1, so BigInteger it has to be).

<cfset bigInt = createObject("java", "java.math.BigInteger").init(strUUID, 16)>

So we use the BigInteger constructor, specifying our string and the Base 16 radix as the second parameter.

Step 3, we want to then convert that BigInteger to Base 36. This is the characters A-Z0-9, and is ‘the most compact case-insensitive alphanumeric numeral system using ASCII characters’. Which I took to be a good thing; the advantage that Base 32 (that my colleague had chosen) would have given is it eliminates certain characters which might be easily-confused if you were reading the values after encoding in that base. So it’s ideal for generating codes used for humans, but that wasn’t going to be an issue here, so I chose Base 36 instead.

<cfset strBase36 = bigInt.toString(36)>

Putting it all together:

<cfset strUUID = createUUID()>
<cfset strUUID = replace(strUUID, "-", "", "ALL")>
<cfset bigInt = createObject("java", "java.math.BigInteger").init(strUUID, 16)>
<cfset strBase36 = bigInt.toString(36)>

strUUID: #strUUID#, #len(strUUID)#<br>
strBase36: #strBase36#, #len(strBase36)#

Gives me something like:

strUUID: AFA64721B8AC6F8CD055DE2527EB20F9, 32
strBase36: aecxzys9dnwydn6ejgkxwgb95, 25

PS: apologies to Base36 (the company) for borrowing their funky (and let’s be honest, better-executed) Base36 mosaic idea.


1 Comment »

  1. Too bad all the examples for doing this are in Java or C#, which already have conversion routines built in. I have yet to see one example in C.

    Comment by Hi ho — February 12, 2013 @ 8:15 am | Reply

RSS feed for comments on this post. TrackBack URI

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

Blog at WordPress.com.

%d bloggers like this: