2010-04-08 19 views
10

Tôi đang làm việc trong python trên appengine.Tạo băm cố định chiều dài trong python cho tham số url

Tôi đang cố gắng tạo giá trị "v" trong url của youtube (http://www.youtube.com/watch?v=XhMN0wlITLk) để truy xuất các thực thể cụ thể. Tự động lưu trữ dữ liệu tạo khóa nhưng nó quá dài (34 chữ số). Tôi đã thử nghiệm với hashlib để xây dựng của riêng tôi, nhưng một lần nữa tôi nhận được một chuỗi dài. Tôi muốn giữ nó dưới 11 chữ số (Tôi không phải làm việc với một số lượng lớn các thực thể) và các chữ cái và số được chấp nhận.

Dường như có một giải pháp khá chuẩn. Tôi có lẽ chỉ thiếu nó.

Trả lời

8

Bạn có thể sử dụng tự động tạo ra integer id của khóa để tạo băm. Một cách đơn giản để tạo băm sẽ là chuyển đổi số nguyên id thành base62 (chữ và số). Để tìm nạp đối tượng, chỉ cần chuyển đổi sang thập phân từ base62 và sử dụng get_by_id để truy lục đối tượng.

Dưới đây là một hàm chuyển đổi base62 đơn giản mà tôi đã sử dụng trong một trong các ứng dụng của mình.

import string 
alphabet = string.letters + string.digits 
max = 11 

def int_to_base62(num): 
    if num == 0: 
     return alphabet[0] 

    arr = [] 
    radix = len(alphabet) 
    while num: 
     arr.append(alphabet[num%radix]) 
     num /= radix 
    arr.reverse() 
    return (alphabet[0] * (max - len(arr))) + ''.join(arr) 

def base62_to_int(str): 
    radix = len(alphabet) 
    power = len(str) - 1 
    num = 0 
    for char in str: 
     num += alphabet.index(char) * (radix ** power) 
     power -= 1 
    return num 
+0

Hai liên kết này rất hữu ích. Vấn đề bây giờ là tìm ra cách lý tưởng để mã hóa và giải mã trong base62. Tôi đã làm một số đọc, là có một phương pháp bạn đề nghị? – LeRoy

+1

bạn có thể sử dụng kỹ thuật chuyển đổi cơ bản số cơ bản. Để làm cho chiều dài cố định băm, chỉ cần thêm một số không padding cho số base62. – z33m

5

Nếu bạn có giá trị duy nhất cho mọi thực thể, bạn có thể nhận phiên bản ngắn hơn bằng cách băm và cắt bớt. Các dấu gạch ngang như md5 hoặc sha1 được trộn đều, nghĩa là mỗi bit trong đầu ra có 50% cơ hội lật nếu bạn thay đổi một bit trong đầu vào. Nếu bạn cắt bớt băm, bạn chỉ đơn giản là tăng tỷ lệ cược của một vụ va chạm, nhưng bạn có thể làm cho sự cân bằng giữa chiều dài và tỷ lệ cược va chạm.

Mã hóa base64 an toàn Url là một tùy chọn tốt để chuyển băm thành văn bản.

orig_id = 'weiowoeiwoeciw0eijw0eij029j20d232weifw0jiw0e20d2' # the original id 
shorter_id = base64.urlsafe_b64encode(hashlib.md5(orig_id).digest())[:11] 

Với base64, bạn có 6 bit thông tin cho mỗi ký tự, 11 ký tự cho bạn 66 bit độc đáo hoặc 1 trong 2 ** 66 cơ hội va chạm.

+0

có lý do nào để bạn chọn chuyển đổi base64 trên base62 như những gì được đề xuất ở trên không? – LeRoy

+0

Base64 dường như luôn bao gồm "=" không thực sự là chuỗi truy vấn an toàn. – LeRoy

+0

Tôi sử dụng base64 trên base62 chỉ vì nó quen thuộc hơn. The = là phần đệm. Bạn đang cắt ngắn anyway, phải không? –

Các vấn đề liên quan