Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Generate fixed length hash in python for url parameter

I am working in python on appengine.

I am trying to create what is equivalent to the "v" value in the youtube url's (http://www.youtube.com/watch?v=XhMN0wlITLk) for retrieving specific entities. The datastore auto generates a key but it is way too long (34 digits). I have experimented with hashlib to build my own, but again I get a long string. I would like to keep it to under 11 digits (I am not dealing with a huge number of entities) and letters and numbers are acceptable.

It seems like there should be a pretty standard solution. I am probably just missing it.

like image 559
LeRoy Avatar asked Apr 08 '10 05:04

LeRoy


People also ask

How do you hash a URL?

To compute the hash prefix of a URL, follow these steps: Canonicalize the URL (see Canonicalization). Create the suffix/prefix expressions for the URL (see Suffix/Prefix Expressions). Compute the full-length hash for each suffix/prefix expression (see Hash Computations).

What does __ hash __ do in Python?

Call __hash__ on the key to compute the hash of the key. If the key is not hashable raise a TypeError. Store (hash_value, key, value) in an array at location hash_value % len(array) . If the array requires resizing, re-use the previously computed hash_value s to re-insert all previously stored values.


1 Answers

You can use the auto generated integer id of the key to generate the hash. A simple way to generate the hash would be to convert the integer id to base62 (alphanumeric). To fetch the object simply convert to decimal back from base62 and use get_by_id to retrieve the object.

Here is a simple base62 conversion function that i have used in one of my apps.

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
like image 140
z33m Avatar answered Oct 26 '22 21:10

z33m