2015-04-30 16 views
5

Tôi đang xây dựng một API HMAC và tôi có vấn đề kiểm tra băm với Paw.Hashes không giống nhau giữa PHP và Paw REST Client

On Paw Tôi có tải trọng này:

GET:/hello/world:"":9a6e30f2016370b6f2dcfb6880501d7f2305d69bout 

và một tùy chỉnh biến HMAC-SHA256 (trên thực tế hoạt động like this mà bộ nó trong tiêu đề X-Hash

X-Hash: 4Cq2yehWumDcUk1dYyfhm6qWjJVBkOCB8o12f5l0WGE= 

Trong API PHP của tôi. Tôi có cùng một điều:

GET:/hello/world:"":9a6e30f2016370b6f2dcfb6880501d7f2305d69bout 

và sử dụng:

hash_hmac('sha256', $this->getPayload(), '9a6e30f2016370b6f2dcfb6880501d7f2305d69bout', false); 

Vì vậy, khi so sánh băm:

Paw: 4Cq2yehWumDcUk1dYyfhm6qWjJVBkOCB8o12f5l0WGE= 
PHP: 6961b9d1f6e986c49d963cbebd691fa68dfa59b4ce3b7f05320c2d43eae3c7c3 

Họ rất khác nhau. Bất kỳ ý tưởng tại sao là điều đó?

Cập nhật

Mã Paw:

function evaluate(context){ 
    var loc = getLocation(context.getCurrentRequest().url); 

    var payload = ""; 
    payload += context.getCurrentRequest().method + ':'; 
    payload += loc.pathname + ':'; 
    payload += JSON.stringify(context.getCurrentRequest().body) + ':'; 
    payload += "9a6e30f2016370b6f2dcfb6880501d7f2305d69bout"; // Private key 
    return payload; 
}; 

function getLocation(href) { 
    var match = href.match(/^(https?\:)\/\/(([^:\/?#]*)(?:\:([0-9]+))?)(\/[^?#]*)(\?[^#]*|)(#.*|)$/); 
    return match && { 
     protocol: match[1], 
     host: match[2], 
     hostname: match[3], 
     port: match[4], 
     pathname: match[5], 
     search: match[6], 
     hash: match[7] 
    } 
} 

PHP Code (với rất nhiều ý kiến):

if (strpos(strtoupper($authHeader), 'HMAC') !== 0) { 
    echo 'out'; 
    throw new HttpForbiddenException(); 
} 
else { 
    $hmacSignature = $app->request->headers()->get('X-Hash'); 
    $publicKey = $app->request->headers()->get('X-Public'); 

    if (empty($hmacSignature) || empty($publicKey)) { 
     echo 'out2'; 
     throw new HttpForbiddenException(); 
    } 
    else { 

     $this->hmacManager->setPublicKey($publicKey); 
     print '$publickey = ' . $publicKey . '<br>'; 

     // Validate if base64_encoded or not 
     if(base64_decode($hmacSignature, true) !== FALSE) { 
      $binaryString = base64_decode($hmacSignature); 
      $hmacSignature = bin2hex($binaryString); 
      print 'decoding ' . '<br>'; 
     } 
     $this->hmacManager->setHmacSignature($hmacSignature); 
     print '$hmacSignature = ' . $hmacSignature . '<br>'; 

     $this->hmacManager->setRequestMethod($app->request->getMethod()); 
     print 'method = ' . $app->request->getMethod() . '<br>'; 
     $this->hmacManager->setRequestResourceUri($app->request->getResourceUri()); 
     print 'uri = ' . $app->request->getResourceUri() . '<br>'; 

     $requestBody = $app->request()->getBody(); 
     if (Utils::isJson($requestBody)) { 
      $requestBody = json_decode($requestBody); 
     } 
     $this->hmacManager->setRequestBody(json_encode($requestBody)); 
     print 'body = ' . json_encode($requestBody) . '<br>'; 

     print 'private key = ' . $this->hmacManager->getPrivateKey() . '<br>'; 

     $payload = ''; 
     $payload .= $this->hmacManager->getRequestMethod() . ":"; 
     $payload .= $this->hmacManager->getRequestResourceUri() . ":"; 
     $payload .= $this->hmacManager->getRequestBody() . ":"; 
     $payload .= $this->hmacManager->getPrivateKey(); 
     print 'PHP payload [' . $payload . ']'; 
     $this->hmacManager->setPayload($payload); 

     $hmacValue = $this->hmacManager->generateHmac(); 
     $isValid = $this->hmacManager->isValid($this->hmacManager->generateHmac(), $hmacSignature); 

     if ($isValid !== true) { 
      echo 'out3'; 
      throw new HttpForbiddenException(); 
     } 
    } 
} 

generateHmac từ một lớp khác:

public function generateHmac() 
{ 
    print 'Generating HMAC' . '<br>'; 
    $algorithm = $this->getAlgorithm(); 
    print 'algo ' . $algorithm . '<br>'; 
    $privateKey = $this->getPrivateKey(); 
    print 'privk ' . $privateKey . '<br>'; 

    if (empty($algorithm)) { 
     throw new \RuntimeException('Algorithm must be set and not empty'); 
    } elseif (empty($privateKey)) { 
     throw new \RuntimeException('Private key must be set and not empty'); 
    } 

    print 'payload ' . $this->getPayload() . '<br>'; 
    $hash = hash_hmac($this->getAlgorithm(), $this->getPayload(), $this->getPrivateKey(), false); 
    print 'php hasj: ' . $hash . '<br>'; 

    return $hash; 
} 

Cuối cùng, đây là báo cáo đầu ra:

$publickey = 95f97b93560f951b4cae46c86d03d9b1a81d4ae8 
decoding 
$hmacSignature = e02ab6c9e856ba60dc524d5d6327e19baa968c954190e081f28d767f99745861 

method = GET 
uri = /hello/world 
body = "" 
private key = 9a6e30f2016370b6f2dcfb6880501d7f2305d69bout 
PHP payload [GET:/hello/world:"":9a6e30f2016370b6f2dcfb6880501d7f2305d69bout] 

Generating HMAC 
algo sha256 
privk 9a6e30f2016370b6f2dcfb6880501d7f2305d69bout 
payload GET:/hello/world:"":9a6e30f2016370b6f2dcfb6880501d7f2305d69bout 
php hash: 6961b9d1f6e986c49d963cbebd691fa68dfa59b4ce3b7f05320c2d43eae3c7c3 

Hy vọng điều đó sẽ hữu ích!

Trả lời

4

Hàm băm được mã hóa base64 trong khi mã băm PHP ở dạng thập lục phân. Vì vậy, giải mã băm chân đầu tiên:

$binary = base64_decode($pawHash); 
$hex = bin2hex($binary); 

Và sau đó so sánh này với băm của riêng bạn.

+0

Tôi không thể làm ngược lại? Giải mã băm được tạo ra trong Paw trước khi gửi nó để API của tôi là như vậy? Hoặc có lẽ phát hiện nếu nó được mã hóa base64? – Vallieres

+0

Vẫn không hoạt động. Tôi đã làm như bạn nói (và kiểm tra xem base64_decode (str, true)! == FALSE) để chắc chắn nó là một chuỗi base64 nhưng nó bây giờ cho tôi băm này: e02ab6c9e856ba60dc524d5d6327e19baa968c954190e081f28d767f99745861 vẫn rất khác với những gì tôi có trong PHP. – Vallieres

+0

Thật khó để nói những gì có thể là vấn đề mà không nhìn thấy phần còn lại của mã. Nó có thể là một cái gì đó sai trái với trọng tải ví dụ.Ngay cả một sự khác biệt nhỏ và băm sẽ trông hoàn toàn khác nhau. –

2

Chúng tôi vừa thêm Base 64 to Hex conversion dynamic values mới, điều này sẽ giải quyết được sự cố của bạn.

Quấn chữ ký giá trị động HMAC của bạn bên trong cơ sở 64 mới để Hex một, và bạn sẽ nhận được một chữ ký hợp lệ thập lục phân:

Hexadecimal HMAC signature with Paw

Bạn có thể cài đặt giá trị này mới năng động ở đây: Base 64 to Hex Dynamic Value

+0

Tuyệt vời, cảm ơn Micha! – bswinnerton

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