Trình tạo UUID v2
Tạo UUID v2 DCE Security với miền cục bộ và ID
UUID v2 là gì?
UUID v2 là phiên bản UUID DCE Security, được chuẩn hóa như một phần của thông số kỹ thuật Distributed Computing Environment (DCE) và được tham chiếu trong RFC 4122.
Cấu trúc tương tự như UUID v1, nhưng trường time_low 32-bit được thay thế bởi định danh cục bộ 32-bit (ví dụ POSIX UID).
UUID v2 cực kỳ hiếm trong phần mềm hiện đại. Hầu hết các nhà phát triển sẽ không bao giờ cần tạo một cái.
Cấu trúc UUID v2
UUID v2 có cùng định dạng 128-bit có gạch nối như các phiên bản UUID khác. Các trường khác với UUID v1 như sau:
| Trường | Bit | Mục đích |
|---|---|---|
| local_id | 32 | <code>local_id</code> — định danh domain cục bộ 32-bit (ví dụ POSIX UID từ <code>/etc/passwd</code>), thay thế trường time_low của UUID v1 |
| time_mid | 16 | <code>time_mid</code> — 16 bit giữa của timestamp UUID v1 bị cắt |
| time_hi+version | 16 | <code>time_hi_and_version</code> — 12 bit timestamp trên với nibble phiên bản được đặt thành <code>2</code> |
| variant+clock_hi | 8 | <code>clock_seq_hi_and_reserved</code> — các bit biến thể cộng phần cao của chuỗi đồng hồ |
| local_domain | 8 | <code>local_domain</code> — định danh domain: <code>0</code> = Người dùng POSIX (UID), <code>1</code> = Nhóm POSIX (GID), <code>2</code> = Tổ chức |
| node | 48 | <code>node</code> — địa chỉ MAC 48-bit của máy chủ tạo |
Ví dụ: 000003e8-92e0-21ef-8000-325096b39f47 — local_id 0x000003e8 = UID 1000, local_domain 0x00 = Người dùng POSIX
Giá trị Domain Cục bộ
Byte local_domain chỉ định loại định danh cục bộ được nhúng trong UUID:
Các giá trị domain được định nghĩa bởi thông số kỹ thuật DCE. Các giá trị 3–255 được dành riêng. Trong thực tế, chỉ domain 0 (Người/UID) thường gặp.
Tại sao UUID v2 Hiếm khi được Sử dụng
Ba đặc điểm làm cho UUID v2 không thực tế cho hầu hết các ứng dụng hiện đại:
Độ phân giải Timestamp Thô
Timestamp bị cắt xuống 28 bit (độ chi tiết khoảng 7,2 phút).
Không có Hỗ trợ Thư viện Tiêu chuẩn
Không giống UUID v1 và v4, UUID v2 không được hỗ trợ bởi hầu hết các thư viện UUID.
Ngữ nghĩa Đặc thù POSIX
Khái niệm domain cục bộ (UID/GID) vốn dĩ đặc thù POSIX và không có ý nghĩa đối với Windows hoặc môi trường đám mây.
Bối cảnh Lịch sử
UUID v2 được định nghĩa như một phần của Distributed Computing Environment (DCE/RPC) của Open Software Foundation vào đầu những năm 1990.
Mô hình bảo mật DCE giả định môi trường POSIX đồng nhất nơi mọi node tham gia vào namespace UID/GID chung.
- Internet chuyển từ môi trường POSIX đồng nhất sang kiến trúc đám mây không đồng nhất
- Xác thực hiện đại sử dụng token (JWT, OAuth) thay vì UID nhúng trong định danh
- UUID v4 (hoàn toàn ngẫu nhiên) và UUID v7 (theo thứ tự thời gian) đáp ứng các trường hợp sử dụng thực tế cho định danh duy nhất
- DCE/RPC chính nó đã không còn được sử dụng rộng rãi
RFC 4122 (2005) bao gồm UUID v2 bằng tham chiếu đến thông số kỹ thuật DCE.
RFC 9562 (2024) giữ lại UUID v2 để hoàn chỉnh lịch sử.
UUID v2 so với UUID v1
UUID v2 được dẫn xuất từ UUID v1. Đây là cách so sánh:
| Khía cạnh | UUID v1 | UUID v2 |
|---|---|---|
| Bit timestamp | 60 bit (độ chính xác ~100ns) | 28 bit (độ chính xác ~7,2 phút) |
| Định danh cục bộ | Không có | POSIX UID/GID 32-bit |
| Domain cục bộ | Không có | 0=UID, 1=GID, 2=Org |
| Trường node | Địa chỉ MAC | Địa chỉ MAC |
| Hỗ trợ thư viện | Được hỗ trợ rộng rãi | Hiếm khi được hỗ trợ |
| Tiêu chuẩn | RFC 4122 / RFC 9562 | Thông số kỹ thuật DCE (được tham chiếu bởi RFC 4122) |
| Sử dụng thực tế | ID theo thứ tự timestamp cũ (Cassandra) | Chỉ các bối cảnh DCE Security |
UUID v2 không cung cấp gì so với UUID v1 cho mục đích sử dụng chung. Không có lý do gì để chọn UUID v2 cho phát triển mới.
Ví dụ Mã
UUID v2 không có hỗ trợ gốc trong các thư viện tiêu chuẩn:
Python — triển khai thủ công
import uuid, struct, time
def uuid_v2(local_id: int, local_domain: int = 0) -> str:
"""
Generate a DCE Security UUID (v2).
local_domain: 0 = POSIX UID, 1 = POSIX GID, 2 = Org
local_id: 32-bit unsigned integer (e.g. os.getuid())
"""
# Get a v1 UUID for the time and node fields
v1 = uuid.uuid1()
fields = list(v1.fields) # [time_low, time_mid, time_hi_version, clock_seq_hi_variant, clock_seq_low, node]
# Replace time_low with local_id
fields[0] = local_id & 0xFFFFFFFF
# Replace version nibble: clear lower 12 bits of time_hi, set version 2
fields[2] = (fields[2] & 0x0FFF) | 0x2000
# Replace clock_seq_low with local_domain
fields[4] = local_domain & 0xFF
return str(uuid.UUID(fields=tuple(fields)))
import os
print(uuid_v2(os.getuid(), local_domain=0)) # POSIX UID
print(uuid_v2(os.getgid(), local_domain=1)) # POSIX GID
Go — ghi chú
// The standard "github.com/google/uuid" package does NOT support v2. // You would need to implement it manually, similar to the Python example above. // Most Go developers use v4 or v7 for new projects. import "github.com/google/uuid" v4 := uuid.New() // v4 — recommended for most use cases v7, _ := uuid.NewV7() // v7 — time-ordered, ideal for database primary keys
JavaScript — trích xuất trường
Để trích xuất local_id và domain từ chuỗi UUID v2 hiện có:
// Extracting fields from a UUID v2 string
const uuidStr = '000003e8-1234-2abc-8200-a1b2c3d4e5f6'
// ^^^^^^^^ ^^^^ ^ ^^
// local_id ver variant+clockSeqHi
// ^^ = local_domain (00 = POSIX UID)
const parts = uuidStr.split('-')
const localId = parseInt(parts[0], 16) // → 1000 (0x3e8)
const version = parseInt(parts[2][0], 16) // → 2
const localDomain = parseInt(parts[3].slice(2), 16) // low byte of octet pair
const DOMAIN_NAMES = ['POSIX UID', 'POSIX GID', 'Org']
console.log(`Local ID: ${localId}`) // Local ID: 1000
console.log(`Version: ${version}`) // Version: 2
console.log(`Domain: ${DOMAIN_NAMES[localDomain]}`) // Domain: POSIX UID
google/uuid hỗ trợ tạo UUID v2 qua uuid.NewDCEGroup() và uuid.NewDCEPerson().