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!
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
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
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. –