Time-based Universally Unique Identifiers (UUIDs v7) for NodeJS and the browser.
0
uuid7.js edited
52 lines 1.7 kB View raw
1const re = /^([0-9a-f]{8})-([0-9a-f]{4})-7[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i; 2 3/** 4 * Convert a byte array to an hexadecimal string. 5 */ 6function toHexString(a) { 7 return Array.from(a, b => b.toString(16).padStart(2, '0')).join(''); 8} 9 10/** 11 * Generate a UUIDv7 (Time-Sortable Identifier). 12 * @returns {string} 13 * The generated UUIDv7 (`00000000-0000-0000-0000-000000000000`). 14 * @example 15 * let id; console.log(id = generateId()); 16 * console.log(new Date(validateId(id)).toLocaleString()); 17 */ 18export function generateId() { 19 const timestamp = Date.now(); 20 21 // Convert the timestamp to a 6-byte hexadecimal string. 22 const timestampHex = timestamp.toString(16).padStart(12, '0'); 23 24 // Generate 10 random bytes for the remaining parts. 25 const randomBytes = new Uint8Array(10); 26 crypto.getRandomValues(randomBytes); 27 28 const randomPart1 = randomBytes.subarray(0, 2); 29 const randomPart2 = randomBytes.subarray(2, 4); 30 const randomPart3 = randomBytes.subarray(4); 31 32 randomPart1[0] = (randomPart1[0] & 0x0F) | 0x70; // version 33 randomPart2[0] = (randomPart2[0] & 0x3F) | 0x80; // variant 34 35 return [ 36 timestampHex.slice(0, 8), // first 4 bytes of timestamp 37 timestampHex.slice(8, 12), // last 2 bytes of timestamp 38 toHexString(randomPart1), // version 7 (2 bytes) 39 toHexString(randomPart2), // variant+random (2 bytes) 40 toHexString(randomPart3), // remaining 6 bytes 41 ].join('-'); // 00000000-0000-0000-0000-000000000000 42} 43 44/** 45 * Validate a UUIDv7 (Time-Sortable Identifier). 46 * @param {string} id 47 * @returns {number} 48 * The Unix timestamp encoded in the UUIDv7. 49 */ 50export function validateId(id) { 51 return parseInt(id.match(re).slice(1, 3).join(''), 16); 52}
Sign up or login to add to the discussion