Hiếp me
Hiếp me

Reputation: 125

md5hash from php to python but false

I'm try rewrite md5hash function from php to python3.2 but it's false:

php code:

function MD5Hash($str) {
    $m = md5($str);
    $s = '';
    foreach(explode("\n", trim(chunk_split($m, 2))) as $h) {
        $s .= chr(hexdec($h));
    }
    return $s;
}

and python code:

def md5hash(self, st):
    m   = hashlib.md5(st).hexdigest()
    print(str(st) +" : "+m)
    s   = bytes()
    for i in range(0, len(m), 2):
        s   += chr(int(m[i:min(i+2, len(m))], 16)).encode('utf-8')
    return s

i'm try with

PHP:

echo(base64_encode(MD5Hash(MD5Hash("123123"))));
result: KXJU6b/guPOcaC7aMLub4A==

Python:

print(base64.b64encode(self.md5hash(self.md5hash(b"123123"))))
result: fcOsw6VSwo5iHEvCjz98w7JMW09w

I unknown how to fix it,please help me :(

Upvotes: 3

Views: 135

Answers (1)

unutbu
unutbu

Reputation: 880627

Use binascii.unhexlify:

import base64
import hashlib
import binascii

def md5hash(st):
    m = hashlib.md5(st).hexdigest()
    # print(str(st) +" : "+m)
    s = binascii.unhexlify(m)
    return s

print(base64.b64encode(md5hash(md5hash(b"123123"))))

yields

KXJU6b/guPOcaC7aMLub4A==

By the way, it was the conversion to unicode and the back to bytes that screwed up your original computation. Encoding with utf-8 turns some unicodes into two bytes. It wasn't packing bytes the way you intended. (Put in a print statement tracking the value of

chr(int(m[i:min(i+2, len(m))], 16)).encode('utf-8')

and you'll see what I mean.) Although binascii.unhexlify is faster and easier to code, one way to salvage most of your code is to use a bytearray:

def md5hash(st):
    m = hashlib.md5(st).hexdigest()
    s = bytearray([int(m[i:min(i+2, len(m))], 16) for i in range(0, len(m), 2)])
    return s

Upvotes: 4

Related Questions