如何将UUID缩短到特定长度?

我想将UU​​ID用于数据库记录,但如果我将它用于URL,我希望它是5到8个字符。

我知道我需要使用SecureRandombase64 ,但是如何指定我需要的长度?

另一个答案指出,你不能得到一个真正的UUID,最多5-8个字符,但你可以稍微缩短它们。 UUID是128位整数,可以处理32个hex数字。 您可以轻松地为每个字符存储6位,并将长度减少到22个字符,这就是base 64编码。 标准base 64编码使用大写和小写字母,数字以及“+”和“/”来完成它。 如果用“ – ”和“_”替换“+”和“/”,最终会得到一个不必进行url编码的字符串。 您可以这样做(使用UUIDTools创建UUID):

 uuid = UUIDTools::UUID.random_create str = [uuid.raw].pack('m*').tr('+/','-_').slice(0..21) 

为了让你的价值回归:

 (str + "==\n").tr('-_','+/').unpack('m*').first if str =~ /^[a-zA-Z0-9_\-]{22}$/ 

这假设UUID可以放入原始格式,其中包含16个8位字符的字符串。 这是一个irb会话,展示了一个真实的例子:

 2.1.1 :016 > uuid=UUIDTools::UUID.random_create => # 2.1.1 :017 > uuid.raw => " \xD0{lR\xAFNS\xAF\xEAk:\xD0\xD0\xC6'" 2.1.1 :018 > str = [uuid.raw].pack('m*').tr('+/','-_').slice(0..21) => "INB7bFKvTlOv6ms60NDGJw" 2.1.1 :019 > uuid2 = (str + "==\n").tr('-_','+/').unpack('m*').first => " \xD0{lR\xAFNS\xAF\xEAk:\xD0\xD0\xC6'" 2.1.1 :022 > UUIDTools::UUID.parse_raw(uuid2) => # 

我在各种网站上使用此方法,我通常使用Postgres生成UUID作为表的主键并将它们作为ID传递。 它不会节省大量空间,但它确实使一些URL适合一个80字符的行,其中标准格式的完整UUID不会。 使用破折号,标准UUID为36个字符,因此22大小约为2/3。

你不能缩短UUID。

来自维基百科

UUID是16个八位字节(128位)的数字。

在其规范forms中,UUID由32个小写hex数字表示。

如果你做得更短,那就不再是UUID了。

有各种用于创建较短URL的技术。 只需搜索“URL缩短器”,您就会找到任意数量的gem。

我创建了两个基于Michael Chaney的单行function

 def encode(uuid) [uuid.tr('-', '').scan(/../).map(&:hex).pack('c*')].pack('m*').tr('+/', '-_').slice(0..21) end def decode(short_id) (short_id.tr('-_', '+/') + '==').unpack('m0').first.unpack('H8H4H4H4H12').join('-') end uuid = "355bf501-ffea-4f5a-a9e2-16074de6fcf2" => "355bf501-ffea-4f5a-a9e2-16074de6fcf2" encode(uuid) => "NVv1Af_qT1qp4hYHTeb88g" decode(_) => "355bf501-ffea-4f5a-a9e2-16074de6fcf2