2012-01-09 97 views
7

Tôi có chức năng sau trong C#, hàm băm mà tôi cần chuyển đổi thành PHP. Tôi đã thử một vài điều trong PHP nhưng tôi không nhận được kết quả tương tự (Tôi không ở tất cả các tốt với NET)Chuyển đổi hàm băm C# thành PHP

private static string GetSignature(string args, string privatekey) 
{ 
    var encoding = new System.Text.ASCIIEncoding(); 
    byte[] key = encoding.GetBytes(privatekey); 
    var myhmacsha256 = new HMACSHA256(key); 
    byte[] hashValue = myhmacsha256.ComputeHash(encoding.GetBytes(args)); 
    string hmac64 = Convert.ToBase64String(hashValue); 
    myhmacsha256.Clear(); 
    return hmac64; 
} 

One (sai) nỗ lực trong PHP là thế này:

function encode($data,$key) 
{ 
    return base64_encode(hash_hmac('sha256', $data, $key)); 
} 

các ĐÁP

Một biến thể nhẹ của những gì đã được đề xuất dưới đây bởi DampeS8N làm việc cho tôi.

function encode($data,$key) 
{ 
    iconv_set_encoding("input_encoding", "ASCII"); 
    iconv_set_encoding("internal_encoding", "ASCII"); 
    iconv_set_encoding("output_encoding", "ASCII"); 

    return base64_encode(hash_hmac('sha256', $data, $key, true)); 
} 

Hãy cũng không phải là tham số thứ tư của hash_hmac - bây giờ thiết lập là true cho sản lượng nguyên như dữ liệu nhị phân

+0

Bạn nên chấp nhận câu trả lời DampeS8Ns nếu anh ấy chỉ cho bạn đúng hướng. – jgauffin

Trả lời

6

tôi nghi ngờ dòng đầu tiên của mã .net của bạn là thủ phạm. PHP has no encoding for the string chính nó và vì vậy khi nó đến thời gian để băm nó hoặc là băm các byte định dạng chuỗi nội bộ PHP (không, ai đó có thể xác nhận?) Hoặc nhiều hơn khả năng là chuyển đổi sang cái gì khác đầu tiên. Trong trường hợp này có thể là unicode vốn không phải là cùng một byte mà chuỗi sẽ ở dạng ASCII như .net đang yêu cầu.

Lời khuyên của tôi là đảm bảo rằng PHP cũng đang sử dụng ASCII, with iconv, để cho phép khả năng tương tác.

function encode($data,$key) 
{ 
    return base64_encode(hash_hmac('sha256', iconv(iconv_get_encoding("internal_encoding"), "ASCII", $data), iconv(iconv_get_encoding("internal_encoding"), "ASCII", $key))); 
} 

Tôi không thể chắc chắn rằng mã ở trên sẽ xuất ra các băm mong muốn, tuy nhiên, vì tôi không có .net tiện dụng để kiểm tra mã ban đầu. Nhưng điều này có thể chỉ cho bạn đi đúng hướng.

Nếu cách này không hiệu quả, giá trị bên trong iconv_get_encoding( có thể là thủ phạm, hãy thử "output_encoding" hoặc "input_encoding". Cũng có thể bạn sẽ cần đặt cùng các giá trị này thành ASCII với iconv_set_encoding(.

Chúc may mắn!


Cập nhật! Đây là những gì cuối cùng đã làm việc:

function encode($data,$key) 
{ 
    iconv_set_encoding("input_encoding", "ASCII"); 
    iconv_set_encoding("internal_encoding", "ASCII"); 
    iconv_set_encoding("output_encoding", "ASCII"); 

    return base64_encode(hash_hmac('sha256', $data, $key, true)); 
} 
+0

Cảm ơn vì điều này. Nó hoàn toàn có ý nghĩa mặc dù doesnt dường như không hoạt động. Tôi có cùng một vấn đề mà tôi không có .net môi trường để kiểm tra với. Tôi cũng nghĩ rằng tôi vẫn cần mã hóa này.GetBytes (privatekey); – 32423hjh32423

+1

Điều đó chỉ cần nhận được các byte thô của ASCII cho khóa. Bởi vì gõ động trong PHP nó có thể được thực sự khó khăn để có được lúc đó và kiểm soát nó. Tôi chắc chắn nó là một số sự kết hợp của việc thiết lập những điều đúng với iconv_set_encoding (để đảm bảo rằng hash_hmac (không phải là hoàn tác tất cả các công việc khó khăn bạn đã thực hiện với iconv (chính nó) – DampeS8N

+0

Cảm ơn câu trả lời được đăng ở trên – 32423hjh32423

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