Формирование сигнатуры Webhook

Вычисляется хеш из предварительно отсортированных по ключу от a-zA-Z тела хука по алгоритму sha256 hmac без экранированных слешей и unicode символов.

Секретный ключ для вычисления хэша:

  • для оплаты “Дополнительный ключ” кассы.
  • для выводов “Дополнительный ключ” пользователя.

Хэш указывается в заголовке x-api-sha256-signature

Пример:

  1. 1.x-api-sha256-signature:
  2. 2.e582b14dd13f8111711e3cb66a982fd7bff28a0ddece8bde14a34a5bb4449136

Секретный ключ вычисленного хеша: example

Данные для подписи:

  1. 1.{
  2. 2. "amount": "100.00",
  3. 3. "credited": "95.50",
  4. 4. "custom_fields": { "user": 1 },
  5. 5. "invoice_id": "a3e9ff6f-c5c1-3bcd-854e-4bc995b1ae7a",
  6. 6. "order_id": "c78d8fe9-ab44-3f21-a37a-ce4ca269cb47",
  7. 7. "pay_service": "card",
  8. 8. "pay_time": "2023-04-06 16:27:59",
  9. 9. "payer_details": "553691******1279",
  10. 10. "status": "success",
  11. 11. "type": 1
  12. 12.}

Примеры кода:

  1. 1.import json
  2. 2.import hmac
  3. 3.import hashlib
  4. 4.
  5. 5.
  6. 6.# Check signature
  7. 7.def check_signature(hook_body: dict, header_signature, secret_key):
  8. 8. sorted_hook_json = json.dumps(hook_body, sort_keys=True, separators=(', ', ': '))
  9. 9. calc_sign = hmac.new(
  10. 10. secret_key,
  11. 11. msg=sorted_hook_json.encode('utf-8'),
  12. 12. digestmod=hashlib.sha256
  13. 13. ).hexdigest()
  14. 14. return hmac.compare_digest(header_signature, calc_sign)
  15. 15.
  16. 16.
  17. 17.hook = {
  18. 18. "credited": "95.50",
  19. 19. "custom_fields": { "user": 1 },
  20. 20. "invoice_id": "a3e9ff6f-c5c1-3bcd-854e-4bc995b1ae7a",
  21. 21. "order_id": "c78d8fe9-ab44-3f21-a37a-ce4ca269cb47",
  22. 22. "pay_service": "card",
  23. 23. "amount": "100.00",
  24. 24. "pay_time": "2023-04-06 16:27:59",
  25. 25. "payer_details": "553691******1279",
  26. 26. "status": "success",
  27. 27. "type": 1
  28. 28.}
  29. 29.head_sign = 'e582b14dd13f8111711e3cb66a982fd7bff28a0ddece8bde14a34a5bb4449136'
  30. 30.secret = b'example'
  31. 31.
  32. 32.# Is signature of hook correct
  33. 33.check_signature(hook, head_sign, secret) # True
  1. 1.function checkSignature(string $hookJson, string $headerSignature, string $secretKey): bool
  2. 2.{
  3. 3. $hookArr = json_decode($hookJson, true);
  4. 4. ksort($hookArr);
  5. 5. $hookJsonSorted = json_encode($hookArr);
  6. 6. $calculatedSignature = hash_hmac('sha256', $hookJsonSorted, $secretKey);
  7. 7. return hash_equals($headerSignature, $calculatedSignature);
  8. 8.}
  9. 9.
  10. 10.$hookJson = '{
  11. 11. "order_id": "c78d8fe9-ab44-3f21-a37a-ce4ca269cb47",
  12. 12. "credited": "95.50",
  13. 13. "custom_fields": { "user": 1 },
  14. 14. "invoice_id": "a3e9ff6f-c5c1-3bcd-854e-4bc995b1ae7a",
  15. 15. "pay_service": "card",
  16. 16. "pay_time": "2023-04-06 16:27:59",
  17. 17. "payer_details": "553691******1279",
  18. 18. "status": "success",
  19. 19. "type": 1,
  20. 20. "amount": "100.00"
  21. 21.}';
  22. 22.$headerSignature = 'e582b14dd13f8111711e3cb66a982fd7bff28a0ddece8bde14a34a5bb4449136';
  23. 23.$secretKey = 'example';
  24. 24.
  25. 25.# Is signature of hook correct
  26. 26.checkSignature($hookJson, $headerSignature, $secretKey); # True