?
Solved

Generate Unique serial numbers

Posted on 2004-11-08
7
Medium Priority
?
321 Views
Last Modified: 2013-12-24
I'm looking for a way to generate unique serial numbers like you would find on a software product..
eg.  ABCD - EFGH - JKLM - NPQR - STWX

i have a few requirements.

1) the number needs to be generated on the fly
2) it must be unique on the host machine, if it can be globally unique even better
3) it should contain only the charachters "123456789ABCDEFGHJKLMNPQRSTUWXYZ", so as to avoid mis-typing them
4) the key should be no more than 20 characters long, and always the same length
5) serial numbers will be validated against the DB, so it does not require a checksum

So far i've experimented with hashing uuid's and trying to convert them to different base systems, but i'm not sure whether the results i'm creating are still unique.

i'm happy to create the keys using cfscript or in a java object that i can instantiate in my CF code

any ideas..



0
Comment
Question by:monkeychump
5 Comments
 
LVL 35

Accepted Solution

by:
mrichmon earned 500 total points
ID: 12529204
Have you thought about using CreateUUID

http://livedocs.macromedia.com/coldfusion/6/CFML_Reference/functions-pt154.htm

It has only hex digits ( 0 throgh 9 and A through F)

But it is 35 characters long

Otherwise it meets all of your requirements.  


Maybe you could use 35 characters or somehow use only a portion of the generated value (although I don't know what unique constraints you would hit that way.

Maybe you could use the 1st 20 chars and do a test to see if it is already in the DB - if so then generate a new one.  Chances are that you will not incurr this penalty too often...

0
 
LVL 1

Author Comment

by:monkeychump
ID: 12531194
i don't want to use a plain uuid, because there values look vaguely sequential, and it is essential that this key cannot just be guessed.

I have MD5 hashed a uuid which gives a 32 character hex string, which is more "random" in its appearance, but what i was hoping to do was shorten that to 20 characters (with a larger caracter set), but retain its uniqueness..

0
 
LVL 6

Assisted Solution

by:mosphat
mosphat earned 500 total points
ID: 12543258
Does the validating DB contain all generated serial numbers? If so, you could do something like this (in pseudo code):

do
generated_code = generate 20 char code using "0-9A-Z"
while (select codecolumn from table where codecolumn = generated_code)

0
 
LVL 7

Assisted Solution

by:INSDivision6
INSDivision6 earned 500 total points
ID: 12547584
The following code will generate 20-char ID with very high probability of uniqueness:

<cfset a=Replace(CreateUUID(), "-", "", "ALL")>
<cfset set="123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ">
<cfset str="">
<cfloop index="i" from="1" to="4">
   <cfset b=InputBaseN(Left(a, 8), 16)>
   <cfif b LT 0>
      <cfset b=-b>
   </cfif>
   <cfset a=RemoveChars(a, 1, 8)>
   <cfloop index="j" from="1" to="5">
      <cfset c=b MOD 35>
      <cfset b=b/35>
      <cfset str=str & Mid(set, c+1, 1)>
   </cfloop>
   <cfset str=str & "-">
</cfloop>
<cfset str=Left(str, 23)>

<cfoutput>#str#</cfoutput>
0
 
LVL 8

Assisted Solution

by:kyle1830
kyle1830 earned 500 total points
ID: 12617816
Or try this.  I am doing something similar but for a much shorter string for generating security passwords.

<cfscript>
function getRandString(stringLength,spacerlength) {
      var tempAlphaList = "a,b,c,d,e,g,h,i,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z";
      var tempNumList = "1,2,3,4,5,6,7,8,9,0";
      var tempCompositeList = tempAlphaList&""&tempNumList;
      var tempCharsInList = listLen(tempCompositeList,",");
      var tempCounter = 1;
      var tempWorkingString = "";
      
      //loop from 1 to stringLength to generate string
      while (tempCounter LTE stringLength+spacerlength) {
            if ((tempCounter mod spacerlength is 0) and (tempCounter LT stringLength+spacerlength)){
                  tempWorkingString = tempWorkingString&"-";}
            else if (tempCounter LT stringLength+spacerlength) {
                  tempWorkingString = tempWorkingString&listGetAt(tempCompositeList,randRange(1,tempCharsInList),",");
            }
            tempCounter = tempCounter + 1;
      }
      
      return tempWorkingString;
}
</cfscript>

cfset licensenum = ucase(getRandString(20,5))#

Query your table for  licensenum, if it exists then loop til recordcount is 0.

Also just changed the number values to change the length of the string and the position of the -
0

Featured Post

How to Use the Help Bell

Need to boost the visibility of your question for solutions? Use the Experts Exchange Help Bell to confirm priority levels and contact subject-matter experts for question attention.  Check out this how-to article for more information.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Have you ever sent email via ColdFusion and thought of tracking this mail to capture the exact date and time when the message was opened ?  If yes, then this article is for you ! First we need a table user_email with columns user_id , email , sub…
When it comes to showing a 404 error page to your visitors, you do not want that generic page to show, and you especially do not want your hosting provider’s ad error page to show either. In this article, I will show you how to enable the custom 40…
Integration Management Part 2
As many of you are aware about Scanpst.exe utility which is owned by Microsoft itself to repair inaccessible or damaged PST files, but the question is do you really think Scanpst.exe is capable to repair all sorts of PST related corruption issues?
Suggested Courses

809 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question