Tpay
API

Notyfikacje

Notyfikacje inaczej webhooks to mechanizm, który umożliwia aplikacjom otrzymywanie powiadomień o określonych zdarzeniach w czasie rzeczywistym. W kontekście Tpay API, webhooki są wykorzystywane do informowania Twojego serwera o różnych wydarzeniach związanych z transakcjami, zwrotami lub tokenizacją kart.

Bezpieczeństwo

Wszystkie powiadomienia POST są podpisane podpisem JWS.

Korzystamy z RFC 7515: JSON Web Signature (JWS).

Podpis jest dostępny w nagłówku X-JWS-Signature, który jest jednym z nagłówków HTTP dołączanych do powiadomień.

Treść powiadomienia powinna być weryfikowana na podstawie publicznie dostępnych certyfikatów:

Dzięki temu możesz upewnić się, że powiadomienie pochodzi z zaufanego źródła i że jego treść nie została zmieniona podczas transmisji.

Ze względów bezpieczeństwa weryfikacja podpisu JWS jest obowiązkowa.

Uwaga

Nie udostępniamy listy adresów IP, z których przychodzą powiadomienia w celu dodania ich do whitelisty, ponieważ adresy te są dynamiczne. Dlatego zaimplementuj algorytm weryfikacji podpisu JWS, aby Twój system był w pełni bezpieczny.

Przykład implementacji walidacji JWS:

<?php
// Get Request X-JWS-Signature header
$jws = isset($_SERVER["HTTP_X_JWS_SIGNATURE"])
    ? $_SERVER["HTTP_X_JWS_SIGNATURE"]
    : null;
if (null === $jws) {
    exit("FALSE - Missing JSW header");
}
// Extract JWS header properties
$jwsData = explode(".", $jws);
$headers = isset($jwsData[0]) ? $jwsData[0] : null;
$signature = isset($jwsData[2]) ? $jwsData[2] : null;
if (null === $headers || null === $signature) {
    exit("FALSE - Invalid JWS header");
}
// Decode received headers json string from base64_url_safe
$headersJson = base64_decode(strtr($headers, "-_", "+/"));
// Get x5u header from headers json
$headersData = json_decode($headersJson, true);
$x5u = isset($headersData["x5u"]) ? $headersData["x5u"] : null;
if (null === $x5u) {
    exit("FALSE - Missing x5u header");
}
// Check certificate url
$prefix = "https://secure.tpay.com";
if (substr($x5u, 0, strlen($prefix)) !== $prefix) {
    exit("FALSE - Wrong x5u url");
}
// Get JWS sign certificate from x5u uri
$certificate = file_get_contents($x5u);
// Verify JWS sign certificate with Tpay CA certificate
// Get Tpay CA certificate to verify JWS sign certificate. CA certificate be cached locally.
$trusted = file_get_contents("https://secure.tpay.com/x509/tpay-jws-root.pem");
// in php7.4+ with ext-openssl you can use openssl_x509_verify
if (1 !== openssl_x509_verify($certificate, $trusted)) {
    exit("FALSE - Signing certificate is not signed by Tpay CA certificate");
}
// or using phpseclib
$x509 = new \phpseclib3\File\X509();
$x509->loadX509($certificate);
$x509->loadCA($trusted);
if (!$x509->validateSignature()) {
    exit("FALSE - Signing certificate is not signed by Tpay CA certificate");
}
// Get request body
$body = file_get_contents("php://input");
// Encode body to base46_url_safe
$payload = str_replace("=", "", strtr(base64_encode($body), "+/", "-_"));
// Decode received signature from base64_url_safe
$decodedSignature = base64_decode(strtr($signature, "-_", "+/"));
// Verify RFC 7515: JSON Web Signature (JWS) with ext-openssl
// Get public key from certificate
$publicKey = openssl_pkey_get_public($certificate);
if (
    1 !==
    openssl_verify(
        $headers . "." . $payload,
        $decodedSignature,
        $publicKey,
        OPENSSL_ALGO_SHA256
    )
) {
    exit("FALSE - Invalid JWS signature");
}
// or using phpseclib
$publicKey = $x509
    ->getPublicKey()
    ->withHash("sha256")
    ->withPadding(\phpseclib3\Crypt\RSA::SIGNATURE_PKCS1);
if (!$publicKey->verify($headers . "." . $payload, $decodedSignature)) {
    exit("FALSE - Invalid JWS signature");
}
// JWS signature verified successfully.
// Process request data and send valid response to notification service.
$transactionData = $_POST;
echo "TRUE";

Pamiętaj, że jest to tylko podstawowy przykład, który ma pomóc Ci zrozumieć proces weryfikacji podpisu JWS i powinien być dostosowany do Twoich wymagań. Istnieje wiele zewnętrznych bibliotek do weryfikacji tokenów JWS. Listę tych bibliotek w różnych językach można znaleźć na stronie https://jwt.io/libraries.

Idempotentna obsługa powiadomień

Twój system musi być przygotowany na sytuację, w której jedno powiadomienie zostanie wysłane więcej niż jeden raz. Ponowne przesłanie powiadomienia nie może skutkować ponowną realizacją usługi, wydaniem towarów ani żadnymi innymi operacjami o charakterze nieodwracalnym. Każde powiadomienie dla danej transakcji będzie zawsze zawierać ten sam identyfikator, co pozwala na bezpieczną weryfikację i zapobieganie zdublowanym operacjom.

Wymagania i ograniczenia systemu powiadomień

System powiadomień nie obsługuje przekierowań 302 i 301.

Oznacza to, że nie jest możliwe przekierowywanie powiadomień wysyłanych z wynikowego URL na inny adres. Jeśli system sprzedawcy jest skonfigurowany, aby na przykład przekierowywać z HTTP na HTTPS, należy wpisać docelowy adres, który będzie odbierał powiadomienia po wszystkich przekierowaniach.

Poprawność odbierania powiadomień można zweryfikować za pomocą narzędzia do testowania powiadomień.

Serwery Tpay.com są wyposażone w zaporę sieciową, która blokuje ruch na innych portach niż standardowe porty www (tj. 80, 8080, 443).

Obecnie obsługiwanym protokołem przez Tpay jest protokół TLS 1.2, który zapewnia poufność i integralność transmisji danych oraz uwierzytelnianie serwera. Serwery używające starszych protokołów, takich jak SSLv3, mogą powodować błąd w odbieraniu powiadomień.

Automatyczne ponowne wysyłanie powiadomień

Mechanizm powiadomień, gdy nie otrzyma poprawnej odpowiedzi, będzie próbował wysłać powiadomienia zgodnie z harmonogramem powiadomień.

Zakres PowiadomieńInterwał czasowy
1 - 10 powiadomienieCo 1 minutę
11 - 20 powiadomienieCo 3 minuty
21 - 30 powiadomienieCo 10 minut
31 - 35 powiadomienieCo 1 godzinę
36 powiadomienie12 godzin po ostatnim powiadomieniu
37 powiadomienie24 godziny po ostatnim powiadomieniu
Uwaga

System przestanie ponawiać wysyłanie powiadomień po otrzymaniu odpowiedzi HTTP z kodem 404 Not Found.

Po trzeciej niepoprawnej odpowiedzi z Twojego systemu, na adres e-mail sprzedawcy zostanie wysłana wiadomość informacyjna. W takim przypadku należy poprawić skrypt odbierający, aby prawidłowo przetwarzał przekazane parametry.

Zalecamy również upewnienie się, że podpis JWS przeszedł poprawną walidacje, skonfigurowano identyfikator sprzedawcy (Merchant ID) oraz kod bezpieczeństwa (dawniej Kod Potwierdzający).

Manualne ponowne wysyłanie powiadomień

System pozwala sprzedawcom na ponowne wysyłanie powiadomień dotyczących ich transakcji. Obecnie w zakładce szczegółów transakcji dostępne są następujące opcje:

  1. Wysyłanie powiadomień za pomocą przycisku Wyślij ponownie. Powiadomienie zostanie wysłane na URL punktu końcowego powiadomień. Jeśli podczas tworzenia transakcji nie zdefiniowano URL wyniku lub nie został on ustawiony w Panelu Akceptanta, ta opcja nie będzie dostępna.
  2. Wysyłanie przypomnienia o niedokończonej transakcji na adres e-mail płatnika. Transakcja, która nie została opłacona przez płatnika, otrzymuje status pending. Dla takich transakcji możliwe jest wysłanie przypomnienia o niedokończonej transakcji na adres e-mail płatnika podany na początku transakcji. Płatnik otrzyma wiadomość umożliwiającą dokończenie płatności. Opcja Wyślij przypomnienie, może być używana raz na 3 godziny.

Notyfikacja po zaksięgowaniu transakcji

Gdy transakcja zostanie poprawnie zaksięgowana wysyłamy powiadomienie POST z typem zawartości application/x-www-form-urlencoded do punktu końcowego Twojego systemu.

Konfiguracja adresu notyfikacji

Endpoint, na który zostanie wysłana notyfikacja o zaksięgowaniu transakcji, możesz skonfigurować w Panelu Akceptanta (Ustawienia > Powiadomienia).

Jeśli masz zaznaczoną opcję Zezwól na nadpisanie, możesz podać adres URL endpointa w parametrze callbacks.notification.url podczas tworzenia transakcji, na który zostanie wysłane powiadomienie zamiast domyślnego endpointu zapisanego w ustawieniach konta.

Przykład:

{
  "amount": 0.1,
  "description": "Test transaction Visa Mobile",
  "payer": {
    "email": "[email protected]",
    "name": "Jan Nowak"
  },
  "pay": {
    "groupId": 171
  },
  "callbacks": {
    "notification": {
      "url": "https://www.your-endpoint.com"
    }
  }
}

Parametry notyfikacji

Po każdej udanej transakcji następujące parametry zostaną wysłane na Twój endpoint.

id
Numeryczny identyfikator przypisany do sprzedawcy podczas rejestracji.
tr_id
Tytuł transakcji przypisany przez system Tpay.
tr_date
Data utworzenia transakcji.
tr_crc
Ten parametr zawiera dokładną wartość przekazaną w żądaniu utworzenia transakcji z Twojego systemu, parametr hiddenDescription. Powinieneś go używać do identyfikacji ID zamówienia po swojej stronie.
tr_amount
Docelowa kwota transakcji.
tr_paid
Rzeczywista kwota zapłacona przez płatnika. Uwaga: w zależności od ustawień konta, wartość ta może się różnić od kwoty transakcji!
tr_desc
Opis transakcji.
tr_status
Powiadomienie o udanej płatności będzie zawierać słowo true. Powiadomienie o ręcznym zwrocie pełnej kwoty dokonanym z Panelu Akceptanta będzie zawierać słowo chargeback.
tr_error
Parametr informacyjny o błędzie. Ten parametr zawsze przyjmuje wartość none, ponieważ funkcjonalność statusu Error została wycofana.
tr_email
Adres e-mail płatnika.
md5sum
Suma kontrolna używana do weryfikacji parametrów wysyłanych do sprzedawcy. Ta suma kontrolna powinna zawsze być weryfikowana po stronie sprzedawcy, a dane odrzucane w przypadku konfliktu. Gdy kod weryfikacyjny sprzedawcy nie jest ustawiony, jego wartość przyjmuje się jako pusty ciąg znaków.
test_mode
Parametr informujący, czy transakcja została utworzona w trybie testowym, czy normalnym: transakcja testowa - 1, transakcja normalna - 0.
card_token
Token płatniczy wysyłany, jeśli płatność została dokonana kartą oraz został przesłany odpowiedni parametr pay.cardPaymentData.save:1, Sprawdź.
token_expiry_date
Data wygaśnięcia tokena w formacie MMYY. Obecna tylko, jeśli token ma datę wygaśnięcia.
card_tail
Ostatnie 4 cyfry numeru karty.
card_brand
Marka karty. Możliwe wartości to Visa lub Mastercard.

Dodatkowe parametry, EISOP.

tokenPaymentData_tokenValue
Token EISOP.
tokenPaymentData_initialTransactionId
Identyfikator transakcji inicjującej, dla której wykonano tokenizację.
tokenPaymentData_cardExpiryDate
Data ważności karty/tokena.
tokenPaymentData_cardBrand
Marka stokenizowanej karty.
tokenPaymentData_cardTail
Ostatnie cztery cyfry numeru stokenizowanej karty.

Oczekiwana odpowiedź

W odpowiedzi na powiadomienie o transakcji z Twojego serwera oczekujemy:

HTTP Code: 200

Body:

TRUE
Uwaga
  • Jeśli odpowiedź jest inna niż true, system zaplanuje ponowne wysłanie powiadomienia. Po kilku próbach z odpowiedziami innymi niż TRUE, wyślemy Ci e-mail z dodatkowymi szczegółami.

  • Aby zweryfikować parametr md5sum, użyj podobnego algorytmu: $md5sum = md5($id . $tr_id . $tr_amount . $tr_crc . $code);

    Parametr $code to kod zabezpieczający sprzedawcy. Znajdziesz go w Panelu Akceptanta (zakładka Powiadomienia -> Zabezpieczenia).

Notyfikacja po tokenizacji bez obciążenia

Gdy tokenizacja bez obciążenia, realizowana poprzez endpoint /tokens zostanie poprawnie zakończona to wysyłamy powiadomienie POST z typem zawartości application/json do wskazanego endpointu Twojego systemu.

Konfiguracja adresu notyfikacji

Endpoint, na który zostanie wysłana notyfikacja o tokenizacji, możesz ustawić w parametrze callbackUrl, podczas tworzenia tokenizacji.

Przykład:

{
  "payer": {
    "name": "Jan Nowak",
    "email": "[email protected]"
  },
  "callbackUrl": "https://your-page.com/webhook/tokens"
}

Parametry notyfikacji

Po każdej udanej tokenizacji następujące parametry zostaną wysłane na Twój endpoint.

data.token
64-znakowy alfanumeryczny token.
data.cardBrand
Jedna z dwóch wartości: Mastercard lub Visa.
data.cardTail
Ostatnie 4 cyfry stokenizowanej karty.
data.tokenExpiryDate
Data wygaśnięcia tokenu w formacie MMYY.
data.type
Typ tokenizacji (tokenization, tokenization_eisop).

Przykład:

{
  "type": "tokenization",
  "data": {
    "tokenizationId": "TO-XXX-XXXXX",
    "token": "fdc235...",
    "cardBrand": "Mastercard",
    "cardTail": "1111",
    "tokenExpiryDate": "0625"
  }
}

Oczekiwana odpowiedź

W odpowiedzi na powiadomienie o tokenizacji z Twojego serwera oczekujemy:

HTTP Code: 200

Body:

{
  "result": true
}
Uwaga

Jeśli wiadomość nie zostanie odebrana przez Twój serwer lub treść odpowiedzi będzie inna, ponowimy próbę zgodnie ze schematem.

Notyfikacja dla aktualizacji tokenu lub karty

Poinformujemy cię o każdej zmianie statusu tokenu płatniczego lub wizerunku karty w programie Tokenizacja Plus. Zobacz więcej.

Konfiguracja adresu notyfikacji

Endpoint, na który zostanie wysłana notyfikacja o aktualizacji tokenu, musisz skonfigurować w parametrze callbackUrl, podczas tworzenia tokenizacji.

Przykład:

{
  "payer": {
    "name": "Jan Nowak",
    "email": "[email protected]"
  },
  "callbackUrl": "https://your-page.com/webhook/tokens"
}

Parametry notyfikacji

Po każdej aktualizacji statusu tokenu następujące parametry zostaną wysłane na Twój endpoint.

type
token_update.
data.token
64-znakowy alfanumeryczny token.

Przykład:

{
  "type": "token_update",
  "data": {
    "token": "fdc235..."
  }
}

Oczekiwana odpowiedź

W odpowiedzi na powiadomienie o zmianie statusu tokenu z Twojego serwera oczekujemy:

HTTP Code: 200

Body:

{
  "result": true
}
Uwaga

Jeśli wiadomość nie zostanie odebrana przez Twój serwer lub treść odpowiedzi będzie inna, ponowimy próbę zgodnie ze schematem.

Po otrzymaniu powiadomienia o zmianie statusu tokenu zalecamy ponowne pobranie statusu tokenu wraz z wizerunkiem karty, aby zaktualizować informacje w swoim systemie, więcej informacji.

Notyfikacja Marketplace

Gdy płatność realizowana poprzez endpoint /marketplace/v1/transaction zostanie poprawnie zakończona to wysyłamy powiadomienie POST z typem zawartości application/json do punktu końcowego Twojego systemu.

Konfiguracja adresu notyfikacji

Endpoint, na który zostanie wysłana notyfikacja o transakcji marketplace, musisz skonfigurować w parametrze callbackUrl, podczas tworzenia transakcji marketplace.

{
  "payer": {
    "name": "Jan Nowak",
    "email": "[email protected]"
  },
  "callbackUrl": "https://your-page.com/webhook/tokens"
}

Parametry notyfikacji

Po każdej udanej transakcji marketplace następujące parametry zostaną wysłane na Twój endpoint.

type
marketplace_transaction.
data.transactionId
Ciąg znaków ID głównej transakcji (ULID zakodowany w formacie base32).
data.transactionTitle
Przyjazny użytkownikowi tytuł transakcji przypisany przez system Tpay.
data.transactionAmount
Wnioskowana kwota transakcji.
data.transactionPaidAmount
Rzeczywista kwota zapłacona przez płatnika. Obecnie system marketplace umożliwia tylko płatności, które odpowiadają dokładnej kwocie i walucie głównej transakcji. Płatności, które nie odpowiadają kwocie lub walucie głównej transakcji, będą automatycznie anulowane i zwracane płatnikowi.
data.transactionStatus
Pomyślne powiadomienie o płatności będzie zawierać słowo correct. Obecnie nie są dostępne żadne inne statusy.
data.transactionHiddenDescription
Ten parametr będzie zawierał dokładną wartość przekazaną przy tworzeniu transakcji z Twojego systemu. Możesz go użyć do identyfikacji ID zamówienia po swojej stronie.
data.payerEmail
Adres e-mail płatnika. Proszę zauważyć, że adres płatnika może się zmienić w trakcie procesu płatności.
data.transactionDate
Data utworzenia transakcji.
data.transactionDescription
Opis transakcji podany przy tworzeniu transakcji.
data.cardToken
Token używany przez metodę transakcji. Zostanie przesłany tylko raz po pomyślnej płatności kartą, jeśli zapis karty został zażądany. Nie będzie obecny w transakcjach z innym kanałem.

Oczekiwana odpowiedź

W odpowiedzi na powiadomienie o transakcji marketplace z Twojego serwera oczekujemy:

HTTP Code: 200

Body:

{
  "result": true
}
Uwaga

Jeśli wiadomość nie zostanie odebrana lub treść odpowiedzi będzie inna, ponowimy próbę zgodnie ze schematem.