PRO REST API
REST API w namespace polski-pro/v1 do zarządzania fakturami, ustawieniami i dokumentami prawnymi. Wymaga uwierzytelnienia i uprawnienia manage_woocommerce.
Uwierzytelnianie
Dział zatytułowany „Uwierzytelnianie”API wymaga dwóch elementów autoryzacji:
- Nonce WordPress - nagłówek
X-WP-Noncez wartością wygenerowaną przezwp_create_nonce('wp_rest') - Uprawnienie - zalogowany użytkownik musi posiadać capability
manage_woocommerce
Przykład uwierzytelnienia (JavaScript)
Dział zatytułowany „Przykład uwierzytelnienia (JavaScript)”const response = await fetch('/wp-json/polski-pro/v1/invoices', { headers: { 'X-WP-Nonce': wpApiSettings.nonce, 'Content-Type': 'application/json', },});Przykład uwierzytelnienia (PHP / cURL)
Dział zatytułowany „Przykład uwierzytelnienia (PHP / cURL)”$nonce = wp_create_nonce('wp_rest');
$response = wp_remote_get( rest_url('polski-pro/v1/invoices'), [ 'headers' => [ 'X-WP-Nonce' => $nonce, ], ]);Brakujący lub nieprawidłowy nonce odrzuca WordPress z kodem rest_cookie_invalid_nonce i statusem 403. Zalogowany użytkownik bez uprawnienia manage_woocommerce dostaje 403 z kodem polski_pro_forbidden, i tak samo kończy się wywołanie bez zalogowania: kontroler faktur ustawia status 403 na sztywno, więc 401 tu nie występuje.
Endpointy faktur
Dział zatytułowany „Endpointy faktur”Pobranie listy faktur
Dział zatytułowany „Pobranie listy faktur”GET /wp-json/polski-pro/v1/invoicesParametry zapytania:
| Parametr | Typ | Domyślna | Opis |
|---|---|---|---|
order_id |
int |
brak | Filtr po ID zamówienia WooCommerce |
type |
string |
brak | Filtr typu: faktura_vat, proforma, korygujaca, paragon, packing_slip |
status |
string |
brak | Filtr statusu: draft, issued, sent, paid, cancelled |
page |
int |
1 |
Numer strony |
per_page |
int |
20 |
Liczba wyników na stronę, przycinana do zakresu 1-100 |
To jest cała lista zarejestrowanych parametrów. Endpoint nie przyjmuje zakresu dat ani wyszukiwania pełnotekstowego: filtrowanie po dacie i szukanie po numerze faktury lub nazwie kontrahenta trzeba zrobić po stronie klienta.
Odpowiedź (200 OK):
Ciałem odpowiedzi jest zwykła tablica obiektów faktur. Liczniki wracają w nagłówkach X-WP-Total i X-WP-TotalPages, a nie w ciele odpowiedzi. Wpisy listy nie zawierają pozycji: items wypełnia wyłącznie endpoint pojedynczej faktury.
[ { "id": 1, "order_id": 567, "original_invoice_id": null, "source_refund_id": null, "type": "faktura_vat", "type_label": "Faktura VAT", "number": "FV/2026/04/001", "status": "issued", "status_label": "Issued", "nip_seller": "9876543210", "nip_buyer": "1234567890", "buyer_name": "Firma Testowa Sp. z o.o.", "buyer_address": "ul. Testowa 1", "buyer_city": "Warszawa", "buyer_postcode": "00-001", "correction_reason": null, "net_total": 1000.00, "vat_total": 230.00, "gross_total": 1230.00, "currency": "PLN", "pdf_path": "/wp-content/uploads/polski-pro/invoices/FV-2026-04-001.pdf", "ksef_reference": null, "ksef_status": null, "issued_at": "2026-04-01T10:30:00+02:00", "created_at": "2026-04-01T10:30:00+02:00", "items": [] }]Utworzenie faktury z zamówienia
Dział zatytułowany „Utworzenie faktury z zamówienia”POST /wp-json/polski-pro/v1/invoicesParametry body (JSON):
| Parametr | Typ | Wymagany | Opis |
|---|---|---|---|
order_id |
int |
Tak | ID zamówienia WooCommerce |
type |
string |
Nie | Typ: faktura_vat (domyślnie), proforma, korygujaca, paragon, packing_slip |
Żądanie:
{ "order_id": 567, "type": "faktura_vat"}Odpowiedź (201 Created):
Utworzona faktura, w tym samym kształcie co wpisy listy powyżej. Nieznany type, brak zamówienia albo nieudane utworzenie zwracają 400 z polem message.
{ "id": 43, "order_id": 567, "original_invoice_id": null, "source_refund_id": null, "type": "faktura_vat", "type_label": "Faktura VAT", "number": "FV/2026/04/002", "status": "issued", "status_label": "Issued", "nip_seller": "9876543210", "nip_buyer": "1234567890", "buyer_name": "Firma Testowa Sp. z o.o.", "buyer_address": "ul. Testowa 1", "buyer_city": "Warszawa", "buyer_postcode": "00-001", "correction_reason": null, "net_total": 500.00, "vat_total": 115.00, "gross_total": 615.00, "currency": "PLN", "pdf_path": null, "ksef_reference": null, "ksef_status": null, "issued_at": "2026-04-05T14:00:00+02:00", "created_at": "2026-04-05T14:00:00+02:00", "items": []}Pobranie szczegółów faktury
Dział zatytułowany „Pobranie szczegółów faktury”GET /wp-json/polski-pro/v1/invoices/{id}Zwraca kompletne dane faktury wraz z pozycjami (items).
Odpowiedź (200 OK):
{ "id": 43, "order_id": 567, "original_invoice_id": null, "source_refund_id": null, "type": "faktura_vat", "type_label": "Faktura VAT", "number": "FV/2026/04/002", "status": "issued", "status_label": "Issued", "nip_seller": "9876543210", "nip_buyer": "1234567890", "buyer_name": "Firma Testowa Sp. z o.o.", "buyer_address": "ul. Testowa 1", "buyer_city": "Warszawa", "buyer_postcode": "00-001", "correction_reason": null, "net_total": 212.20, "vat_total": 48.80, "gross_total": 261.00, "currency": "PLN", "pdf_path": "/wp-content/uploads/polski-pro/invoices/FV-2026-04-002.pdf", "ksef_reference": null, "ksef_status": null, "issued_at": "2026-04-05T14:00:00+02:00", "created_at": "2026-04-05T14:00:00+02:00", "items": [ { "id": 91, "product_id": 120, "name": "Produkt testowy", "quantity": 2, "unit": "szt.", "net_price": 100.00, "vat_rate": 23, "vat_amount": 46.00, "gross_price": 246.00 }, { "id": 92, "product_id": null, "name": "Dostawa - InPost Paczkomat", "quantity": 1, "unit": "szt.", "net_price": 12.20, "vat_rate": 23, "vat_amount": 2.80, "gross_price": 15.00 } ]}Nazwa i adres sprzedawcy nie należą do tego payloadu. Pochodzą z danych sprzedawcy w ustawieniach faktur, a na samej fakturze zapisywany jest tylko nip_seller.
Odpowiedź (404 Not Found):
{ "message": "Invoice not found."}Regenerowanie PDF faktury
Dział zatytułowany „Regenerowanie PDF faktury”POST /wp-json/polski-pro/v1/invoices/{id}/pdfRegeneruje plik PDF faktury. Endpoint nie przyjmuje żadnych parametrów body: szablon i język pochodzą z ustawień faktur.
Odpowiedź (200 OK):
Odświeżony obiekt faktury, z polem pdf_path wskazującym nowy plik. Brak faktury zwraca 404, brak zamówienia 400, a nieudane wygenerowanie pliku 500, każde z polem message.
Wysłanie faktury do KSeF
Dział zatytułowany „Wysłanie faktury do KSeF”POST /wp-json/polski-pro/v1/invoices/{id}/ksefKolejkuje fakturę do wysyłki do Krajowego Systemu e-Faktur (KSeF) przez Action Scheduler. Endpoint nie przyjmuje parametrów body i nic w kokpicie WordPressa go nie wywołuje: jedyną drogą jest klient REST.
Wywołanie kończy się w chwili zakolejkowania zadania. Nigdy nie zwraca w odpowiedzi numeru referencyjnego KSeF, statusu KSeF ani linku do UPO, bo w tym momencie żadna z tych wartości jeszcze nie istnieje. Odczytaj je później z pól ksef_reference i ksef_status faktury.
Zanim się na tym oprzesz, przeczytaj Integracja z KSeF: klient API jest przypięty do środowiska testowego KSeF, a jego uwierzytelnianie nie zostało potwierdzone od początku do końca.
Odpowiedź (202 Accepted):
{ "invoice": { "id": 43, "number": "FV/2026/04/002", "status": "issued", "ksef_reference": null, "ksef_status": null }, "message": "Invoice queued for KSeF submission."}Wartość invoice to pełny obiekt faktury pokazany wyżej, tutaj przycięty do pól istotnych dla tego wywołania.
Pozostałe odpowiedzi:
| Kod | Kiedy |
|---|---|
404 |
Nie ma faktury o tym ID |
422 |
Dokument nie jest dokumentem księgowym. Kwalifikują się tylko faktura_vat i korygujaca, więc paragon, proforma i WZ są tu odrzucane |
409 |
Faktura ma już referencję KSeF, a wysłaną fakturę można wyłącznie skorygować, nigdy wysłać ponownie |
503 |
Action Scheduler jest niedostępny, więc nie da się nic zakolejkować |
{ "message": "Paragon documents are not eligible for KSeF submission."}Utworzenie faktury korygującej
Dział zatytułowany „Utworzenie faktury korygującej”POST /wp-json/polski-pro/v1/invoices/{id}/correctionTworzy fakturę korygującą powiązaną z fakturą źródłową. Skorygowane kwoty wyliczane są z zamówienia oraz, jeśli został podany, ze zwrotu WooCommerce. Tym endpointem nie da się wpisać skorygowanych pozycji ręcznie.
Parametry body (JSON):
| Parametr | Typ | Wymagany | Opis |
|---|---|---|---|
refund_id |
int |
Nie | Zwrot WooCommerce, na którym opiera się korekta |
Żądanie:
{ "refund_id": 981}Odpowiedź (201 Created):
Faktura korygująca, w tym samym kształcie co każdy inny obiekt faktury. type to korygujaca, original_invoice_id wskazuje fakturę źródłową, a sumy są ujemne.
{ "id": 44, "order_id": 567, "original_invoice_id": 43, "source_refund_id": 981, "type": "korygujaca", "type_label": "Faktura korygujaca", "number": "FK/2026/04/001", "status": "issued", "status_label": "Issued", "correction_reason": "Zwrot 1 sztuki produktu", "net_total": -100.00, "vat_total": -23.00, "gross_total": -123.00, "currency": "PLN", "pdf_path": null, "ksef_reference": null, "ksef_status": null, "issued_at": "2026-04-05T15:00:00+02:00", "created_at": "2026-04-05T15:00:00+02:00", "items": []}Brak faktury źródłowej zwraca 404, a korekta, której serwis nie potrafi zbudować, 400.
Endpoint statystyk
Dział zatytułowany „Endpoint statystyk”Pobranie statystyk faktur
Dział zatytułowany „Pobranie statystyk faktur”GET /wp-json/polski-pro/v1/invoices/statsParametry zapytania:
| Parametr | Typ | Domyślna | Opis |
|---|---|---|---|
days |
int |
30 |
Liczba dni wstecz, przycinana do zakresu 1-365 |
To jedyny parametr tego endpointu. Nie ma grupowania po dniach, tygodniach ani miesiącach.
Odpowiedź (200 OK):
Liczniki obejmują faktury utworzone w oknie days. total_revenue sumuje gross_total z pominięciem faktur anulowanych, natomiast kwoty w by_type sumują wszystko, więc gdy w oknie są faktury anulowane, suma przychodów z by_type jest wyższa niż total_revenue. ksef_sent liczy faktury, które mają zapisaną referencję KSeF.
{ "period_days": 30, "total": 156, "total_revenue": 150588.9, "ksef_sent": 12, "by_type": [ { "type": "faktura_vat", "count": 148, "revenue": 152430.4 }, { "type": "korygujaca", "count": 3, "revenue": -1230.0 }, { "type": "proforma", "count": 5, "revenue": 3078.5 } ], "by_status": [ { "status": "issued", "count": 120 }, { "status": "sent", "count": 25 }, { "status": "paid", "count": 8 }, { "status": "cancelled", "count": 3 } ]}Odpowiedź zawiera wyłącznie pola wymienione wyżej, bez dodatkowych podsumowań, rozbić po stawkach VAT czy osi czasu. Rozbicia by_type i by_status są listami, nie obiektami z kluczami. W tym przykładzie trzy anulowane faktury o łącznej wartości brutto 3690,00 nie wchodzą do total_revenue, ale wchodzą do przychodu w by_type.
Endpoint ustawień
Dział zatytułowany „Endpoint ustawień”Odczyt i aktualizacja ustawień PRO
Dział zatytułowany „Odczyt i aktualizacja ustawień PRO”GET /wp-json/polski-pro/v1/settingsPUT /wp-json/polski-pro/v1/settingsTrasa rejestruje metody odczytu i edycji, więc zapis przyjmuje PUT, PATCH albo POST. Obie metody wymagają uprawnienia manage_woocommerce.
Parametry body (JSON):
Nie ma parametrów section ani settings. Body to same grupy ustawień na najwyższym poziomie. Grupy, które rozpoznaje handler:
| Grupa | Zapisywana opcja |
|---|---|
invoices |
polski_pro_invoices |
ksef |
polski_pro_ksef |
nip |
polski_pro_nip |
shipping |
polski_pro_shipping |
delivery_date |
polski_delivery_date |
checkout |
polski_pro_checkout |
abandoned_carts |
polski_abandoned_carts |
conditional_payments |
polski_pro_conditional_payments |
product_feed |
polski_pro_product_feed |
loyalty |
polski_pro_loyalty |
sms |
polski_pro_sms |
accounting |
polski_pro_accounting |
Każda podana grupa nadpisuje zapisaną opcję w całości, więc wysyłaj pełną zawartość grupy, a nie pojedyncze pola. Klucze spoza listy dozwolonych pól danej grupy są odrzucane. Grupy pominięte w body zostają bez zmian, a wszystko wysłane pod nazwą spoza powyższej tabeli jest ignorowane.
Żądanie:
{ "invoices": { "auto_generate": true, "numbering_format": "FV/{YYYY}/{MM}/{NR}", "seller_nip": "9876543210", "payment_deadline_days": 14 }, "ksef": { "enabled": false, "environment": "test", "auto_send": false }}Odpowiedź (200 OK):
Zapis zwraca kompletny zestaw ustawień PRO, dokładnie taki sam jak GET, a nie tylko zmienioną grupę. W odpowiedzi nie ma pól section ani updated_at.
{ "invoices": { "auto_generate": true, "numbering_format": "FV/{YYYY}/{MM}/{NR}", "seller_nip": "9876543210", "payment_deadline_days": 14 }, "ksef": { "enabled": false, "environment": "test", "auto_send": false }, "nip": { "checkout_field": true, "required": false, "validate_gus": true }}Endpoint generowania dokumentów prawnych
Dział zatytułowany „Endpoint generowania dokumentów prawnych”Pobranie listy zmiennych
Dział zatytułowany „Pobranie listy zmiennych”GET /wp-json/polski-pro/v1/legal/variablesZwraca nazwy zmiennych obsługiwanych przez szablony, wartości domyślne wzięte z ustawień WooCommerce oraz etykiety trzech dostępnych typów dokumentów.
Odpowiedź (200 OK):
{ "required": { "company_name": "Full company name", "company_address": "Company address", "company_nip": "NIP (tax ID)", "company_regon": "REGON number", "company_email": "Contact email", "company_phone": "Contact phone", "shop_url": "Shop URL", "shop_name": "Shop name", "bank_name": "Bank name", "bank_account": "Bank account number" }, "defaults": { "company_name": "Mój Sklep", "company_address": "ul. Sklepowa 5, 02-222 Warszawa", "company_nip": "9876543210", "company_regon": "", "company_phone": "", "shop_url": "https://mojsklep.pl", "shop_name": "Mój Sklep", "bank_name": "", "bank_account": "" }, "types": { "regulamin": "Regulamin sklepu", "polityka-prywatnosci": "Polityka prywatnosci", "polityka-zwrotow": "Prawo odstapienia / Polityka zwrotow" }}Generowanie dokumentu prawnego
Dział zatytułowany „Generowanie dokumentu prawnego”POST /wp-json/polski-pro/v1/legal/generateRenderuje szablon dokumentu i zwraca go do podglądu. Nic nie zapisuje.
Parametry body (JSON):
| Parametr | Typ | Wymagany | Opis |
|---|---|---|---|
type |
string |
Tak | Typ dokumentu: regulamin, polityka-prywatnosci, polityka-zwrotow |
variables |
object |
Nie | Nadpisania zmiennych szablonu, domyślnie pusty obiekt. Wartości niepodane biorą się z ustawień sklepu |
Endpoint nie zna parametrów company_data, format ani language. Dane firmy przekazuje się jako zmienne, a wynik zawsze wraca jako treść szablonu, bez wariantu Markdown czy PDF.
Żądanie:
{ "type": "regulamin", "variables": { "company_name": "Mój Sklep Sp. z o.o.", "company_nip": "9876543210", "company_address": "ul. Sklepowa 5, 02-222 Warszawa", "company_phone": "+48 123 456 789" }}Odpowiedź (200 OK):
{ "type": "regulamin", "content": "<h1>Regulamin sklepu internetowego...</h1>...", "variables_used": { "company_name": "Mój Sklep Sp. z o.o.", "company_nip": "9876543210", "company_address": "ul. Sklepowa 5, 02-222 Warszawa", "company_phone": "+48 123 456 789" }}Nieznany type zwraca 400, a brakujący lub pusty szablon 500, oba z polem message.
Publikacja dokumentu jako strony
Dział zatytułowany „Publikacja dokumentu jako strony”POST /wp-json/polski-pro/v1/legal/publishRenderuje ten sam dokument i zapisuje go jako stronę WordPressa o statusie draft, a następnie zapamiętuje jej ID w ustawieniach Polski. Publikację strony zostawia człowiekowi.
Parametry body (JSON):
| Parametr | Typ | Wymagany | Opis |
|---|---|---|---|
type |
string |
Tak | Typ dokumentu: regulamin, polityka-prywatnosci, polityka-zwrotow |
variables |
object |
Nie | Nadpisania zmiennych szablonu, domyślnie pusty obiekt |
page_id |
int |
Nie | Istniejąca strona do nadpisania, domyślnie 0, czyli utwórz nową |
Odpowiedź (201 Created):
{ "page_id": 412, "edit_url": "https://mojsklep.pl/wp-admin/post.php?post=412&action=edit", "view_url": "https://mojsklep.pl/?page_id=412", "status": "draft", "message": "Page created as draft. Review and publish when ready."}Kody błędów
Dział zatytułowany „Kody błędów”Endpointy faktur nie mają własnego słownika kodów błędów. Zwracają status HTTP i gołe ciało z jednym polem:
{ "message": "Invoice not found."}Jedyny nazwany kod błędu w kontrolerze faktur to polski_pro_forbidden, zwracany przez sprawdzenie uprawnień.
| Kod HTTP | Kod błędu | Kiedy |
|---|---|---|
| 400 | brak | Nieznany type, brak zamówienia, nieudane utworzenie faktury albo korekty |
| 403 | polski_pro_forbidden |
Użytkownik nie ma uprawnienia manage_woocommerce |
| 404 | brak | Nie ma faktury o tym ID |
| 409 | brak | Faktura ma już referencję KSeF |
| 422 | brak | Dokument nie kwalifikuje się do KSeF |
| 500 | brak | Nie udało się wygenerować PDF |
| 503 | brak | Action Scheduler jest niedostępny |
Poza polski_pro_forbidden wtyczka nie definiuje tu żadnych nazwanych kodów błędów, więc nie ma sensu testować na inne identyfikatory: pozostałe błędy rozpoznaje się po statusie HTTP i polu message.
Endpointy dokumentów prawnych zachowują się tak samo: 400 przy nieznanym typie i 500 przy braku szablonu, oba z polem message.
Wyszukiwarka GUS to jedyne miejsce z własnymi kodami: polski_pro_invalid_nip (400), polski_pro_rate_limited (429) i polski_pro_gus_unavailable (502).
Limity i throttling
Dział zatytułowany „Limity i throttling”Nie ma globalnego limitu żądań. Cała warstwa REST w PRO ma dokładnie jeden licznik i dotyczy on wyłącznie wyszukiwania danych firmy w GUS:
POST /wp-json/polski-pro/v1/gus/lookupLimit liczony jest per adres IP i domyślnie wynosi 10 zapytań na godzinę. Zalogowani użytkownicy z uprawnieniem manage_woocommerce są z niego wyłączeni, bo checkout ma z tego korzystać także dla niezalogowanych klientów. Po przekroczeniu endpoint zwraca 429 z kodem polski_pro_rate_limited.
Okno i próg da się przestawić filtrami:
| Filtr | Domyślnie | Opis |
|---|---|---|
polski-pro/gus/rate_limit_window_seconds |
HOUR_IN_SECONDS |
Długość okna w sekundach. Wartość 0 lub mniejsza wyłącza limit |
polski-pro/gus/rate_limit_max_attempts |
10 |
Liczba zapytań w oknie. Wartość 0 lub mniejsza wyłącza limit |
Dalsze kroki
Dział zatytułowany „Dalsze kroki”- Zgłaszaj problemy: GitHub Issues
- Powiązane: Integracje księgowe