Przejdź do głównej zawartości

Weryfikacja podpisów webhooków

Każda notyfikacja wysyłana z systemu Paymentic jest opatrzona kryptograficznym podpisem HMAC, który pozwala Twojej aplikacji upewnić się, że payload rzeczywiście pochodzi od nas i nie został zmodyfikowany po drodze. Jest to niezależna warstwa od zabezpieczeń transportowych (TLS, mTLS) — podpis weryfikuje treść, nie kanał.

Dlaczego to jest krytyczne

URL endpointu webhooka w Twojej infrastrukturze zwykle nie jest sekretem — pojawia się w konfiguracji wielu środowisk, logach, narzędziach monitorujących, dashboardach. Gdyby ktoś poznał ten adres, bez weryfikacji podpisu mógłby wysłać spreparowaną notyfikację w stylu "transakcja zakończona sukcesem" i doprowadzić do wydania towaru bez realnej płatności.

Walidacja podpisu HMAC gwarantuje, że:

  • żądanie zostało wygenerowane przez system posiadający Twój wspólny sekret podpisujący
  • treść żądania nie została zmieniona między naszym serwerem a Twoim
  • żądanie nie jest sklejką starszych żądań (dzięki polu X-Paymentic-Time)

Jak to działa

Paymentic przy każdej notyfikacji wysyła nagłówek X-Paymentic-Signature zawierający HMAC-SHA512 po konkatenacji wybranych pól nagłówka oraz pełnego body żądania. Twoje zadanie to policzyć podpis po swojej stronie z tego samego zestawu danych i porównać go z otrzymanym — w trybie porównania stało-czasowego (hash_equals w PHP, crypto.timingSafeEqual w Node), żeby nie wystawiać się na atak timingowy.

Pełną specyfikację algorytmu, strukturę danych wejściowych, przykłady implementacji w kilku językach oraz interaktywny walidator znajdziesz w sekcji Notyfikacje → Sygnatura.

Co sprawdzić po stronie integracji

Nawet mając poprawny kod liczący HMAC warto pilnować kilku rzeczy na poziomie całego endpointu webhooka:

  • Odrzucaj żądania bez nagłówka X-Paymentic-Signature natychmiast (HTTP 401), nie próbuj ich przetwarzać "best effort".
  • Weryfikuj X-Paymentic-Time — jeśli różnica względem bieżącego czasu serwera przekracza kilka minut, odrzuć żądanie. Chroni to przed replay attack z przechwyconego wcześniej żądania.
  • Nie loguj samego sekretu podpisującego w żadnych logach aplikacyjnych ani systemach observability.
  • Traktuj sekret jak hasło produkcyjne — trzymaj w sejfie (Vault, AWS Secrets Manager, podobne), a nie w repozytorium kodu.
  • Rotuj sekret po każdym incydencie, w którym mógł wyciec (wyciekły logi, kompromitacja maszyny dev, odejście pracownika z dostępem).