Szablon danych do obsługi faktur w cyklu od zakupu do płatności
Szablon danych do obsługi faktur w cyklu od zakupu do płatności
- Zalecane atrybuty do zebrania
- Najważniejsze działania do śledzenia
- Wskazówki dotyczące ekstrakcji danych z SAP S/4HANA
Atrybuty obsługi faktur w cyklu od zakupu do płatności
| Nazwa | Opis | ||
|---|---|---|---|
| Numer faktury InvoiceNumber | Unikalny identyfikator dokumentu faktury od dostawcy, który służy jako główny identyfikator sprawy w procesie. | ||
| Opis Numer faktury to unikalny identyfikator przypisany do każdej faktury od dostawcy w SAP S/4HANA. Łączy powiązane czynności, takie jak utworzenie, zaparkowanie, zatwierdzenie i płatność, w jeden spójny przebieg procesu. W process mining ten atrybut jest podstawą śledzenia całego przebiegu każdej faktury. Umożliwia odtworzenie procesu od otrzymania faktury po płatność końcową oraz analizę czasu realizacji, wąskich gardeł i różnic w przebiegu poszczególnych faktur. Dlaczego to ważne To podstawowy identyfikator łączący wszystkie powiązane zdarzenia i umożliwiający prześledzenie całego cyklu życia faktury w systemie. Skąd pobrać Jest to numer dokumentu księgowego, zapisany w tabeli BKPF w polu BELNR. Przykłady 190000000119000000451900000132 | |||
| Czas zdarzenia EventTime | Dokładna data i godzina wystąpienia czynności. | ||
| Opis Czas zdarzenia to znacznik czasu wskazujący dokładny moment wykonania danej czynności. Dane te są niezbędne do obliczania czasu trwania, czasu realizacji procesu i czasu oczekiwania między jego etapami. W analizie process mining dokładne znaczniki czasu służą do pomiaru KPI, takich jak „Średni czas realizacji faktury” i „Czas zatwierdzania faktury”. Analiza czasu między czynnościami pozwala wskazać miejsca, w których faktury się opóźniają, i znaleźć możliwości przyspieszenia procesu. Dlaczego to ważne Ten znacznik czasu stanowi podstawę analiz opartych na czasie, w tym monitorowania wyników, wykrywania wąskich gardeł i śledzenia SLA. Skąd pobrać Zazwyczaj dane pochodzą z tabel dokumentów zmian CDHDR (nagłówek) i CDPOS (pozycja), z pól UDATE i UTIME. W przypadku niektórych zdarzeń mogą pochodzić z dat utworzenia lub wprowadzenia w tabelach takich jak BKPF (CPUDT, CPUTM). Przykłady 2023-04-15T10:30:00Z2023-04-18T14:05:21Z2023-05-02T09:00:00Z | |||
| Nazwa czynności ActivityName | Nazwa czynności biznesowej lub zdarzenia, które miało miejsce w określonym czasie w odniesieniu do faktury. | ||
| Opis Nazwa czynności opisuje konkretny etap lub zmianę statusu w cyklu obsługi faktury. Przykłady: „Utworzenie dokumentu faktury”, „Przekazanie faktury do zatwierdzenia”, „Ustawienie blokady płatności” i „Realizacja płatności”. Ten atrybut służy do tworzenia mapy procesu, która przedstawia przebieg czynności. Analiza ich kolejności, częstotliwości i czasu między nimi pomaga wykrywać wąskie gardła, pętle poprawek i odstępstwa od zgodnego przebiegu procesu. To podstawa analizy process mining. Dlaczego to ważne Określa etapy procesu, umożliwiając wizualizację map procesów oraz analizę ich przebiegu i odchyleń. Skąd pobrać Ustalana na podstawie kodów transakcji SAP (SY-TCODE), statusów obiektów dokumentów zmian (CDHDR/CDPOS) oraz konkretnych wartości pól wskazujących zmianę statusu. Przykłady Wstępne wprowadzenie fakturyAkceptacja fakturyRealizacja płatności | |||
| Kod spółki CompanyCode | Jednostka organizacyjna reprezentująca prawnie niezależną spółkę, dla której sporządza się sprawozdania finansowe. | ||
| Opis Kod spółki to podstawowa jednostka organizacyjna w module SAP Finance. Każda faktura jest przypisana do konkretnego kodu spółki, który wskazuje podmiot prawny odpowiedzialny za transakcję. W process mining filtrowanie lub porównywanie danych według kodu spółki jest niezbędne do analizy wyników procesu w różnych jednostkach biznesowych, podmiotach prawnych i krajach. Pomaga wykrywać regionalne różnice w sprawności, zgodności i poziomie automatyzacji, co ułatwia planowanie ukierunkowanych usprawnień. Dlaczego to ważne Umożliwia podział i porównanie wyników obsługi faktur w różnych podmiotach prawnych i lokalizacjach geograficznych firmy. Skąd pobrać To standardowe pole w tabeli nagłówka dokumentu BKPF: BUKRS. Przykłady 1000US01DE01 | |||
| Kwota faktury AmountInCompanyCodeCurrency | Łączna kwota brutto faktury w walucie lokalnej kodu spółki. | ||
| Opis Ten atrybut określa łączną wartość faktury. Pozwala ocenić wpływ finansowy i skalę operacji związanych z obsługą faktur. Analiza kwot faktur pomaga ustalać priorytety i szybciej obsługiwać faktury o wysokiej wartości, wykrywać trendy w wydatkach oraz sprawdzać, czy problemy w procesie wiążą się z określoną wartością finansową. Można na przykład ustalić, czy faktury o wysokiej wartości częściej są blokowane lub dłużej czekają na zatwierdzenie. Dlaczego to ważne Dostarcza kontekstu finansowego do analizy procesu według wartości pieniężnej, na przykład pozwala sprawdzić, czy faktury o wysokiej wartości są obsługiwane inaczej. Skąd pobrać Wartość jest zwykle obliczana jako suma odpowiednich pozycji w tabeli BSEG, w polu WRBTR (kwota w walucie lokalnej). Przykłady 1500.75125000.00850.20 | |||
| Nazwa użytkownika UserName | Identyfikator użytkownika SAP, który wykonał daną czynność. Może to być osoba lub system. | ||
| Opis Ten atrybut wskazuje użytkownika, który wykonał konkretną transakcję lub utworzył dokument. Może to być identyfikator osoby albo systemu obsługującego zautomatyzowane zadania wsadowe. Analiza według użytkownika pomaga ocenić rozkład obciążenia, określić potrzeby szkoleniowe i wykryć nietypowe zachowania. Można na przykład sprawdzić, kto często obsługuje wyjątki i które faktury są przetwarzane automatycznie, na przykład przez użytkownika „BATCHUSER”. To ważne przy obliczaniu KPI „Poziom automatyzacji faktur”. Dlaczego to ważne Przypisuje czynności w procesie do konkretnych użytkowników lub kont systemowych, umożliwiając analizę obciążenia, porównanie wyników i wykrywanie automatyzacji. Skąd pobrać Dane pochodzą z pól takich jak BKPF-USNAM (wprowadził) lub CDHDR-USERNAME (zmienił). Przykłady SMITHJMUELLERTWF-BATCH | |||
| Numer dostawcy VendorNumber | Unikalny identyfikator dostawcy, który wystawił fakturę. | ||
| Opis Numer dostawcy identyfikuje dostawcę lub wierzyciela powiązanego z fakturą. Łączy transakcję faktury z danymi podstawowymi dostawcy. Ten atrybut umożliwia analizę według dostawców, na przykład ocenę „Terminowości płatności dla dostawców” lub wskazanie dostawców, którzy często przesyłają problematyczne faktury powodujące wyjątki lub blokady płatności. Pomaga zarządzać relacjami z dostawcami i oceniać ich rzetelność. Dlaczego to ważne Umożliwia analizę wyników procesu według dostawcy, co pomaga wykrywać powtarzające się problemy, zarządzać relacjami i oceniać kwestie związane z dostawcami. Skąd pobrać Zazwyczaj znajduje się w tabeli pozycji dokumentu księgowego BSEG, w polu LIFNR. Przykłady 100345700012V9832 | |||
| Przyczyna blokady płatności PaymentBlockReason | Kod wskazujący przyczynę blokady płatności za fakturę. | ||
| Opis Gdy płatność za fakturę jest zablokowana, ten atrybut podaje konkretną przyczynę, na przykład „Niezgodność ilości” lub „Niezgodność ceny”. Przyczyny te konfiguruje się w SAP, aby ujednolicić obsługę wyjątków. Ten atrybut jest niezbędny do tworzenia dashboardu „Występowanie i czas trwania blokad płatności”. Analiza częstotliwości poszczególnych przyczyn pomaga wykrywać źródła opóźnień, takie jak problemy z konkretnymi dostawcami, materiałami lub procesami wewnętrznymi, i podejmować odpowiednie działania naprawcze. Dlaczego to ważne Wskazuje konkretną przyczynę blokady płatności, umożliwiając ukierunkowaną analizę, która pomaga ograniczyć opóźnienia i zwiększyć odsetek spraw załatwianych poprawnie za pierwszym razem. Skąd pobrać Znajduje się w pozycji dostawcy w tabeli BSEG, w polu ZLSPR (klucz blokady płatności). Przykłady RIA | |||
| Rodzaj dokumentu DocumentType | Kod określający rodzaj dokumentu księgowego, na przykład fakturę od dostawcy lub notę uznaniową. | ||
| Opis Rodzaj dokumentu służy w SAP do rozróżniania transakcji biznesowych. Na przykład „KR” zwykle oznacza standardową fakturę od dostawcy, a „KG” może oznaczać notę uznaniową od dostawcy. Analiza według rodzaju dokumentu pozwala podzielić proces i sprawdzić, jak obsługiwane są różne typy transakcji. Proces obsługi noty uznaniowej może się znacznie różnić od procesu obsługi standardowej faktury. Taki podział pozwala uzyskać dokładniejsze i bardziej przydatne informacje o procesie. Dlaczego to ważne Pomaga rozróżniać rodzaje transakcji finansowych, takie jak standardowe faktury i noty uznaniowe, które często przebiegają różnymi ścieżkami. Skąd pobrać Znajduje się w tabeli nagłówka dokumentu BKPF, w polu BLART. Przykłady KRREKG | |||
| Termin płatności PaymentDueDate | Data, do której należy opłacić fakturę, aby uniknąć opóźnienia. | ||
| Opis Termin płatności to obliczona data, do której należy zapłacić dostawcy, ustalana na podstawie daty faktury i uzgodnionych warunków płatności. Jest to ważny termin w procesie. Ten atrybut jest niezbędny do obliczania KPI „Odsetek płatności terminowych” i tworzenia dashboardu „Terminowość płatności dla dostawców”. Porównanie faktycznej daty płatności z terminem pozwala ocenić, czy firma wywiązuje się ze zobowiązań, co wpływa na relacje z dostawcami i jej wiarygodność finansową. Dlaczego to ważne To podstawowy punkt odniesienia przy ocenie terminowości płatności. Ma to znaczenie dla utrzymania dobrych relacji z dostawcami i uniknięcia opłat za opóźnienia. Skąd pobrać Data ta jest często dostępna bezpośrednio w pozycji dostawcy w tabeli BSEG, w polu ZFBDT (data bazowa do obliczenia terminu płatności). Termin płatności netto oblicza się na podstawie tej daty i warunków płatności. Przykłady 2023-05-302023-06-152023-07-01 | |||
| Zamówienie zakupu PurchasingDocument | Numer zamówienia zakupu powiązanego z fakturą. | ||
| Opis Numer dokumentu zakupu łączy fakturę od dostawcy z pierwotnym zamówieniem zakupu (PO). To powiązanie jest podstawą procesu trójstronnego uzgadniania, w którym fakturę porównuje się z zamówieniem i potwierdzeniem odbioru towaru. Analiza tego atrybutu pomaga zrozumieć różnice między fakturami powiązanymi z zamówieniem a fakturami bez zamówienia. Ułatwia badanie rozbieżności w uzgadnianiu i ocenę sprawności procesu zakupowego. Dlaczego to ważne Łączy fakturę z procesem zakupowym, co ma znaczenie przy analizie rozbieżności w uzgadnianiu i zgodności z zamówieniami zakupu. Skąd pobrać Informacja ta znajduje się zwykle w tabeli pozycji dokumentu BSEG, w polu EBELN (numer dokumentu zakupu). Przykłady 450000123445000056784500009012 | |||
| Czy czynność jest zautomatyzowana IsAutomated | Flaga wskazująca, czy czynność wykonało konto użytkownika systemowego. | ||
| Opis Ten atrybut logiczny ma wartość prawda, jeśli użytkownik przypisany do czynności jest znanym kontem systemowym lub wsadowym, takim jak „WF-BATCH” lub „SAP_SYSTEM”. Pomaga odróżnić etapy wykonywane ręcznie od zautomatyzowanych. Atrybut ten jest niezbędny do obliczania KPI „Poziom automatyzacji faktur”. Analiza zautomatyzowanych etapów procesu pozwala ocenić wyniki inicjatyw automatyzacyjnych i wskazać kolejne możliwości ograniczenia pracy ręcznej oraz poprawy sprawności. Dlaczego to ważne Pozwala odróżnić czynności wykonywane ręcznie od tych realizowanych przez system. Ma to podstawowe znaczenie przy pomiarze poziomu automatyzacji i wskazywaniu kolejnych możliwości automatyzacji. Skąd pobrać Ustalany na podstawie atrybutu UserName. Określone identyfikatory użytkowników są oznaczane jako „zautomatyzowane” za pomocą mapowania lub reguły. Przykłady truefalse | |||
| Czy płatność została zrealizowana terminowo IsPaidOnTime | Flaga ma wartość prawda, jeśli fakturę opłacono najpóźniej w terminie płatności. | ||
| Opis Ten atrybut logiczny powstaje przez porównanie faktycznej daty płatności, czyli znacznika czasu czynności „Realizacja płatności”, z „Terminem płatności”. Jednoznacznie określa status płatności każdej faktury. To podstawowe obliczenie dla KPI „Odsetek płatności terminowych”. Ułatwia filtrowanie i analizę opóźnionych płatności, na przykład według dostawców, kodów spółek lub kwot faktur powiązanych z opóźnieniami. Dlaczego to ważne Bezpośrednio mierzy przestrzeganie warunków płatności. To ważny KPI w zarządzaniu relacjami z dostawcami i operacjami finansowymi. Skąd pobrać Obliczany przez porównanie EventTime czynności „Realizacja płatności” z atrybutem PaymentDueDate. (Data płatności <= PaymentDueDate). Przykłady truefalse | |||
| Czy wystąpiły poprawki IsRework | Flaga wskazująca, czy przy obsłudze faktury wystąpiły poprawki, na przykład po odrzuceniu zatwierdzenia lub usunięciu blokady płatności. | ||
| Opis Ten atrybut oznacza faktury, przy których wystąpiła co najmniej jedna pętla poprawek. Można je rozpoznać po określonych sekwencjach czynności, na przykład po czynności „Zatwierdzenie faktury” następującej po „Odrzuceniu faktury” albo po „Usunięciu blokady płatności” następującym po „Ustawieniu blokady płatności”. Atrybut ten ułatwia obliczanie KPI „Odsetek faktur wymagających poprawek”. Analitycy mogą szybko wyodrębnić i zbadać sprawy wymagające poprawek, aby ustalić źródła nieefektywności i powtarzanej pracy ręcznej. Dlaczego to ważne Wskazuje nieefektywne przebiegi procesu, w których trzeba ponownie wykonać pracę. Pomaga oszacować straty i ustalić źródła wyjątków w procesie. Skąd pobrać Obliczany na podstawie kolejności czynności w dzienniku zdarzeń. Na przykład jeśli w przebiegu faktury występuje „Odrzucenie faktury”, flaga przyjmuje wartość prawda. Przykłady truefalse | |||
| Data faktury InvoiceDate | Data wystawienia dokumentu faktury przez dostawcę. | ||
| Opis Data faktury, nazywana również datą dokumentu, to data podana przez dostawcę na fakturze. Służy jako punkt wyjścia do obliczenia terminu płatności na podstawie uzgodnionych warunków. W analizie jest podstawą obliczeń finansowych, takich jak ustalanie wieku faktury i prawa do rabatu za wcześniejszą płatność. To ważna dana wejściowa przy obliczaniu KPI „Wykorzystanie rabatów za wcześniejszą płatność”. Dlaczego to ważne Stanowi podstawę obliczania warunków i terminów płatności, co ma znaczenie dla zarządzania kapitałem obrotowym i korzystania z rabatów. Skąd pobrać Znajduje się w tabeli nagłówka dokumentu BKPF, w polu BLDAT (data dokumentu). Przykłady 2023-04-122023-05-152023-06-20 | |||
| Identyfikator systemu źródłowego SourceSystemId | Identyfikator źródłowego systemu SAP S/4HANA, z którego wyodrębniono dane. | ||
| Opis Ten atrybut wskazuje system źródłowy, na przykład „S4H_PROD” lub „ERP_EU”. Jest szczególnie ważny w środowiskach korzystających z wielu instancji ERP albo łączących starsze i nowoczesne systemy. Umożliwia porównywanie wyników procesu między systemami i regionami. Pozwala ustalić pochodzenie danych, co ma znaczenie dla zarządzania danymi i rozwiązywania problemów, gdy dane z wielu źródeł są łączone na jednej platformie process mining. Dlaczego to ważne Informuje o pochodzeniu danych, co ma znaczenie dla zarządzania danymi i porównywania procesów w różnych systemach oraz lokalizacjach firmy. Skąd pobrać Wartość jest zwykle pobierana z identyfikatora systemu SAP (sy-sysid) podczas ekstrakcji danych lub ustawiana na stałe w potoku ETL. Przykłady S4PS4H_PROD_100ECC_EU | |||
| Liczba cykli zatwierdzania ApprovalCycleCount | Liczba przypadków przekazania faktury do zatwierdzenia. | ||
| Opis Ta miara zlicza wystąpienia czynności „Przekazanie faktury do zatwierdzenia” dla jednej faktury. Wynik większy niż jeden oznacza, że fakturę co najmniej raz odrzucono lub odesłano, co wymagało ponownego rozpoczęcia cyklu zatwierdzania. Atrybut ten bezpośrednio wspiera KPI „Odsetek zatwierdzeń za pierwszym razem”. Analiza faktur z dużą liczbą cykli zatwierdzania pomaga ustalić przyczyny odrzuceń, takie jak brakujące informacje lub nieprawidłowe kodowanie, i usprawnić proces. Dlaczego to ważne Pozwala określić skalę poprawek w podprocesie zatwierdzania, ocenić odsetek spraw załatwianych poprawnie za pierwszym razem i ustalić przyczyny odrzuceń. Skąd pobrać Obliczany przez zliczenie wystąpień czynności „Przekazanie faktury do zatwierdzenia” dla każdego unikalnego InvoiceNumber. Przykłady 123 | |||
| Numer dokumentu rozliczającego. ClearingDocumentNumber | Numer dokumentu rozliczającego fakturę, zazwyczaj dokumentu płatności. | ||
| Opis Numer dokumentu rozliczającego łączy otwartą pozycję faktury z transakcją, która ją rozlicza, najczęściej dokumentem płatności. Potwierdza to, że faktura została opłacona. Ten atrybut stanowi bezpośrednie powiązanie między fakturą a jej płatnością. Służy do identyfikacji czynności „Realizacja płatności” i przypisanego do niej znacznika czasu. Jest to niezbędne do obliczenia całkowitego czasu realizacji procesu i odsetka płatności terminowych. Dlaczego to ważne Potwierdza opłacenie faktury i łączy ją z konkretną transakcją płatniczą, co ma znaczenie przy analizie czasu realizacji procesu i wyników płatności. Skąd pobrać Znajduje się w tabeli pozycji dokumentu BSEG, w polu AUGBL (numer dokumentu rozliczającego). Przykłady 150000000115000000231500000088 | |||
| Przyczyna odwrócenia ReversalReason | Kod wskazujący przyczynę odwrócenia dokumentu faktury. | ||
| Opis Jeśli faktura została zaksięgowana nieprawidłowo, często się ją odwraca. Kod przyczyny odwrócenia wyjaśnia powód, na przykład „Nieprawidłowa data księgowania” lub „Błąd przy wprowadzaniu danych”. Analiza przyczyn odwróceń pomaga wykrywać powtarzające się błędy w procesie księgowania faktur. Uzyskane informacje można wykorzystać do poprawy szkoleń, wzmocnienia kontroli systemowych lub rozwiązania problemów, które powodują ponowne wykonywanie pracy i zwiększają obciążenie administracyjne. Dlaczego to ważne Wyjaśnia, dlaczego faktury zostały anulowane, i bezpośrednio wskazuje źródła błędów oraz poprawek w procesie księgowania. Skąd pobrać Znajduje się w nagłówku pierwotnego dokumentu w tabeli BKPF, w polu STGRD (przyczyna odwrócenia). Przykłady 010205 | |||
| Warunki płatności PaymentTerms | Kod określający uzgodnione z dostawcą warunki płatności, takie jak terminy płatności i okresy obowiązywania rabatu. | ||
| Opis Warunki płatności określają zasady opłacania faktury, w tym dostępne rabaty za wcześniejszą płatność. Na przykład „Z030” może oznaczać „płatność netto w ciągu 30 dni”. Ten atrybut jest niezbędny do planowania finansowego i optymalizacji kapitału obrotowego. W process mining służy do obliczania „Terminu płatności” i ustalania prawa do rabatu za wcześniejszą płatność, wspierając bezpośrednio KPI „Wykorzystanie rabatów za wcześniejszą płatność”. Dlaczego to ważne Określa zasady ustalania terminów płatności i rabatów, bezpośrednio wpływając na KPI dotyczące terminowości płatności i zarządzanie kapitałem obrotowym. Skąd pobrać Znajduje się w pozycji dostawcy w tabeli BSEG, w polu ZTERM (klucz warunków płatności). Przykłady 0001Z030NT60 | |||
| Znacznik czasu ekstrakcji ExtractionTimestamp | Data i godzina wyodrębnienia danych z systemu źródłowego. | ||
| Opis Ten atrybut zapisuje znacznik czasu ekstrakcji danych. Informuje, jak aktualne są dane analizowane w narzędziu process mining. Pozwala ocenić aktualność uzyskanych wniosków. Ma znaczenie dla dashboardów monitorujących operacje, ponieważ pomaga upewnić się, że decyzje opierają się na aktualnych informacjach, i skutecznie zarządzać cyklami odświeżania danych. Dlaczego to ważne Informuje o aktualności danych, dzięki czemu analiza i raportowanie mogą opierać się na najnowszych dostępnych informacjach. Skąd pobrać To nie jest pole SAP. Dodaje je narzędzie do ekstrakcji danych lub proces ETL podczas pobierania danych. Przykłady 2023-10-27T02:00:00Z2023-10-28T02:00:00Z2023-10-29T02:00:00Z | |||
Działania w procesie obsługi faktur w cyklu od zakupu do płatności
| Działanie | Opis | ||
|---|---|---|---|
| Akceptacja faktury | To zdarzenie oznacza, że faktura została zaakceptowana przez uprawnioną osobę. Rejestruje się je po pomyślnym zakończeniu workflow akceptacji lub ustawieniu wskaźnika zwolnienia. | ||
| Dlaczego to ważne To ważny etap, po którym faktura może zostać opłacona. Opóźnienia w akceptacji często tworzą wąskie gardło. Monitorowanie tego zdarzenia pomaga wskazać osoby lub etapy procesu, które spowalniają obsługę. Skąd pobrać Zdarzenie można ustalić na podstawie końcowego etapu zwolnienia w workflow SAP lub śledząc zmiany pól statusu zwolnienia w tabelach powiązanych z fakturą albo dokumentem zakupu. Rejestrowanie Ustal zdarzenie na podstawie zakończenia workflow lub zmian pola statusu zwolnienia dokumentu. Typ zdarzenia inferred | |||
| Odwrócenie faktury | Czynność oznaczająca odwrócenie wcześniej zaksięgowanego dokumentu faktury. W przypadku błędnej faktury jest to zdarzenie końcowe, po którym często wprowadza się poprawną fakturę. | ||
| Dlaczego to ważne Odwrócenia wskazują na poważne błędy, których nie wykryto na wcześniejszych etapach procesu. Śledzenie ich częstotliwości i przyczyn źródłowych jest niezbędne, by usprawniać proces i ograniczać nieścisłości finansowe. Skąd pobrać Odwrócenie można rozpoznać po utworzeniu dokumentu odwracającego. Nagłówek pierwotnego dokumentu (BKPF) zawiera numer dokumentu odwracającego (BKPF-STBLG), a nagłówek dokumentu odwracającego zawiera numer dokumentu pierwotnego. Czasem zdarzenia jest data księgowania dokumentu odwracającego. Rejestrowanie Należy znaleźć dokumenty z wartością w polu BKPF-STBLG i użyć daty księgowania dokumentu odwracającego. Typ zdarzenia explicit | |||
| Realizacja płatności | To ostatnia czynność w standardowym procesie. Płatność zostaje zrealizowana, a faktura rozliczona. Oznacza to, że środki zostały przekazane dostawcy. | ||
| Dlaczego to ważne To koniec cyklu życia faktury w procesie P2P. Ten etap jest niezbędny do obliczenia całkowitego czasu realizacji procesu oraz oceny terminowości płatności względem terminu płatności. Skąd pobrać Zdarzenie jest rejestrowane na podstawie informacji o rozliczeniu pozycji dostawcy. Data rozliczenia (BSEG-AUGDT) i numer dokumentu rozliczającego (BSEG-AUGBL) wskazują, że płatność została zrealizowana. Rejestrowanie Należy użyć daty rozliczenia (BSEG-AUGDT) z rozliczonej pozycji dostawcy. Typ zdarzenia explicit | |||
| Utworzenie dokumentu faktury | To pierwsze zdarzenie, które oznacza utworzenie dokumentu faktury w SAP. Można je zarejestrować w chwili zapisania przez użytkownika nowego dokumentu, który może mieć status wstępnie wprowadzony lub niezaksięgowany. | ||
| Dlaczego to ważne To zdarzenie rozpoczyna cykl obsługi faktury. Pomiar czasu od tego momentu do kolejnych zdarzeń jest niezbędny do określenia całkowitego czasu obsługi. Skąd pobrać Zdarzenie można zarejestrować na podstawie daty i godziny utworzenia (CPUDT, CPUTM) w tabeli nagłówka dokumentu, zwykle BKPF lub RBKP w przypadku faktur logistycznych. Kod transakcji (BKPF-TCODE), na przykład FB60, MIRO lub MIR7, wskazuje sposób utworzenia dokumentu. Rejestrowanie Użyj timestampu utworzenia dokumentu faktury z pól BKPF-CPUDT i BKPF-CPUTM. Typ zdarzenia explicit | |||
| Zaksięgowanie faktury | To ważne zdarzenie finansowe, w którym wstępnie wprowadzona lub zaakceptowana faktura zostaje formalnie zaksięgowana w księdze głównej. W ten sposób zobowiązanie wobec dostawcy zostaje ujęte w księgach. | ||
| Dlaczego to ważne Zaksięgowanie to ważny etap, który oddziela wprowadzanie i zatwierdzanie danych od rozliczenia finansowego. Czas od utworzenia faktury do jej zaksięgowania jest miarą sprawności wewnętrznego przetwarzania. Skąd pobrać Zdarzenie to jest identyfikowane na podstawie daty księgowania (BKPF-BUDAT) w nagłówku dokumentu. Jeśli dokument najpierw zaparkowano, znacznik czasu zdarzenia wskazuje moment zmiany jego statusu na zaksięgowany. Rejestrowanie Jako znacznik czasu zdarzenia należy przyjąć datę księgowania (BKPF-BUDAT). Typ zdarzenia explicit | |||
| Aktualizacja danych faktury | To zdarzenie oznacza zmianę dokumentu faktury po jego utworzeniu. Często występuje podczas poprawek po odrzuceniu faktury lub korygowania błędów. | ||
| Dlaczego to ważne Częste aktualizacje wskazują na poprawki i możliwe problemy z jakością danych wprowadzanych na początku procesu. Śledzenie zmian pozwala zmierzyć nakład pracy związany z korektami i wykryć najczęstsze błędy. Skąd pobrać Zmiany ważnych pól są rejestrowane w tabelach dokumentów zmian SAP: CDHDR (nagłówek) i CDPOS (pozycje). Zdarzenia można wygenerować, filtrując zmiany dotyczące odpowiedniego obiektu faktury. Rejestrowanie Wyodrębnij zdarzenia zmian z tabel CDHDR i CDPOS dla obiektu faktury. Typ zdarzenia explicit | |||
| Odrzucenie faktury | Zdarzenie oznacza odrzucenie faktury podczas akceptacji. Powoduje konieczność wprowadzenia poprawek i ponownego przekazania faktury do akceptacji. | ||
| Dlaczego to ważne Odrzucenia faktur wskazują na nieefektywności procesu i problemy z jakością danych. Analiza ich częstotliwości i przyczyn pomaga znaleźć możliwości usprawnień i określić potrzeby szkoleniowe. Skąd pobrać Zdarzenie można ustalić na podstawie określonych zmian statusu w workflow SAP, na przykład statusu „odrzucona”, lub zdarzeń anulujących bieżący workflow akceptacji i przekazujących fakturę z powrotem do osoby obsługującej. Rejestrowanie Ustal zdarzenie na podstawie zmian statusu workflow wskazujących na odrzucenie. Typ zdarzenia inferred | |||
| Opóźniona realizacja płatności | To zdarzenie obliczane, które występuje, gdy płatność za fakturę zostaje zrealizowana po wyznaczonym terminie płatności. Ustala się je przez porównanie dwóch pól daty. | ||
| Dlaczego to ważne Ta czynność bezpośrednio wspiera KPI dotyczące terminowości płatności. Pomaga też wskazać dostawców lub jednostki biznesowe, w których często dochodzi do opóźnień, co może pogarszać relacje z dostawcami i prowadzić do naliczania kar. Skąd pobrać Zdarzenie ustala się przez porównanie daty rozliczenia (BSEG-AUGDT) z terminem płatności netto. Termin ten oblicza się na podstawie daty bazowej (BSEG-ZFBDT) i warunków płatności (BSEG-ZTERM). Rejestrowanie Ustalić przez porównanie BSEG-AUGDT > (BSEG-ZFBDT + liczba dni wynikająca z warunków płatności). Typ zdarzenia calculated | |||
| Przekazanie faktury do akceptacji | To zdarzenie oznacza rozpoczęcie formalnego workflow akceptacji faktury. Zwykle można je rozpoznać po zmianie statusu faktury na „oczekuje na akceptację” lub utworzeniu elementu workflow. | ||
| Dlaczego to ważne To punkt początkowy pomiaru czasu akceptacji. Wiedza o tym, kiedy rozpoczyna się akceptacja, jest niezbędna do wykrycia wąskich gardeł w samym workflow akceptacji. Skąd pobrać Zdarzenie można zwykle ustalić na podstawie rozpoczęcia SAP Business Workflow (tabela SWW_WI2OBJ) powiązanego z obiektem faktury, na przykład BUS2081, lub zmiany niestandardowego pola statusu w nagłówku dokumentu. Rejestrowanie Ustal zdarzenie na podstawie utworzenia elementu workflow powiązanego z dokumentem faktury. Typ zdarzenia inferred | |||
| Ustawienie blokady płatności | To czynność polegająca na nałożeniu blokady na fakturę, aby uniemożliwić jej opłacenie. Przyczyną mogą być na przykład rozbieżności w cenie lub ilości albo oczekiwanie na notę kredytową. | ||
| Dlaczego to ważne Blokady płatności często powodują opóźnienia i spory z dostawcami. Analiza ich częstotliwości, czasu trwania i przyczyn jest niezbędna do poprawy terminowości płatności. Skąd pobrać Zdarzenie można zarejestrować, śledząc zmiany pola klucza blokady płatności (BSEG-ZLSPR) w pozycji faktury. Dzienniki zmian CDHDR i CDPOS zawierają timestamp oraz użytkownika, który ustawił blokadę. Rejestrowanie Ustal, kiedy pole BSEG-ZLSPR zostało wypełnione, korzystając z dokumentów zmian (CDHDR/CDPOS). Typ zdarzenia explicit | |||
| Usunięcie blokady płatności | Zdarzenie oznacza rozwiązanie problemu i usunięcie wcześniej ustawionej blokady płatności. Faktura ponownie kwalifikuje się do zapłaty. | ||
| Dlaczego to ważne Czas od ustawienia do usunięcia blokady to czas rozwiązania wyjątku w procesie. Skrócenie tego okresu poprawia efektywność i relacje z dostawcami. Skąd pobrać Zdarzenie można zarejestrować, gdy pole klucza blokady płatności (BSEG-ZLSPR) zostanie wyczyszczone. Zmiana jest zapisywana w tabelach CDHDR i CDPOS, które zawierają timestamp usunięcia blokady. Rejestrowanie Ustal, kiedy pole BSEG-ZLSPR zostało wyczyszczone, korzystając z dokumentów zmian (CDHDR/CDPOS). Typ zdarzenia explicit | |||
| Utworzenie propozycji płatności | Faktura zostaje wybrana i uwzględniona w propozycji płatności w ramach przebiegu płatności. To pierwszy etap zautomatyzowanego procesu płatności. | ||
| Dlaczego to ważne Ta czynność wskazuje zamiar dokonania płatności. Opóźnienia między tym etapem a realizacją płatności mogą świadczyć o problemach z przebiegiem płatności, zatwierdzeniami lub komunikacją z bankiem. Skąd pobrać Informacje te znajdują się w tabelach przebiegu płatności, a konkretnie w REGUP, która zawiera pozycje uwzględnione w propozycji płatności. Znacznik czasu można ustalić na podstawie daty przebiegu w powiązanej tabeli REGUH. Rejestrowanie Należy ustalić, kiedy faktura pojawia się w tabeli REGUP w ramach przebiegu propozycji płatności. Typ zdarzenia explicit | |||
| Wstępne wprowadzenie faktury | Faktura została wprowadzona do systemu, ale nie została jeszcze zaksięgowana w księdze głównej. Wstępne wprowadzenie pozwala zapisać niekompletną fakturę lub odłożyć ją do sprawdzenia przed zaksięgowaniem. | ||
| Dlaczego to ważne Wstępne wprowadzenie oznacza celową przerwę w procesie. Pomiar czasu i częstotliwości takich przypadków pomaga ustalić przyczyny opóźnień przed rozpoczęciem formalnego księgowania i akceptacji. Skąd pobrać Można to ustalić na podstawie dokumentów utworzonych za pomocą transakcji wstępnego wprowadzania, takich jak MIR7 lub FV60, albo sprawdzając odpowiednie pola statusu w tabeli BKPF lub dedykowane tabele dokumentów wstępnie wprowadzonych, takie jak VBKPF. Rejestrowanie Wskaż dokumenty utworzone za pomocą transakcji wstępnego wprowadzania lub sprawdź, czy mają status dokumentu wstępnie wprowadzonego. Typ zdarzenia explicit | |||
Instrukcje ekstrakcji danych
Kroki
- Wymagania wstępne i uprawnienia: Należy upewnić się, że użytkownik wykonujący ekstrakcję ma w SAP S/4HANA uprawnienia do wymaganych widoków Core Data Services (CDS). Należą do nich
I_InvoiceDocument,I_OperationalAcctgDocItem,I_ChangeDocument,I_ChangeDocumentItemiI_PaymentProposalItem. Użytkownik potrzebuje również uprawnień do wykonywania zapytań przez wybrany interfejs, na przykład usługę OData lub bezpośrednie połączenie SQL. - Wybór metody połączenia: Należy ustalić, jak połączyć się z systemem SAP S/4HANA, aby wykonać zapytanie SQL. Można użyć SAP Data Services, SAP Data Intelligence, zewnętrznego narzędzia ETL z konektorem SAP albo bezpośredniego połączenia SQL z bazą SAP HANA, jeśli zezwalają na to zasady bezpieczeństwa organizacji.
- Ustalenie parametrów ekstrakcji: Przed wykonaniem zapytania należy określić najważniejsze parametry. Trzeba podać zakres dat ekstrakcji, na przykład
CreationDatemiędzy'YYYY-MM-DD'a'YYYY-MM-DD'. Należy też wskazać wartościCompanyCode, które mają zostać uwzględnione, aby ograniczyć zakres pobieranych danych. - Dostosowanie zapytania SQL: Należy skopiować podane zapytanie SQL do wybranego klienta SQL lub narzędzia do ekstrakcji danych. Trzeba dokładnie sprawdzić symbole zastępcze, takie jak
'{StartDate}','{EndDate}'i('{CompanyCode1}', '{CompanyCode2}'), a następnie zastąpić je wartościami ustalonymi w poprzednim kroku. W zależności od konfiguracji SAP może być też konieczne dostosowanie nazw pól określających status workflow. - Wykonanie zapytania: Należy uruchomić pełne zapytanie SQL w bazie SAP S/4HANA lub za pośrednictwem odpowiedniej warstwy usług. Zapytanie obejmuje szeroki zakres danych, dlatego jego wykonanie może zająć dużo czasu, zależnie od ilości danych i wybranego zakresu dat. Warto monitorować przebieg i sprawdzać, czy nie występują błędy lub przekroczenia limitu czasu.
- Wstępna kontrola wyników: Po zakończeniu zapytania należy szybko sprawdzić wyniki. Trzeba upewnić się, że kolumny
InvoiceNumber,ActivityNameiEventTimezawierają dane. W kolumnieActivityNamepowinny występować różne działania, a nie tylko 'Invoice Document Created'. - Przygotowanie danych: Zapytanie ma zwracać dane w uporządkowanym formacie dziennika zdarzeń. Należy jednak sprawdzić, czy kolumna
EventTimema spójny format znacznika czasu, na przykładYYYY-MM-DDTHH:MM:SS. W razie potrzeby zapytanie łączy pola daty i czasu w jeden znacznik czasu. - Eksport danych: Należy wyeksportować końcowy zestaw wyników z narzędzia do pliku CSV (wartości rozdzielane przecinkami). Ten format jest zgodny z narzędziami process mining, w tym ProcessMind.
- Przygotowanie pliku do przesłania: Przed przesłaniem należy sprawdzić, czy plik CSV jest zapisany w kodowaniu UTF-8, aby uniknąć problemów ze znakami. Nagłówki kolumn muszą dokładnie odpowiadać wymaganym atrybutom:
InvoiceNumber,ActivityName,EventTime,UserName,CompanyCodeitd. - Przesłanie danych do ProcessMind: Należy przesłać przygotowany plik CSV do projektu process mining. Następnie trzeba przypisać kolumny z pliku do pól identyfikatora case, nazwy działania i znacznika czasu w konfiguracji modelu danych narzędzia.
Konfiguracja
- Używane widoki CDS: Głównymi źródłami danych są standardowe widoki SAP CDS. Najważniejsze z nich to
I_InvoiceDocumentz danymi nagłówkowymi,I_OperationalAcctgDocItemze szczegółami księgowania i rozliczenia orazI_ChangeDocumentwraz zI_ChangeDocumentItem, które służą do śledzenia zmian historycznych atrybutów faktury, takich jak blokady płatności i status workflow. - Filtrowanie zakresu dat: Aby zachować wydajność, należy ograniczyć dane do określonego zakresu dat. Podane zapytanie zawiera symbol zastępczy dla
CreationDatew widokuI_InvoiceDocument. Na początek zaleca się pobranie danych z okresu od 3 do 6 miesięcy. - Filtrowanie według kodu spółki: Aby ekstrakcja obejmowała właściwy zakres danych i była łatwa do obsłużenia, należy zawsze filtrować według co najmniej jednego
CompanyCode. Zapytanie zawiera w tym celu symbol zastępczyWHERE inv.CompanyCode IN ('{CompanyCode1}', '{CompanyCode2}'). - Filtrowanie według typu dokumentu: Zakres ekstrakcji można dodatkowo ograniczyć, filtrując według
InvoiceDocumentType. Można na przykład uwzględnić standardowe faktury dostawców (RE), a wykluczyć noty kredytowe. Filtr można dodać do klauzuliWHEREw początkowym CTE. - Wymagania wstępne: Użytkownik wykonujący zapytanie potrzebuje odpowiednich uprawnień do wyświetlania dokumentów finansowych i zakupowych w określonych kodach spółek. Dostęp do bazowej bazy HANA przez klienta SQL nie jest standardowo dostępny i wymaga specjalnych uprawnień.
- Wydajność: Pobieranie danych z tabel dokumentów zmian (
I_ChangeDocument,I_ChangeDocumentItem) może znacznie obciążać system. Aby uniknąć długiego czasu wykonania, należy zastosować ścisłe filtry dotyczące daty, kodu spółki i klasy obiektu (INCOMINGINVOICE).
Przykładowe zapytanie sql
WITH InvoiceBase AS (
SELECT
inv.InvoiceDocument,
inv.FiscalYear,
inv.CompanyCode,
inv.Supplier AS VendorNumber,
inv.DocumentType,
inv.GrossInvoiceAmountInCoCoCrcy AS AmountInCompanyCodeCurrency,
inv.NetDueDate AS PaymentDueDate,
inv.PurchasingDocument,
inv.CreationDateTime,
inv.CreatedByUser,
accdoc.AccountingDocument,
accdoc.ClearingDate,
accdoc.ClearingJournalEntry,
accdoc.PaymentBlockReason,
accdoc.IsReversed
FROM I_InvoiceDocument AS inv
LEFT JOIN I_OperationalAcctgDocItem AS accdoc
ON inv.AccountingDocument = accdoc.AccountingDocument
AND inv.FiscalYear = accdoc.FiscalYear
AND inv.CompanyCode = accdoc.CompanyCode
WHERE
inv.CreationDate BETWEEN '{StartDate}' AND '{EndDate}'
AND inv.CompanyCode IN ('{CompanyCode1}', '{CompanyCode2}')
)
-- 1. Invoice Document Created
SELECT
InvoiceDocument AS "InvoiceNumber",
'Invoice Document Created' AS "ActivityName",
CreationDateTime AS "EventTime",
CreatedByUser AS "UserName",
CompanyCode AS "CompanyCode",
VendorNumber AS "VendorNumber",
AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
PaymentDueDate AS "PaymentDueDate",
DocumentType AS "DocumentType",
CAST(NULL AS VARCHAR(1)) AS "PaymentBlockReason",
PurchasingDocument AS "PurchasingDocument"
FROM InvoiceBase
UNION ALL
-- 2. Invoice Parked
SELECT
i.InvoiceDocument AS "InvoiceNumber",
'Invoice Parked' AS "ActivityName",
i.CreationDateTime AS "EventTime",
i.CreatedByUser AS "UserName",
i.CompanyCode AS "CompanyCode",
i.Supplier AS "VendorNumber",
i.GrossInvoiceAmountInCoCoCrcy AS "AmountInCompanyCodeCurrency",
i.NetDueDate AS "PaymentDueDate",
i.DocumentType AS "DocumentType",
CAST(NULL AS VARCHAR(1)) AS "PaymentBlockReason",
i.PurchasingDocument AS "PurchasingDocument"
FROM I_InvoiceDocument AS i
WHERE
i.InvoiceDocumentIsParked = 'X'
AND i.CreationDate BETWEEN '{StartDate}' AND '{EndDate}'
AND i.CompanyCode IN ('{CompanyCode1}', '{CompanyCode2}')
UNION ALL
-- 3, 4, 5. Workflow activities (Sent for Approval, Approved, Rejected) from Change Docs
SELECT
cdpos.ObjectValue AS "InvoiceNumber",
CASE
WHEN cdpos.ValueNew = '[StatusSentForApproval]' THEN 'Invoice Sent For Approval'
WHEN cdpos.ValueNew = '[StatusApproved]' THEN 'Invoice Approved'
WHEN cdpos.ValueNew = '[StatusRejected]' THEN 'Invoice Rejected'
END AS "ActivityName",
CAST(cdhdr.ChangeDate AS TIMESTAMP) + CAST(cdhdr.ChangeTime AS TIME) AS "EventTime",
cdhdr.UserName AS "UserName",
inv.CompanyCode AS "CompanyCode",
inv.VendorNumber AS "VendorNumber",
inv.AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
inv.PaymentDueDate AS "PaymentDueDate",
inv.DocumentType AS "DocumentType",
CAST(NULL AS VARCHAR(1)) AS "PaymentBlockReason",
inv.PurchasingDocument AS "PurchasingDocument"
FROM I_ChangeDocument AS cdhdr
JOIN I_ChangeDocumentItem AS cdpos ON cdhdr.ChangeDocument = cdpos.ChangeDocument
JOIN InvoiceBase AS inv ON cdpos.ObjectValue = inv.InvoiceDocument
WHERE
cdhdr.ObjectClassName = 'INCOMINGINVOICE'
AND cdpos.FieldName = '[WorkflowStatusFieldName]'
AND cdpos.ValueNew IN ('[StatusSentForApproval]', '[StatusApproved]', '[StatusRejected]')
UNION ALL
-- 6. Invoice Data Updated
SELECT
cdpos.ObjectValue AS "InvoiceNumber",
'Invoice Data Updated' AS "ActivityName",
CAST(cdhdr.ChangeDate AS TIMESTAMP) + CAST(cdhdr.ChangeTime AS TIME) AS "EventTime",
cdhdr.UserName AS "UserName",
inv.CompanyCode AS "CompanyCode",
inv.VendorNumber AS "VendorNumber",
inv.AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
inv.PaymentDueDate AS "PaymentDueDate",
inv.DocumentType AS "DocumentType",
CAST(NULL AS VARCHAR(1)) AS "PaymentBlockReason",
inv.PurchasingDocument AS "PurchasingDocument"
FROM I_ChangeDocument AS cdhdr
JOIN I_ChangeDocumentItem AS cdpos ON cdhdr.ChangeDocument = cdpos.ChangeDocument
JOIN InvoiceBase AS inv ON cdpos.ObjectValue = inv.InvoiceDocument
WHERE
cdhdr.ObjectClassName = 'INCOMINGINVOICE'
AND cdpos.FieldName IN ('GrossInvoiceAmount', 'DocumentDate', 'PaymentTerms')
AND cdhdr.ChangeDate BETWEEN '{StartDate}' AND '{EndDate}'
UNION ALL
-- 7 & 8. Payment Block Set/Removed
SELECT
inv.InvoiceDocument AS "InvoiceNumber",
CASE
WHEN cdpos.ValueNew <> '' AND cdpos.ValueOld = '' THEN 'Payment Block Set'
WHEN cdpos.ValueNew = '' AND cdpos.ValueOld <> '' THEN 'Payment Block Removed'
END AS "ActivityName",
CAST(cdhdr.ChangeDate AS TIMESTAMP) + CAST(cdhdr.ChangeTime AS TIME) AS "EventTime",
cdhdr.UserName AS "UserName",
inv.CompanyCode AS "CompanyCode",
inv.VendorNumber AS "VendorNumber",
inv.AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
inv.PaymentDueDate AS "PaymentDueDate",
inv.DocumentType AS "DocumentType",
cdpos.ValueNew AS "PaymentBlockReason",
inv.PurchasingDocument AS "PurchasingDocument"
FROM I_ChangeDocument AS cdhdr
JOIN I_ChangeDocumentItem AS cdpos ON cdhdr.ChangeDocument = cdpos.ChangeDocument
JOIN InvoiceBase AS inv ON cdpos.ObjectValue = inv.AccountingDocument
WHERE
cdhdr.ObjectClassName = 'BELEG'
AND cdpos.TableName = 'BSEG'
AND cdpos.FieldName = 'ZLSPR'
AND ( (cdpos.ValueNew <> '' AND cdpos.ValueOld = '') OR (cdpos.ValueNew = '' AND cdpos.ValueOld <> '') )
UNION ALL
-- 9. Invoice Posted
SELECT
inv.InvoiceDocument AS "InvoiceNumber",
'Invoice Posted' AS "ActivityName",
CAST(accdoc.PostingDate AS TIMESTAMP) AS "EventTime",
accdoc.CreatedByUser AS "UserName",
inv.CompanyCode AS "CompanyCode",
inv.VendorNumber AS "VendorNumber",
inv.AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
inv.PaymentDueDate AS "PaymentDueDate",
inv.DocumentType AS "DocumentType",
accdoc.PaymentBlockReason AS "PaymentBlockReason",
inv.PurchasingDocument AS "PurchasingDocument"
FROM InvoiceBase AS inv
JOIN I_OperationalAcctgDocItem AS accdoc ON inv.AccountingDocument = accdoc.AccountingDocument
WHERE inv.AccountingDocument IS NOT NULL AND inv.IsReversed = FALSE
UNION ALL
-- 10. Payment Proposal Created
SELECT
item.InvoiceReference AS "InvoiceNumber",
'Payment Proposal Created' AS "ActivityName",
CAST(prun.PaymentRunDate AS TIMESTAMP) AS "EventTime",
prun.CreatedByUser AS "UserName",
item.CompanyCode AS "CompanyCode",
item.Supplier AS "VendorNumber",
item.AmountInTransactionCurrency AS "AmountInCompanyCodeCurrency",
item.NetDueDate AS "PaymentDueDate",
item.AccountingDocumentType AS "DocumentType",
item.PaymentBlockReason AS "PaymentBlockReason",
item.PurchasingDocument AS "PurchasingDocument"
FROM I_PaymentProposalItem as item
JOIN I_PaymentRun as prun ON item.PaymentRunName = prun.PaymentRunName
JOIN InvoiceBase AS inv ON item.InvoiceReference = inv.InvoiceDocument
UNION ALL
-- 11 & 12. Payment Executed / Late Payment Executed
SELECT
InvoiceDocument AS "InvoiceNumber",
CASE
WHEN ClearingDate > PaymentDueDate THEN 'Late Payment Executed'
ELSE 'Payment Executed'
END AS "ActivityName",
CAST(ClearingDate AS TIMESTAMP) AS "EventTime",
CAST(NULL AS VARCHAR(12)) AS "UserName", -- User for clearing is not always straightforward
CompanyCode AS "CompanyCode",
VendorNumber AS "VendorNumber",
AmountInCompanyCodeCurrency AS "AmountInCompanyCodeCurrency",
PaymentDueDate AS "PaymentDueDate",
DocumentType AS "DocumentType",
'' AS "PaymentBlockReason",
PurchasingDocument AS "PurchasingDocument"
FROM InvoiceBase
WHERE ClearingDate IS NOT NULL AND IsReversed = FALSE
UNION ALL
-- 13. Invoice Reversed
SELECT
rev.OriginalInvoiceDocument AS "InvoiceNumber",
'Invoice Reversed' AS "ActivityName",
rev.CreationDateTime AS "EventTime",
rev.CreatedByUser AS "UserName",
rev.CompanyCode AS "CompanyCode",
rev.Supplier AS "VendorNumber",
rev.GrossInvoiceAmountInCoCoCrcy AS "AmountInCompanyCodeCurrency",
CAST(NULL AS DATE) AS "PaymentDueDate",
rev.DocumentType AS "DocumentType",
CAST(NULL AS VARCHAR(1)) AS "PaymentBlockReason",
rev.PurchasingDocument AS "PurchasingDocument"
FROM I_InvoiceDocument AS rev
WHERE rev.OriginalInvoiceDocument IN (SELECT InvoiceDocument FROM InvoiceBase) AND rev.IsReversal = 'X' Kroki
- Należy potwierdzić, że bezpośredni dostęp tylko do odczytu do dzierżawy SAP HANA lub schematu bazy danych jest zatwierdzony. Trzeba uzyskać użytkownika bazy danych z uprawnieniami tylko do odczytu do wymaganych tabel SAP oraz zatwierdzonych tabel historii zmian lub workflow. Należy używać SAP HANA Database Explorer, SAP HANA Studio albo zatwierdzonego klienta SQL. Nie wolno korzystać z dostępu do zapisu w środowisku produkcyjnym.
- Należy potwierdzić fizyczne nazwy tabel i kolumn w docelowym systemie S/4HANA. ACDOCA, BKPF i RBKP to standardowe punkty wyjścia, ale workflow, parkowanie dokumentów, propozycje płatności, realizacja płatności, historia zmian i historia blokad płatności mogą korzystać z obiektów zależnych od wersji lub konfiguracji klienta. Każdy symbol zastępczy w nawiasach kwadratowych należy zastąpić obiektami zweryfikowanymi w katalogu systemowym i odpowiadającymi właściwym pojęciom biznesowym.
- Należy określić okres ekstrakcji za pomocą [Start timestamp] i [End timestamp]. Trzeba uwzględnić odpowiednio szeroki okres dokumentów i zdarzeń, zwykle od trzech do sześciu miesięcy, i wydłużyć go, jeśli terminy płatności lub opóźnione płatności mogą przypadać poza okresem utworzenia faktur.
- Należy identyfikować sprawy dotyczące faktur za pomocą skonfigurowanego klucza faktury. Zapytanie używa InvoiceNumber jako identyfikatora case i w razie potrzeby wewnętrznie łączy go z kodem spółki i rokiem obrotowym, aby uniknąć kolizji. Trzeba potwierdzić, czy definicja biznesowa wymaga dodania roku obrotowego lub kodu spółki do identyfikatora case w ProcessMind.
- Należy przypisać dane zaksięgowanych faktur z RBKP, BKPF i ACDOCA. RBKP zawiera informacje nagłówkowe faktury, BKPF znaczniki czasu i użytkowników dokumentu księgowego, a ACDOCA dane dostawcy, kwoty, dokumentu zakupu, rozliczenia i księgowania płatności, jeśli są dostępne. Nie należy zakładać, że każde pole jest wypełnione w każdym scenariuszu księgowania.
- Zatwierdzenia, odrzucenia, aktualizacje, blokady płatności, storna, propozycje i realizację płatności należy odwzorować na podstawie zweryfikowanych źródeł właściwych dla danego systemu. Symbole zastępcze źródeł trzeba zastąpić zatwierdzonymi widokami lub tabelami, które udostępniają znaczniki czasu zdarzeń, odwołania do faktur, użytkowników, statusy oraz wartości poprzednie i nowe. Każde działanie musi być zapisane jako osobny wiersz zdarzenia, ponieważ ProcessMind nie wywnioskuje zdarzeń samodzielnie.
- Należy wykonać pełne zapytanie SQL w środowisku nieprodukcyjnym lub sesji tylko do odczytu. Warto sprawdzić plany wykonania i w razie potrzeby ograniczyć zapytanie według kodu spółki, typu dokumentu, roku obrotowego i znacznika czasu zdarzenia. Należy unikać nieograniczonych złączeń dużych tabel księgowych i tabel historii.
- Wynik należy zweryfikować za pomocą opisanych niżej kontroli. Trzeba potwierdzić obecność wszystkich wymaganych kolumn, wypełnienie
EventTimedla każdego zdarzenia iInvoiceNumberdla każdej sprawy oraz występowanie wszystkich 13 nazw działań, jeśli istnieją odpowiadające im dane źródłowe. - Wynik należy wyeksportować do pliku rozdzielanego obsługiwanego przez ProcessMind, najlepiej CSV w kodowaniu UTF-8, z jednym wierszem na zdarzenie i kolumnami InvoiceNumber, ActivityName, EventTime, UserName, CompanyCode, VendorNumber, AmountInCompanyCodeCurrency, PaymentDueDate, DocumentType, PaymentBlockReason i PurchasingDocument. Znaczniki czasu powinny mieć spójną strefę czasową, a identyfikatory zachowane z zerami wiodącymi.
- Należy przesłać dziennik zdarzeń do ProcessMind i skonfigurować InvoiceNumber jako identyfikator case, ActivityName jako kolumnę działań, a EventTime jako kolumnę znacznika czasu. Jeśli konfiguracja ProcessMind obsługuje dodatkowe klucze case, należy zastosować tę samą zasadę klucza złożonego co podczas ekstrakcji.
Konfiguracja
- Zakres dat: Przy pierwszej ekstrakcji należy użyć ruchomego okresu od trzech do sześciu miesięcy. Warto uwzględnić dodatkową historię, jeśli zatwierdzenia, płatności, rozliczenia, storna lub opóźnione płatności mogą wystąpić po okresie utworzenia faktury.
- Zakres spółek: Należy filtrować według [Company code filter] i sprawdzić, czy wybrane kody spółek są objęte uprawnieniami do ekstrakcji.
- Zakres dokumentów: Należy filtrować według [Document type filter] i uwzględnić typy dokumentów odpowiadające fakturom dostawców, notom kredytowym, fakturom zaparkowanym i stornom w analizowanym procesie.
- Identyfikator case: Zgodnie z definicją procesu należy użyć InvoiceNumber. Jeśli numery faktur nie są unikatowe globalnie, trzeba zachować kod spółki i rok obrotowy w wyniku źródłowym albo skonfigurować klucz złożony zgodnie z modelem ProcessMind.
- Źródła zdarzeń: Należy zweryfikować fizyczne źródła zmian statusu workflow, decyzji akceptacyjnych, parkowania, historii zmian, blokad płatności, propozycji płatności i realizacji płatności. Źródła te zależą od wersji S/4HANA, aktywowanego zakresu, konfiguracji workflow i rozszerzeń klienta.
- Zasady dotyczące znaczników czasu: Należy wybrać znacznik czasu zdarzenia biznesowego, a nie ekstrakcji. Trzeba udokumentować strefę czasową i ujednolicić znaczniki czasu wszystkich zdarzeń przed przesłaniem.
- Zasady dotyczące kwot: Należy używać kwoty w walucie kodu spółki i potwierdzić, czy wybrane źródło spójnie zapisuje znaki debetu i kredytu. Nie należy sumować pozycji księgowych, dopóki reguła agregacji dla danej sprawy faktury nie zostanie zweryfikowana.
- Zasady dotyczące płatności: Należy określić, czy „Payment Executed” oznacza rozliczenie, zaksięgowanie dokumentu płatności, realizację przelewu bankowego czy inny etap biznesowy. Trzeba użyć źródła zgodnego z uzgodnioną definicją procesu.
- Opóźniona płatność: Zdarzenie Late Payment Executed należy zapisać tylko wtedy, gdy Payment Executed nastąpi po PaymentDueDate. Zapytanie oblicza to zdarzenie jawnie i nie polega na wnioskowaniu ProcessMind.
- Wydajność: Odczyt źródeł należy ograniczyć według daty, kodu spółki, typu dokumentu i odpowiedniego roku obrotowego. Warto wybierać tylko wymagane kolumny, sprawdzać plany zapytań i tworzyć zatwierdzone widoki pośrednie, jeśli historia źródłowa jest obszerna.
- Wymagania wstępne: Bezpośrednie połączenie z SAP HANA, uprawnienia do odczytu wszystkich wybranych obiektów, możliwość sprawdzania metadanych oraz dostęp do odpowiednich danych z obszarów zobowiązań, księgi głównej, zakupów, workflow i płatności. Należy potwierdzić wymagane licencje SAP, zasady dostępu do bazy danych i zgody dotyczące ochrony danych.
- Bezpieczeństwo: Należy używać technicznego użytkownika z uprawnieniami tylko do odczytu, chronić dane dostawców i płatności oraz przestrzegać zasad organizacji dotyczących transportu, audytu, maskowania danych i zarządzania danymi uwierzytelniającymi.
Przykładowe zapytanie sql
WITH
invoice_base AS (
SELECT
r.INV_DOC_NO AS InvoiceNumber,
r.COMPANY_CODE AS CompanyCode,
r.FISCAL_YEAR AS FiscalYear,
r.DOCUMENT_TYPE AS DocumentType,
r.VENDOR_NO AS VendorNumber,
r.GROSS_AMOUNT_CC AS AmountInCompanyCodeCurrency,
r.PAYMENT_DUE_DATE AS PaymentDueDate,
r.PURCHASING_DOCUMENT AS PurchasingDocument,
r.CREATED_AT AS InvoiceCreatedAt,
r.CREATED_BY AS InvoiceCreatedBy
FROM [Your RBKP invoice header source] r
WHERE r.CREATED_AT >= '[Start timestamp]'
AND r.CREATED_AT < '[End timestamp]'
AND r.COMPANY_CODE IN ([Company code filter])
AND r.DOCUMENT_TYPE IN ([Document type filter])
),
posted_accounting AS (
SELECT
b.INV_DOC_NO AS InvoiceNumber,
b.COMPANY_CODE AS CompanyCode,
b.FISCAL_YEAR AS FiscalYear,
b.ACCOUNTING_DOCUMENT AS AccountingDocument,
b.POSTING_DATE AS PostingDate,
b.CREATED_AT AS PostedAt,
b.CREATED_BY AS PostedBy,
b.REVERSAL_DOCUMENT AS ReversalDocument,
b.REVERSED_DOCUMENT AS ReversedDocument
FROM [Your BKPF accounting document source] b
WHERE b.CREATED_AT >= '[Start timestamp]'
AND b.CREATED_AT < '[End timestamp]'
AND b.COMPANY_CODE IN ([Company code filter])
),
journal_attributes AS (
SELECT
a.COMPANY_CODE AS CompanyCode,
a.FISCAL_YEAR AS FiscalYear,
a.ACCOUNTING_DOCUMENT AS AccountingDocument,
MAX(a.VENDOR_NO) AS VendorNumber,
SUM(a.AMOUNT_IN_COMPANY_CODE_CURRENCY) AS AmountInCompanyCodeCurrency,
MAX(a.PURCHASING_DOCUMENT) AS PurchasingDocument,
MAX(a.CLEARING_DATE) AS ClearingDate,
MAX(a.CLEARING_DOCUMENT) AS ClearingDocument
FROM [Your ACDOCA universal journal source] a
WHERE a.COMPANY_CODE IN ([Company code filter])
AND a.POSTING_DATE >= '[Start date]'
AND a.POSTING_DATE < '[End date]'
GROUP BY
a.COMPANY_CODE,
a.FISCAL_YEAR,
a.ACCOUNTING_DOCUMENT
),
source_events AS (
SELECT
e.INV_DOC_NO AS InvoiceNumber,
e.COMPANY_CODE AS CompanyCode,
e.FISCAL_YEAR AS FiscalYear,
e.EVENT_TIMESTAMP AS EventTime,
e.EVENT_USER AS UserName,
e.PAYMENT_BLOCK_REASON AS PaymentBlockReason,
e.PURCHASING_DOCUMENT AS PurchasingDocument,
e.VENDOR_NO AS VendorNumber,
e.AMOUNT_IN_COMPANY_CODE_CURRENCY AS AmountInCompanyCodeCurrency,
e.PAYMENT_DUE_DATE AS PaymentDueDate,
e.DOCUMENT_TYPE AS DocumentType,
e.EVENT_TYPE AS SourceEventType
FROM [Your verified invoice event and workflow source] e
WHERE e.EVENT_TIMESTAMP >= '[Start timestamp]'
AND e.EVENT_TIMESTAMP < '[End timestamp]'
AND e.COMPANY_CODE IN ([Company code filter])
),
base_events AS (
SELECT
i.InvoiceNumber,
'Invoice Document Created' AS ActivityName,
i.InvoiceCreatedAt AS EventTime,
i.InvoiceCreatedBy AS UserName,
i.CompanyCode,
COALESCE(i.VendorNumber, j.VendorNumber) AS VendorNumber,
COALESCE(i.AmountInCompanyCodeCurrency, j.AmountInCompanyCodeCurrency) AS AmountInCompanyCodeCurrency,
i.PaymentDueDate,
i.DocumentType,
CAST(NULL AS NVARCHAR(20)) AS PaymentBlockReason,
COALESCE(i.PurchasingDocument, j.PurchasingDocument) AS PurchasingDocument
FROM invoice_base i
LEFT JOIN posted_accounting p
ON p.InvoiceNumber = i.InvoiceNumber
AND p.CompanyCode = i.CompanyCode
AND p.FiscalYear = i.FiscalYear
LEFT JOIN journal_attributes j
ON j.CompanyCode = p.CompanyCode
AND j.FiscalYear = p.FiscalYear
AND j.AccountingDocument = p.AccountingDocument
WHERE i.InvoiceCreatedAt IS NOT NULL
UNION ALL
SELECT
s.InvoiceNumber,
'Invoice Parked' AS ActivityName,
s.EventTime,
s.UserName,
s.CompanyCode,
COALESCE(s.VendorNumber, i.VendorNumber) AS VendorNumber,
COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency) AS AmountInCompanyCodeCurrency,
COALESCE(s.PaymentDueDate, i.PaymentDueDate) AS PaymentDueDate,
COALESCE(s.DocumentType, i.DocumentType) AS DocumentType,
s.PaymentBlockReason,
COALESCE(s.PurchasingDocument, i.PurchasingDocument) AS PurchasingDocument
FROM source_events s
LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PARKED'
UNION ALL
SELECT s.InvoiceNumber, 'Invoice Sent For Approval', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'SENT_FOR_APPROVAL'
UNION ALL
SELECT s.InvoiceNumber, 'Invoice Approved', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'APPROVED'
UNION ALL
SELECT s.InvoiceNumber, 'Invoice Rejected', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'REJECTED'
UNION ALL
SELECT s.InvoiceNumber, 'Invoice Data Updated', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'DATA_UPDATED'
UNION ALL
SELECT s.InvoiceNumber, 'Payment Block Set', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PAYMENT_BLOCK_SET'
UNION ALL
SELECT s.InvoiceNumber, 'Payment Block Removed', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PAYMENT_BLOCK_REMOVED'
UNION ALL
SELECT
i.InvoiceNumber,
'Invoice Posted',
p.PostedAt,
p.PostedBy,
i.CompanyCode,
COALESCE(i.VendorNumber, j.VendorNumber),
COALESCE(i.AmountInCompanyCodeCurrency, j.AmountInCompanyCodeCurrency),
i.PaymentDueDate,
i.DocumentType,
CAST(NULL AS NVARCHAR(20)),
COALESCE(i.PurchasingDocument, j.PurchasingDocument)
FROM invoice_base i
INNER JOIN posted_accounting p ON p.InvoiceNumber = i.InvoiceNumber AND p.CompanyCode = i.CompanyCode AND p.FiscalYear = i.FiscalYear
LEFT JOIN journal_attributes j ON j.CompanyCode = p.CompanyCode AND j.FiscalYear = p.FiscalYear AND j.AccountingDocument = p.AccountingDocument
WHERE p.PostedAt IS NOT NULL
UNION ALL
SELECT s.InvoiceNumber, 'Payment Proposal Created', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PAYMENT_PROPOSAL_CREATED'
UNION ALL
SELECT s.InvoiceNumber, 'Payment Executed', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PAYMENT_EXECUTED'
UNION ALL
SELECT s.InvoiceNumber, 'Late Payment Executed', s.EventTime, s.UserName, s.CompanyCode, COALESCE(s.VendorNumber, i.VendorNumber), COALESCE(s.AmountInCompanyCodeCurrency, i.AmountInCompanyCodeCurrency), COALESCE(s.PaymentDueDate, i.PaymentDueDate), COALESCE(s.DocumentType, i.DocumentType), s.PaymentBlockReason, COALESCE(s.PurchasingDocument, i.PurchasingDocument)
FROM source_events s LEFT JOIN invoice_base i ON i.InvoiceNumber = s.InvoiceNumber AND i.CompanyCode = s.CompanyCode AND i.FiscalYear = s.FiscalYear
WHERE s.SourceEventType = 'PAYMENT_EXECUTED'
AND s.EventTime > CAST(COALESCE(s.PaymentDueDate, i.PaymentDueDate) AS TIMESTAMP)
UNION ALL
SELECT
i.InvoiceNumber,
'Invoice Reversed',
p.ReversalEventAt,
p.ReversalUser,
i.CompanyCode,
COALESCE(i.VendorNumber, j.VendorNumber),
COALESCE(i.AmountInCompanyCodeCurrency, j.AmountInCompanyCodeCurrency),
i.PaymentDueDate,
i.DocumentType,
CAST(NULL AS NVARCHAR(20)),
COALESCE(i.PurchasingDocument, j.PurchasingDocument)
FROM invoice_base i
INNER JOIN [Your verified reversal event source] p ON p.INV_DOC_NO = i.InvoiceNumber AND p.COMPANY_CODE = i.CompanyCode AND p.FISCAL_YEAR = i.FiscalYear
LEFT JOIN journal_attributes j ON j.CompanyCode = p.COMPANY_CODE AND j.FiscalYear = p.FISCAL_YEAR AND j.AccountingDocument = p.ACCOUNTING_DOCUMENT
WHERE p.ReversalEventAt IS NOT NULL
)
SELECT
InvoiceNumber,
ActivityName,
EventTime,
UserName,
CompanyCode,
VendorNumber,
AmountInCompanyCodeCurrency,
PaymentDueDate,
DocumentType,
PaymentBlockReason,
PurchasingDocument
FROM base_events
WHERE InvoiceNumber IS NOT NULL
AND EventTime IS NOT NULL
ORDER BY InvoiceNumber, EventTime, ActivityName; Kroki
- Otwórz edytor ABAP: Zaloguj się do systemu SAP S/4HANA. Otwórz transakcję
SE38(edytor ABAP). - Utwórz program: W polu Program wpisz nazwę nowego programu, na przykład
Z_PM_INVOICE_EXTRACT, i kliknij przycisk „Utwórz”. Podaj tytuł, ustaw typ „Program wykonywalny” i zapisz program w odpowiednim pakiecie. - Zdefiniuj strukturę programu i ekran wyboru: W edytorze zdefiniuj struktury danych dla wynikowego dziennika zdarzeń. Następnie utwórz ekran wyboru, na którym użytkownicy będą mogli podać parametry, takie jak zakres daty wprowadzenia faktury, kody spółek i typy dokumentów. Dzięki temu program będzie można ponownie wykorzystać i łatwo dostosować.
- Zaimplementuj logikę wyboru danych: Napisz podstawowe instrukcje ABAP SQL, które pobiorą dane z różnych tabel SAP. Program powinien kolejno pobierać dane dla każdego z 13 wymaganych działań.
- Pobierz dane nagłówków i pozycji: W przypadku podstawowych zdarzeń, takich jak „Utworzono dokument faktury” i „Zaksięgowano fakturę”, pobierz dane z głównych tabel, na przykład
RBKP(nagłówek faktury logistycznej) iBKPF(nagłówek dokumentu księgowego). - Pobierz dane dokumentów zmian: W przypadku działań takich jak „Ustawiono blokadę płatności” i „Usunięto blokadę płatności” odpytaj tabele dokumentów zmian
CDHDR(nagłówek dokumentu zmian) iCDPOS(pozycje dokumentu zmian). Trzeba zidentyfikować zmiany konkretnych pól, na przykładZLSPRw tabeliBSEG. - Pobierz dane płatności: Aby uwzględnić działania związane z płatnościami, odpytaj tabele takie jak
REGUP(pozycje przetworzone przez program płatniczy) w celu pobrania propozycji płatności orazBSAK(rozliczone pozycje dostawców) w celu pobrania zrealizowanych płatności. Zdarzenie „Zrealizowano opóźnioną płatność” można rozpoznać, porównując datę rozliczenia (AUGDT) z terminem płatności netto (ZFBDT). - Pobierz dane workflow: W przypadku działań związanych z akceptacją odpytaj tabele SAP Business Workflow, takie jak
SWW_WI2OBJ, aby powiązać elementy workflow z obiektami faktur. Ten etap w dużym stopniu zależy od konfiguracji workflow i może wymagać znacznych modyfikacji. - Połącz dane w formacie dziennika zdarzeń: Dane każdego wybranego działania sformatuj w jednej wspólnej strukturze tabeli wewnętrznej. Każdy wiersz tej tabeli reprezentuje pojedyncze zdarzenie i musi zawierać identyfikator case (
InvoiceNumber),ActivityNameiEventTime, a także inne zalecane atrybuty. - Utwórz plik wynikowy: Użyj instrukcji ABAP
OPEN DATASET,TRANSFERiCLOSE DATASET, aby zapisać zawartość końcowej tabeli wewnętrznej do pliku płaskiego na serwerze aplikacyjnym SAP. Zalecany jest format CSV (wartości rozdzielane przecinkami). - Zaplanowanie i uruchomienie: W celu przetestowania uruchom program na pierwszym planie (za pomocą
F8). W środowisku produkcyjnym zaplanuj go jako zadanie w tle za pomocą transakcjiSM36, poza godzinami szczytu, aby nie obciążać systemu. - Pobierz plik i prześlij dane: Użyj transakcji
AL11, aby przejść do katalogu serwera aplikacyjnego, w którym zapisano plik. Pobierz go do lokalnego systemu. Przed przesłaniem do narzędzia process mining sprawdź, czy plik jest zapisany w kodowaniu UTF-8 i ma prawidłowy format.
Konfiguracja
- Zakres dat: Określ zakres dat ekstrakcji na podstawie daty wprowadzenia faktury (
RBKP-CPUDT) lub daty księgowania (BKPF-BUDAT). Przy pierwszej analizie zaleca się okres od 3 do 6 miesięcy, aby ilość danych była możliwa do obsłużenia. - Kod spółki (BUKRS): Należy filtrować dane według co najmniej jednego kodu spółki. Pobranie danych ze wszystkich kodów spółek w dużej organizacji może znacznie wydłużyć czas działania programu i zwiększyć rozmiar plików.
- Typ dokumentu (BLART): Filtruj według odpowiednich typów dokumentów, aby wyodrębnić faktury dostawców. Typowe wartości to 'RE' (faktura brutto) i 'KR' (faktura dostawcy). Dzięki temu z analizy można wykluczyć nieistotne dokumenty.
- Konto dostawcy (LIFNR): Program może opcjonalnie filtrować dane według wybranych numerów dostawców. Przydaje się to w analizach ukierunkowanych i testach.
- Konfiguracja pliku wynikowego: Program powinien umożliwiać określenie ścieżki pliku wynikowego na serwerze aplikacyjnym oraz separatora pól, na przykład przecinka lub średnika.
- Wymagania wstępne: Użytkownik lub konto systemowe uruchamiające program musi mieć uprawnienia programistyczne do tworzenia i uruchamiania programów ABAP (przez
SE38) oraz szerokie uprawnienia do odczytu tabel FI, MM i Basis, w tymBKPF,BSEG,RBKP,RSEG,CDHDR,CDPOSi tabel workflow.
Przykładowe zapytanie abap
REPORT Z_PM_INVOICE_EXTRACT.
* --- Internal table structure for the final event log
TYPES: BEGIN OF ty_s_event_log,
invoicenumber TYPE char25,
activityname TYPE char50,
eventtime TYPE char19, "YYYY-MM-DD HH:MM:SS
username TYPE sy-uname,
companycode TYPE bukrs,
vendornumber TYPE lifnr,
amountincompanycodecurrency TYPE wrbtr,
paymentduedate TYPE char10, "YYYY-MM-DD
documenttype TYPE blart,
paymentblockreason TYPE char1,
purchasingdocument TYPE ebeln,
END OF ty_s_event_log.
DATA: lt_event_log TYPE STANDARD TABLE OF ty_s_event_log.
DATA: ls_event_log TYPE ty_s_event_log.
* --- Selection Screen for user inputs
PARAMETERS: p_path TYPE string DEFAULT '/usr/sap/tmp/invoice_events.csv'.
SELECT-OPTIONS: s_erdat FOR sy-datum OBLIGATORY, " Entry Date
s_bukrs FOR bkpf-bukrs OBLIGATORY, " Company Code
s_blart FOR bkpf-blart. " Document Type
START-OF-SELECTION.
* --- 1. Invoice Document Created (from Logistics Invoice Verification)
SELECT CONCAT( rbkp~belnr, rbkp~gjahr ) AS invoicenumber,
'Invoice Document Created' AS activityname,
CONCAT( rbkp~cpudt, rbkp~cputm ) AS eventtime,
rbkp~usnam AS username,
rbkp~bukrs AS companycode,
rbkp~lifnr AS vendornumber,
rbkp~rmwwr AS amountincompanycodecurrency,
'' AS paymentduedate,
rbkp~blart AS documenttype,
rbkp~zuonr AS paymentblockreason,
'' AS purchasingdocument
FROM rbkp
INTO TABLE @DATA(lt_created)
WHERE rbkp~cpudt IN @s_erdat
AND rbkp~bukrs IN @s_bukrs
AND rbkp~blart IN @s_blart.
LOOP AT lt_created INTO DATA(ls_created).
ls_event_log-invoicenumber = ls_created-invoicenumber.
ls_event_log-activityname = ls_created-activityname.
ls_event_log-eventtime = |{ ls_created-eventtime(8) } { ls_created-eventtime+8(2) }:{ ls_created-eventtime+10(2) }:{ ls_created-eventtime+12(2) }|.
ls_event_log-username = ls_created-username.
ls_event_log-companycode = ls_created-companycode.
ls_event_log-vendornumber = ls_created-vendornumber.
ls_event_log-amountincompanycodecurrency = ls_created-amountincompanycodecurrency.
ls_event_log-paymentduedate = ''.
ls_event_log-documenttype = ls_created-documenttype.
ls_event_log-paymentblockreason = ''.
ls_event_log-purchasingdocument = ls_created-purchasingdocument.
APPEND ls_event_log TO lt_event_log.
ENDLOOP.
* --- 2. Invoice Parked (assuming status 'A' or 'B' in RBKP)
SELECT CONCAT( belnr, gjahr ) AS invoicenumber,
'Invoice Parked' AS activityname,
CONCAT( cpudt, cputm ) AS eventtime,
usnam AS username,
bukrs AS companycode,
lifnr AS vendornumber,
rmwwr AS amountincompanycodecurrency,
'' AS paymentduedate,
blart AS documenttype,
'' AS paymentblockreason,
'' AS purchasingdocument
FROM rbkp
INTO TABLE @DATA(lt_parked)
WHERE rbstat IN ('A', 'B')
AND cpudt IN @s_erdat
AND bukrs IN @s_bukrs
AND blart IN @s_blart.
LOOP AT lt_parked INTO DATA(ls_parked).
ls_event_log-invoicenumber = ls_parked-invoicenumber.
ls_event_log-activityname = ls_parked-activityname.
ls_event_log-eventtime = |{ ls_parked-eventtime(8) } { ls_parked-eventtime+8(2) }:{ ls_parked-eventtime+10(2) }:{ ls_parked-eventtime+12(2) }|.
ls_event_log-username = ls_parked-username.
ls_event_log-companycode = ls_parked-companycode.
ls_event_log-vendornumber = ls_parked-vendornumber.
ls_event_log-amountincompanycodecurrency = ls_parked-amountincompanycodecurrency.
ls_event_log-paymentduedate = ''.
ls_event_log-documenttype = ls_parked-documenttype.
ls_event_log-paymentblockreason = ''.
ls_event_log-purchasingdocument = ''.
APPEND ls_event_log TO lt_event_log.
ENDLOOP.
* --- 3, 4, 5. Sent For Approval, Approved, Rejected (Placeholder logic, needs adaptation)
* --- This logic is a generic template for SAP Business Workflow.
* --- Your implementation will vary. You must identify the correct workflow tasks.
SELECT obj.instid, wi.wi_cd, wi.wi_ct, wi.wi_stat, wi.wi_aagent
FROM sww_wi2obj AS obj
JOIN swwlog AS wi ON obj~instid = wi~wi_id
INTO TABLE @DATA(lt_workflow)
WHERE obj~typeid = 'BUS2081' " Business Object for Incoming Invoice
AND obj~catid = 'BO'
AND wi~wi_cd IN s_erdat.
LOOP AT lt_workflow INTO DATA(ls_workflow).
* --- This is a placeholder, adapt task IDs and logic
CASE ls_workflow-wi_stat.
WHEN 'STARTED'.
ls_event_log-activityname = 'Invoice Sent For Approval'.
WHEN 'COMPLETED'.
ls_event_log-activityname = 'Invoice Approved'.
WHEN 'CANCELLED'.
ls_event_log-activityname = 'Invoice Rejected'.
WHEN OTHERS.
CONTINUE.
ENDCASE.
* --- Code to get invoice details based on ls_workflow-instid needed here
* --- ... appending to lt_event_log ...
ENDLOOP.
* --- 6, 7, 8. Payment Block Set/Removed, Data Updated (from Change Docs)
SELECT h~objectid, h~username, h~udate, h~utime, p~fname, p~value_new, p~value_old
FROM cdhdr AS h
JOIN cdpos AS p ON h~objectclas = p~objectclas AND h~objectid = p~objectid AND h~changenr = p~changenr
INTO TABLE @DATA(lt_changes)
WHERE h~objectclas = 'BELEGV'
AND h~udate IN s_erdat.
LOOP AT lt_changes INTO DATA(ls_change).
ls_event_log-invoicenumber = |{ ls_change-objectid+10(10) }{ ls_change-objectid(4) }|.
ls_event_log-username = ls_change-username.
ls_event_log-eventtime = |{ ls_change-udate } { ls_change-utime(2) }:{ ls_change-utime+2(2) }:{ ls_change-utime+4(2) }|.
IF ls_change-fname = 'ZLSPR'. " Payment Block
IF ls_change-value_old IS INITIAL AND ls_change-value_new IS NOT INITIAL.
ls_event_log-activityname = 'Payment Block Set'.
ls_event_log-paymentblockreason = ls_change-value_new.
ELSEIF ls_change-value_old IS NOT INITIAL AND ls_change-value_new IS INITIAL.
ls_event_log-activityname = 'Payment Block Removed'.
ls_event_log-paymentblockreason = ''.
ELSE.
CONTINUE.
ENDIF.
ELSE.
ls_event_log-activityname = 'Invoice Data Updated'.
ENDIF.
* --- Need to select other attributes based on invoice number
* --- ... appending to lt_event_log ...
ENDLOOP.
* --- 9. Invoice Posted
SELECT CONCAT( bkpf~belnr, bkpf~gjahr ) AS invoicenumber,
'Invoice Posted' AS activityname,
CONCAT( bkpf~cpudt, bkpf~cputm ) AS eventtime,
bkpf~usnam AS username,
bkpf~bukrs AS companycode,
bseg~lifnr AS vendornumber,
bseg~wrbtr AS amountincompanycodecurrency,
bseg~zfBDT AS paymentduedate,
bkpf~blart AS documenttype,
bseg~zlspr AS paymentblockreason,
bseg~ebeln AS purchasingdocument
FROM bkpf
JOIN bseg ON bkpf~bukrs = bseg~bukrs AND bkpf~belnr = bseg~belnr AND bkpf~gjahr = bseg~gjahr
INTO TABLE @DATA(lt_posted)
WHERE bkpf~cpudt IN @s_erdat
AND bkpf~bukrs IN @s_bukrs
AND bkpf~blart IN @s_blart
AND bseg~koart = 'K'. " Vendor line
LOOP AT lt_posted INTO DATA(ls_posted).
ls_event_log-invoicenumber = ls_posted-invoicenumber.
ls_event_log-activityname = ls_posted-activityname.
ls_event_log-eventtime = |{ ls_posted-eventtime(8) } { ls_posted-eventtime+8(2) }:{ ls_posted-eventtime+10(2) }:{ ls_posted-eventtime+12(2) }|.
ls_event_log-username = ls_posted-username.
ls_event_log-companycode = ls_posted-companycode.
ls_event_log-vendornumber = ls_posted-vendornumber.
ls_event_log-amountincompanycodecurrency = ls_posted-amountincompanycodecurrency.
ls_event_log-paymentduedate = ls_posted-paymentduedate.
ls_event_log-documenttype = ls_posted-documenttype.
ls_event_log-paymentblockreason = ls_posted-paymentblockreason.
ls_event_log-purchasingdocument = ls_posted-purchasingdocument.
APPEND ls_event_log TO lt_event_log.
ENDLOOP.
* --- 10. Payment Proposal Created
SELECT CONCAT( regup~belnr, regup~gjahr ) AS invoicenumber,
'Payment Proposal Created' AS activityname,
CONCAT( reguh~erfdt, reguh~erfzt ) AS eventtime,
reguh~erfbu AS username,
regup~bukrs AS companycode,
regup~lifnr AS vendornumber,
regup~wrbtr AS amountincompanycodecurrency,
'' AS paymentduedate,
regup~blart AS documenttype,
'' AS paymentblockreason,
'' AS purchasingdocument
FROM regup
JOIN reguh ON regup~laufd = reguh~laufd AND regup~laufi = reguh~laufi
INTO TABLE @DATA(lt_proposal)
WHERE reguh~erfdt IN @s_erdat
AND regup~bukrs IN @s_bukrs.
LOOP AT lt_proposal INTO DATA(ls_proposal).
ls_event_log-invoicenumber = ls_proposal-invoicenumber.
ls_event_log-activityname = ls_proposal-activityname.
ls_event_log-eventtime = |{ ls_proposal-eventtime(8) } { ls_proposal-eventtime+8(2) }:{ ls_proposal-eventtime+10(2) }:{ ls_proposal-eventtime+12(2) }|.
ls_event_log-username = ls_proposal-username.
ls_event_log-companycode = ls_proposal-companycode.
ls_event_log-vendornumber = ls_proposal-vendornumber.
ls_event_log-amountincompanycodecurrency = ls_proposal-amountincompanycodecurrency.
APPEND ls_event_log TO lt_event_log.
ENDLOOP.
* --- 11, 12. Payment Executed / Late Payment Executed
SELECT CONCAT( belnr, gjahr ) AS invoicenumber,
augdt,
zfBDT
FROM bsak
INTO TABLE @DATA(lt_cleared)
WHERE augdt IN @s_erdat
AND bukrs IN @s_bukrs.
LOOP AT lt_cleared INTO DATA(ls_cleared).
IF ls_cleared-augdt > ls_cleared-zfbdt.
ls_event_log-activityname = 'Late Payment Executed'.
ELSE.
ls_event_log-activityname = 'Payment Executed'.
ENDIF.
ls_event_log-invoicenumber = ls_cleared-invoicenumber.
ls_event_log-eventtime = |{ ls_cleared-augdt } 00:00:00|.
* --- Need to select other attributes based on invoice number
* --- ... appending to lt_event_log ...
ENDLOOP.
* --- 13. Invoice Reversed
SELECT CONCAT( stblg, stjah ) AS invoicenumber,
'Invoice Reversed' AS activityname,
CONCAT( cpudt, cputm ) AS eventtime,
usnam AS username,
bukrs AS companycode,
'' AS vendornumber,
'' AS amountincompanycodecurrency,
'' AS paymentduedate,
blart AS documenttype,
'' AS paymentblockreason,
'' AS purchasingdocument
FROM bkpf
INTO TABLE @DATA(lt_reversed)
WHERE stblg IS NOT NULL
AND cpudt IN @s_erdat
AND bukrs IN @s_bukrs.
LOOP AT lt_reversed INTO DATA(ls_reversed).
ls_event_log-invoicenumber = ls_reversed-invoicenumber.
ls_event_log-activityname = ls_reversed-activityname.
ls_event_log-eventtime = |{ ls_reversed-eventtime(8) } { ls_reversed-eventtime+8(2) }:{ ls_reversed-eventtime+10(2) }:{ ls_reversed-eventtime+12(2) }|.
ls_event_log-username = ls_reversed-username.
ls_event_log-companycode = ls_reversed-companycode.
APPEND ls_event_log TO lt_event_log.
ENDLOOP.
* --- Write internal table to CSV file
OPEN DATASET p_path FOR OUTPUT IN TEXT MODE ENCODING UTF-8.
IF sy-subrc <> 0.
MESSAGE 'Error opening file.' TYPE 'E'.
ENDIF.
DATA: lv_line TYPE string.
FIELD-SYMBOLS: <fs_any> TYPE any.
* --- Header row
lv_line = 'InvoiceNumber,ActivityName,EventTime,UserName,CompanyCode,VendorNumber,AmountInCompanyCodeCurrency,PaymentDueDate,DocumentType,PaymentBlockReason,PurchasingDocument'.
TRANSFER lv_line TO p_path.
LOOP AT lt_event_log INTO ls_event_log.
CLEAR lv_line.
DO.
ASSIGN COMPONENT sy-index OF STRUCTURE ls_event_log TO <fs_any>.
IF sy-subrc <> 0.
EXIT.
ENDIF.
IF sy-index = 1.
lv_line = <fs_any>.
ELSE.
CONCATENATE lv_line <fs_any> INTO lv_line SEPARATED BY ','.
ENDIF.
ENDDO.
TRANSFER lv_line TO p_path.
ENDLOOP.
CLOSE DATASET p_path.
WRITE: / 'Extraction complete. File saved to:', p_path. Gotowi do rozpoczęcia?
Zacznij optymalizować obsługę faktur już dziś. Ten szablon to pierwszy krok do usprawnienia operacji i zwiększenia efektywności.
Zoptymalizuj obsługę faktur P2P w SAP S/4HANA
Wskaż wąskie gardła i skróć cykl obsługi faktur o 30% lub więcej.
Karta kredytowa nie jest wymagana. Konfiguracja zajmuje kilka minut.