Podstawy API
Stronicowanie
Każda lista wraca w tej samej kopercie z elementami od najnowszego i polem has_more. Kolejne strony pobierasz kursorem: starting_after z identyfikatorem ostatniego obiektu daje starsze, ending_before nowsze. Kursor jest stabilny nawet wtedy, gdy w międzyczasie dochodzą nowe obiekty, czego nie da się powiedzieć o numerach stron.
Klucz testowy w przykładach
Wklej klucz sk_test_ z panelu (zakładka Deweloperzy), a każdy przykład będzie gotowy do uruchomienia. Klucz zostaje w tej karcie przeglądarki, nie wysyłamy go nigdzie.
Przykłady używają Twojego klucza testowego. Produkcyjnego klucza nie przyjmujemy.
Koperta listy#
| Pole | Znaczenie |
|---|---|
object | zawsze list |
url | ścieżka listy, np. /v1/payments |
has_more | true, gdy w tym kierunku są kolejne obiekty |
data | tablica obiektów od najnowszego |
{
"object": "list",
"url": "/v1/payments",
"has_more": true,
"data": [
{"id": "pay_Cd34Ef56Gh78Ij", "object": "payment", "created": 1760000200},
{"id": "pay_Bc23De45Fg67Hi", "object": "payment", "created": 1760000100},
{"id": "pay_Ab12Cd34Ef56Gh", "object": "payment", "created": 1760000000}
]
}
Parametry stronicowania#
| Parametr | Znaczenie |
|---|---|
limit | liczba obiektów na stronie, od 1 do 100, domyślnie 10 |
starting_after | identyfikator obiektu; zwraca starsze od niego (następna strona) |
ending_before | identyfikator obiektu; zwraca nowsze od niego (poprzednia strona); nie łączyć ze starting_after |
created[gt], created[gte], created[lt], created[lte] | filtr po chwili utworzenia (znacznik Unix) |
Listy mają też filtry po polach zasobu: status, customer, payment_link, subscription, invoice dla płatności; payment dla zwrotów; email dla klientów; active dla planów i linków; type i delivered dla zdarzeń. Komplet jest przy każdej operacji listy w referencji.
Pobranie całej historii#
Pętla: pobierz stronę, zapamiętaj id ostatniego elementu, wyślij je jako starting_after, powtarzaj aż has_more będzie false. Przy regularnej synchronizacji zawęź zakres filtrem created[gte] z czasu ostatniego przebiegu.
curl "https://oplac.pl/api/v1/payments?limit=100&status=succeeded&created[gte]=1759276800" \
-H "Authorization: Bearer sk_test_TWOJ_KLUCZ"
# następna strona: id ostatniego obiektu z poprzedniej
curl "https://oplac.pl/api/v1/payments?limit=100&status=succeeded&created[gte]=1759276800&starting_after=pay_Ab12Cd34Ef56Gh" \
-H "Authorization: Bearer sk_test_TWOJ_KLUCZ"
function wszystkiePlatnosci(array $filtry): Generator
{
$ostatni = null;
do {
$zapytanie = http_build_query($filtry + ['limit' => 100] + ($ostatni ? ['starting_after' => $ostatni] : []));
$ch = curl_init('https://oplac.pl/api/v1/payments?' . $zapytanie);
curl_setopt_array($ch, [
CURLOPT_HTTPHEADER => ['Authorization: Bearer sk_test_TWOJ_KLUCZ'],
CURLOPT_RETURNTRANSFER => true,
]);
$strona = json_decode(curl_exec($ch), true);
foreach ($strona['data'] as $p) {
yield $p;
$ostatni = $p['id'];
}
} while ($strona['has_more']);
}
foreach (wszystkiePlatnosci(['status' => 'succeeded', 'created[gte]' => 1759276800]) as $payment) {
// ...
}
async function* wszystkiePlatnosci(filtry) {
let ostatni = null;
let strona;
do {
const q = new URLSearchParams({ ...filtry, limit: '100', ...(ostatni ? { starting_after: ostatni } : {}) });
const res = await fetch(`https://oplac.pl/api/v1/payments?${q}`, {
headers: { Authorization: 'Bearer sk_test_TWOJ_KLUCZ' },
});
strona = await res.json();
for (const p of strona.data) {
yield p;
ostatni = p.id;
}
} while (strona.has_more);
}
for await (const payment of wszystkiePlatnosci({ status: 'succeeded', 'created[gte]': '1759276800' })) {
// ...
}
import requests
def wszystkie_platnosci(**filtry):
ostatni = None
while True:
params = {**filtry, "limit": 100}
if ostatni:
params["starting_after"] = ostatni
strona = requests.get(
"https://oplac.pl/api/v1/payments",
headers={"Authorization": "Bearer sk_test_TWOJ_KLUCZ"},
params=params,
).json()
for p in strona["data"]:
yield p
ostatni = p["id"]
if not strona["has_more"]:
return
for payment in wszystkie_platnosci(status="succeeded", **{"created[gte]": 1759276800}):
...
HTTP/1.1 200 OK
{
"object": "list",
"url": "/v1/payments",
"has_more": false,
"data": [
{
"id": "pay_Ab12Cd34Ef56Gh",
"object": "payment",
"amount": 12900,
"currency": "PLN",
"status": "succeeded",
"created": 1760000000
}
]
}
Na co uważać#
-
starting_afteriending_beforeprzyjmują identyfikator obiektu z tej samej listy. Identyfikator z innego trybu albo zasobu daje400 parameter_invalid. - Kursor nie wymaga, żeby obiekt dalej istniał w wyniku filtrów; stronicowanie liczy się po chwili utworzenia i identyfikatorze.
-
Listy zdarzeń (
GET /v1/events) stronicują się tak samo, z filtramitypeidelivered; to wygodna droga do nadrobienia zdarzeń po awarii odbiorcy webhooków. -
expand[]na liście działa na każdy element:expand[]=data.customer(samocustomerteż jest przyjmowane). Rozwinięte listy są cięższe, więc używaj mniejszegolimit.
Powiązane
Klucz testowy dostajesz od razu po zapisie
Adres e-mail, kod z maila i piaskownica z kodami BLIK. Produkcję włączasz sam w panelu: plan, dostawca płatności, klucz sk_live_. Wolisz, żeby wdrożenie w sklepie zrobił nasz zespół? To też jest za darmo.