GitHub

Status i UPO

Zrozum powierzchnie statusu, polling, dokumenty UPO i lokalne timeouty w przepływach ksef2.

Na tej stronie

Przepływy KSeF są asynchroniczne. Wiele wywołań SDK rozpoczyna pracę i zwraca numer referencyjny; inne wywołanie mówi, co stało się później.

Nie sprowadzaj tego do jednej flagi done. Każda powierzchnia statusu odpowiada na inne pytanie i ma inny numer referencyjny.

Którego statusu potrzebujesz?

PytaniePowierzchnia SDKTypowy uchwyt
Czy uwierzytelnianie się zakończyło?client.authenticationreferencja operacji uwierzytelniania
Czy sesja online albo batch nadal się przetwarza?klient sesji albo auth.batchnumer referencyjny sesji
Czy jedna wysłana faktura się udała albo nie?status faktury w sesji online/batchnumer referencyjny faktury
Czy przetworzone faktury są widoczne w wyszukiwaniu?zapytania metadanych auth.invoicesfiltry, paginacja, numer KSeF
Czy paczka eksportu jest gotowa?status eksportu auth.invoicesnumer referencyjny eksportu
Czy token jest aktywny albo cofnięty?auth.tokensnumer operacji/referencji tokenu
Czy operacja uprawnień się zakończyła?auth.permissionsreferencja operacji uprawnień

Używaj powierzchni, która pasuje do pytania. Sesja może być zakończona, a jedna faktura w środku może być błędna. Eksport może nadal się przygotowywać, mimo że metadane faktur są już widoczne. Operacja tokenu kończy się niezależnie od sesji wysyłki faktur.

Status sesji

Status sesji jest podsumowaniem zdalnego przepływu online albo batch po stronie KSeF. Po przetworzeniu może zawierać liczniki i referencje stron UPO.

status = session.get_status()
print(
    status.status.code,
    status.invoice_count,
    status.successful_invoice_count,
    status.failed_invoice_count,
)
python

Kod statusu dotyczy przepływu sesji, a niekoniecznie każdej faktury w środku. Podsumowanie sesji może mówić, że przetwarzanie się zakończyło, i jednocześnie raportować błędne faktury w failed_invoice_count. Gdy potrzebujesz szczegółów per faktura, sprawdzaj faktury sesji.

failed = session.list_failed_invoices()
for invoice in failed.invoices:
    print(invoice.reference_number, invoice.status.code, invoice.status.details)
python

Status faktury

Status faktury jest przypisany do jednej faktury w jednej sesji. Przy wysyłce online numer referencyjny faktury zwykle dostajesz od razu z send_invoice(). Przy wysyłce batch statusy poszczególnych faktur stają się widoczne po przetworzeniu wgranej paczki przez KSeF.

Zaakceptowany status faktury ma ksef_number. Błędny status faktury niesie kod statusu KSeF, opis i opcjonalne szczegóły.

invoice_status = session.get_invoice_status(
    invoice_reference_number=sent.reference_number,
)
print(invoice_status.ksef_number, invoice_status.status.description)
python

Dokumenty UPO

UPO jest urzędowym poświadczeniem. To XML podpisany przez Ministerstwo Finansów. Traktuj zwrócone bajty jak artefakt audytowy i zapisuj je trwale.

UPO nie jest dostępne w momencie wysyłki:

  1. Wyślij albo wgraj dane faktury.

  2. Poczekaj, aż KSeF przetworzy fakturę albo sesję.

  3. Odczytaj referencję UPO albo użyj referencji faktury/numeru KSeF.

  4. Pobierz i zapisz bajty XML UPO.

SDK udostępnia typowe ścieżki UPO przez klientów sesji:

invoice_upo = submission.download_upo()

session_upo_pages = session.download_upo()  # wszystkie strony, referencje rozwiązuje SDK
python

download_upo() nigdy nie czeka. Najpierw wywołaj submission.wait() dla UPO faktury albo session.wait() (po zamknięciu sesji) dla stron UPO sesji. Wywołane za wcześnie, submission.download_upo() rzuca KSeFNotReadyError, a warianty sesji rzucają go, dopóki KSeF przetwarza zamkniętą sesję. Sesja, która jest nadal otwarta, rzuca KSeFSessionError. Oba niosą hint wskazujący wait(). submission.download_upo() wykonuje dokładnie jedno zapytanie; warianty sesji raz odczytują status sesji, a potem pobierają kolejne strony UPO.

Odpowiedzi statusowe mogą też wystawiać dane stron UPO, takie jak download_url_expiration_date. Do wywołań SDK używaj referencji i zapisuj pobrany XML, gdy już go masz.

Polling i timeouty

Helpery oczekujące pollują KSeF do momentu, gdy stanie się jedna z trzech rzeczy:

  • pojawi się oczekiwany stan;
  • KSeF zgłosi terminalny błąd klasyfikowany przez SDK;
  • minie lokalny timeout.

Lokalny timeout nie dowodzi, że zdalna operacja nie powiodła się. Oznacza tylko, że stan docelowy nie został zaobserwowany przed twoim deadline.

Dostosuj ustawienia pollingu do przepływu:

PrzepływTypowy helper oczekujący
Akceptacja faktury onlinesubmission.wait()
Przetwarzanie batchsession.wait()
Gotowość paczki eksportuauth.invoices.export(...).wait()
Aktywacja albo sprawdzanie tokenuauth.tokens.generate(...).wait() albo auth.tokens.get_status()
Nadanie albo cofnięcie uprawnieniaoperation.wait() albo auth.permissions.get_operation_status()
Wydanie certyfikatuenrollment.wait() albo auth.certificates.get_enrollment_status()

Co zapisywać

Zapisz informacje wystarczające do późniejszej inspekcji statusu bez pierwotnego obiektu Pythona:

  • numer referencyjny sesji;
  • numer referencyjny faktury;
  • numer KSeF po akceptacji;
  • referencję UPO albo bajty XML UPO;
  • numer referencyjny eksportu albo operacji dla przepływów poza sesją;
  • ostatni zaobserwowany payload statusu do audytu.

Powiązane strony

  • Sprawdź status i UPO: Polluj sesje online i batch, a potem pobierz XML UPO.
  • Sesje: Zrozum zdalne konteksty przepływów, które wystawiają status.
  • Cykl życia faktury: Prześledź fakturę od wysyłki po numer KSeF, metadane, pobranie i UPO.
  • Obsługa błędów: Obsłuż operacje odrzucone, nieudane, wygasłe i możliwe do ponowienia.