Presta atención porque en esta sección encontrarás el hallazgo que buscas.
Solución:
Convierta los bytes subyacentes a un valor base64, eliminando el =
relleno y la nueva línea.
Probablemente quieras usar el base64.urlsafe_b64encode()
función para evitar el uso /
y +
(_
y -
se utilizan en su lugar), por lo que el resultado string se puede utilizar como un elemento de ruta de URL:
>>> import uuid, base64
>>> base64.urlsafe_b64encode(uuid.uuid1().bytes).rstrip(b'=').decode('ascii')
'81CMD_bOEeGbPwAjMtYnhg'
El revés:
>>> uuid.UUID(bytes=base64.urlsafe_b64decode('81CMD_bOEeGbPwAjMtYnhg' + '=='))
UUID('f3508c0f-f6ce-11e1-9b3f-002332d62786')
Para convertir eso en funciones genéricas:
from base64 import urlsafe_b64decode, urlsafe_b64encode
from uuid import UUID
def uuid2slug(uuidstring):
return urlsafe_b64encode(UUID(uuidstring).bytes).rstrip(b'=').decode('ascii')
def slug2uuid(slug):
return str(UUID(bytes=urlsafe_b64decode(slug + '==')))
Esto le brinda un método para representar el UUID de 16 bytes en una forma más compacta. Comprima más y perderá información, lo que significa que no puede descomprimirlo nuevamente al UUID completo. El rango completo de valores que pueden representar 16 bytes nunca se ajustará a menos de 22 caracteres base64, lo que necesita 4 caracteres por cada tres bytes de entrada y cada carácter codifica 6 bits de información.
YouTube es único string por lo tanto, no se basa en un UUID completo de 16 bytes, sus ID de 11 caracteres probablemente se almacenen en la base de datos para facilitar la búsqueda y se basen en un valor más pequeño.
Para aquellos que buscan específicamente una forma de acortar uuids de una manera segura para URL, la respuesta realmente útil de @MartijnPieters se puede simplificar un poco usando el base64
módulo para manejar los caracteres que no son seguros para URL similar al comentario sobre esa respuesta de @okoboko (sin algunos bits innecesarios).
import base64
import uuid
# uuid to b64 string and back
uuid_to_b64str = base64.urlsafe_b64encode(uuid.uuid1().bytes).decode('utf8').rstrip('=n')
b64str_to_uuid = uuid.UUID(bytes=base64.urlsafe_b64decode(f'uuid_to_b64str=='))
# uuid string to b64 string and back
uuidstr_to_b64str = base64.urlsafe_b64encode(uuid.UUID(str(uuid.uuid1())).bytes).decode('utf8').rstrip('=n')
b64str_to_uuidstr = str(uuid.UUID(bytes=base64.urlsafe_b64decode(f'uuidstr_to_b64str==')))