GUID UUID in Java Summary

herosoft發表於2007-07-18

Foreground Knowledge About GUID and UUID.

Implementation in Java.

Before JDK 5.0

After JDK 5.0

Conclusion

[@more@]

Foreground Knowledge About GUID and UUID.

UUID

通用惟一識別符號(UUID)是128位位元的數字,用來惟一地標識因特網上的某些物件或者實體。

A Universally Unique Identifier is an identifier standard used in software construction, standardized by the Open Software Foundation (OSF) as part of the Distributed Computing Environment (DCE). The intent of UUIDs is to enable distributed systems to uniquely identify information without significant central coordination. Thus, anyone can create a UUID and use it to identify something with reasonable confidence that the identifier will never be unintentionally used by anyone for anything else. Information labelled with UUIDs can therefore be later combined into a single database without need to resolve name conflicts. The most widespread use of this standard is in Microsoft's Globally Unique Identifiers (GUIDs) which implement this standard.

一個UUID 是一個識別符號標準用於軟體架構,是由開放軟體基金會(OSF)作為分散式計算環境(DCE)的一部分而制定的標準。UUIDs的目的就是使分散式系統可以不需要重要的中央調合系統而能唯一地標識資訊。這樣,任何人能創造一個UUID 和使用它來標識一些東西,而且,你有足夠的信心來確定這個標識是永遠不會被任何人無意地使用在任何東西上。因此,資訊加上了UUID標籤就能合併到單個資料庫中而不用去解決命名衝突的問題。這個標準的廣泛應用在微軟的全球唯一識別符號(GUIDs)上,GUID實現了這個標準。

A UUID is essentially a 16-byte number and in its canonical form a UUID may look like this:

:550E8400-E29B-11D4-A716-446655440000

And has this structure in the C programming language:

typedef struct {
unsigned32 time_low;
unsigned16 time_mid;
unsigned16 time_hi_and_version;
unsigned8 clock_seq_hi_and_reserved;
unsigned8 clock_seq_low;
byte node6;
} uuid_t;

The J2SE 5.0 release of Java provides a class that will produce 128-bit UUIDs. The API documentation for the class refers to ISO/IEC 11578:1996.

關於UUID的定義,詳細內容可參考,文件裡面還有C語言對UUID標準的各種實現。

GUID

A Globally Unique Identifier or GUID is a pseudo-random number used in software applications. While each generated GUID is not guaranteed to be unique, the total number of unique keys (2128 or 3.4028×1038) is so large that the possibility of the same number being generated twice is very small.

一個全球唯一識別符號 或 GUID 是一個假隨機數用於軟體中。雖然每個產生的GUID是不保證唯一的,但不同的識別符號總數是(2128 也就是3.4028×1038)如此之大,以至於相同的數字被產生兩次的機率是很相當小的。

The GUID is an implementation by Microsoft of a standard called Universally Unique Identifier (UUID), specified by the Open Software Foundation (OSF).

GUID 是微軟對UUID這個標準的實現。UUID是由開放軟體基金會(OSF)定義的。

UUID還有其它各種實現,不止GUID一種,其它的在此不詳細說明。


Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=1406125

Implementation in Java.

Before JDK 5.0

1.

JUG is a pure java UUID generator, that can be used either as a component in a bigger application, or as a standalone command line tool (a la 'uuidgen').

org.safehaus.uuid.UUID _uuid = UUIDGenerator.getInstance().generateTimeBasedUUID();
System.out.println(_uuid + " the length is:" + _uuid.toString().length());

_uuid = UUIDGenerator.getInstance().generateRandomBasedUUID();
System.out.println(_uuid + " the length is:" + _uuid.toString().length());

2.jakarta commons sandbox id

//not avaliable in binary release in Jul 18, 2007

3.UUIDHexGenerator in Hibernate.

//havn't tried it.

4.A widely source code based on the MD5 hashing algorithm in the internet.

/**
* @author Administrator
*
* TODO To change the template for this generated type comment go to
* Window - Preferences - Java - Code Style - Code Templates
*/
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.Random;

public class RandomGUID extends Object {
protected final org.apache.commons.logging.Log logger = org.apache.commons.logging.LogFactory
.getLog(getClass());

public String valueBeforeMD5 = "";
public String valueAfterMD5 = "";
private static Random myRand;
private static SecureRandom mySecureRand;

private static String s_id;
private static final int PAD_BELOW = 0x10;
private static final int TWO_BYTES = 0xFF;

/*
* Static block to take care of one time secureRandom seed.
* It takes a few seconds to initialize SecureRandom. You might
* want to consider removing this static block or replacing
* it with a "time since first loaded" seed to reduce this time.
* This block will run only once per JVM instance.
*/

static {
mySecureRand = new SecureRandom();
long secureInitializer = mySecureRand.nextLong();
myRand = new Random(secureInitializer);
try {
s_id = InetAddress.getLocalHost().toString();
} catch (UnknownHostException e) {
e.printStackTrace();
}

}


/*
* Default constructor. With no specification of security option,
* this constructor defaults to lower security, high performance.
*/
public RandomGUID() {
getRandomGUID(false);
}

/*
* Constructor with security option. Setting secure true
* enables each random number generated to be cryptographically
* strong. Secure false defaults to the standard Random function seeded
* with a single cryptographically strong random number.
*/
public RandomGUID(boolean secure) {
getRandomGUID(secure);
}

/*
* Method to generate the random GUID
*/
private void getRandomGUID(boolean secure) {
MessageDigest md5 = null;
StringBuffer sbValueBeforeMD5 = new StringBuffer(128);

try {
md5 = MessageDigest.getInstance("MD5");
} catch (NoSuchAlgorithmException e) {
logger.error("Error: " + e);
}

try {
long time = System.currentTimeMillis();
long rand = 0;

if (secure) {
rand = mySecureRand.nextLong();
} else {
rand = myRand.nextLong();
}
sbValueBeforeMD5.append(s_id);
sbValueBeforeMD5.append(":");
sbValueBeforeMD5.append(Long.toString(time));
sbValueBeforeMD5.append(":");
sbValueBeforeMD5.append(Long.toString(rand));

valueBeforeMD5 = sbValueBeforeMD5.toString();
md5.update(valueBeforeMD5.getBytes());

byte[] array = md5.digest();
StringBuffer sb = new StringBuffer(32);
for (int j = 0; j < array.length; ++j) {
int b = array[j] & TWO_BYTES;
if (b < PAD_BELOW)
sb.append('0');
sb.append(Integer.toHexString(b));
}

valueAfterMD5 = sb.toString();

} catch (Exception e) {
logger.error("Error:" + e);
}
}

/*
* Convert to the standard format for GUID
* (Useful for SQL Server UniqueIdentifiers, etc.)
* Example: C2FEEEAC-CFCD-11D1-8B05-00600806D9B6
*/
public String toString() {
String raw = valueAfterMD5.toUpperCase();
StringBuffer sb = new StringBuffer(64);
sb.append(raw.substring(0, 8));
sb.append("-");
sb.append(raw.substring(8, 12));
sb.append("-");
sb.append(raw.substring(12, 16));
sb.append("-");
sb.append(raw.substring(16, 20));
sb.append("-");
sb.append(raw.substring(20));

return sb.toString();
}


// Demonstraton and self test of class
public static void main(String args[]) {
for (int i=0; i< 100; i++) {
RandomGUID myGUID = new RandomGUID();
System.out.println("Seeding String=" + myGUID.valueBeforeMD5);
System.out.println("rawGUID=" + myGUID.valueAfterMD5);
System.out.println("RandomGUID=" + myGUID.toString());
}
}


}

After JDK 5.0

It's so easy and guarantted.

import java.util.UUID;
public class Test {
public static void main(String[] args) {
UUID uuid = UUID.randomUUID();
System.out.println (uuid);
}
}

Conclusion

If you currently use JDK prior to 5.0, It is recommended to get the UUID by using JUG implementation. Thanks.

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/220284/viewspace-926990/,如需轉載,請註明出處,否則將追究法律責任。

相關文章