"""平台 ID 生成与校验(ADR-015 与 docs/contracts/README.md 生成规则)。 格式固定为 ````;解析时必须校验前缀与 UUID version。UUID 生成使用成熟实现 uuid-utils,不自行拼位。 """ import re from uuid import UUID from uuid_utils import uuid4, uuid7 _UUID_RE = re.compile(r"^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$") def new_id(prefix: str, *, version: int = 7) -> str: """生成带登记前缀的平台 ID;持久化资源默认 UUIDv7。""" value = uuid7() if version == 7 else uuid4() return f"{prefix}{value}" def parse_id(value: str, prefix: str, *, version: int = 7) -> UUID: """校验并解析平台 ID:前缀与 UUID version 均须匹配,否则抛 ValueError。""" if not value.startswith(prefix): raise ValueError(f"ID 前缀不合法:期望 {prefix!r}") raw = value[len(prefix) :] if not _UUID_RE.match(raw): raise ValueError("ID 不是 canonical 小写 UUID 文本") parsed = UUID(raw) if parsed.version != version: raise ValueError(f"ID version 不合法:期望 UUIDv{version}") return parsed def is_valid_id(value: str, prefix: str, *, version: int = 7) -> bool: try: parse_id(value, prefix, version=version) except ValueError: return False return True