Il Suo template dei dati per Purchase to Pay - Ordine di acquisto
Il Suo template dei dati per Purchase to Pay - Ordine di acquisto
- Attributi consigliati da raccogliere
- Attività principali da monitorare
- Indicazioni per l’estrazione da SAP ECC
Attributi di Purchase to Pay - Ordine di acquisto
| Nome | Descrizione | ||
|---|---|---|---|
| Attività Activity | Nome dello specifico evento o passaggio aziendale che si è verificato nel ciclo di vita dell’ordine di acquisto. | ||
| Descrizione Questo attributo descrive un singolo passaggio del processo, ad esempio «Ordine di acquisto creato», «Ordine di acquisto approvato» o «Entrata merci registrata». La sequenza di queste attività costituisce il flusso del processo per ciascun ordine di acquisto. L’analisi della sequenza, della frequenza e della durata tra le attività è alla base del Process Mining. Aiuta a individuare colli di bottiglia, cicli di rilavorazione e scostamenti dal processo standard, consentendo di intervenire in modo mirato e favorire la standardizzazione. Perché è importante Le attività definiscono i passaggi del processo. Analizzarne la sequenza e i tempi permette di ricostruire il flusso effettivo, individuare i colli di bottiglia e rilevare gli scostamenti. Dove reperirli Ricavato da diverse tabelle SAP e dai log delle transazioni, ad esempio CDHDR/CDPOS per le modifiche, EKBE per entrate merci e fatture e EBAN per le richieste. Spesso è necessario ricorrere a una logica personalizzata o a un programma di estrazione per generarlo. Esempi Ordine di acquisto creatoOrdine di acquisto approvatoEntrata merci registrata | |||
| Ora dell’evento EventTime | Data e ora precise in cui si è verificata l’attività. | ||
| Descrizione Questa marca temporale indica il momento esatto in cui si è verificato un evento, ad esempio l’approvazione di un ordine di acquisto o la registrazione di un’entrata merci. Definisce l’ordine cronologico di tutte le attività all’interno di un caso. Le marche temporali sono fondamentali per il Process Mining, perché consentono tutte le analisi basate sul tempo: calcolare i tempi di ciclo tra le attività, individuare i ritardi, analizzare il flusso del processo e misurare le prestazioni rispetto agli accordi sul livello di servizio (SLA). Perché è importante Questa marca temporale è fondamentale per calcolare tutte le metriche basate sulla durata, come i tempi di ciclo e i colli di bottiglia, e per ordinare cronologicamente gli eventi. Dove reperirli Ricavato da diversi campi di data e ora nelle tabelle SAP, ad esempio EKKO-AEDAT (data di modifica), CDHDR-UDATE/UTIME (marca temporale del log delle modifiche) o EKBE-BUDAT (data di registrazione). Esempi 2023-04-15T10:05:31Z2023-04-16T14:22:00Z2023-05-01T09:00:15Z | |||
| Ordine di acquisto PurchaseOrder | Identificativo univoco del documento dell’ordine di acquisto (PO), utilizzato come caso principale per monitorare il processo di approvvigionamento. | ||
| Descrizione Il numero dell’ordine di acquisto è l’identificativo centrale che collega tutte le attività, dalla creazione alla ricezione finale della merce e al completamento. Ogni numero univoco corrisponde a una singola istanza del processo di approvvigionamento. Nel Process Mining, questo attributo è essenziale per ricostruire l’intero percorso di ogni acquisto. Consente di analizzare nel dettaglio i tempi di ciclo, le varianti del processo e la conformità di ciascun ordine, costituendo la base dell’intero modello di processo. Perché è importante È l’identificativo fondamentale che collega tutti gli eventi correlati e permette di analizzare l’intero ciclo di vita di ogni singolo ordine di acquisto. Dove reperirli Tabella: EKKO, campo: EBELN Esempi 450001762345000176244500017625 | |||
| Gruppo di materiali MaterialGroup | Classificazione che raggruppa materiali o servizi con caratteristiche simili. | ||
| Descrizione Il gruppo di materiali, o categoria di acquisto, serve a classificare il tipo di beni o servizi acquistati. Alcuni esempi sono «Hardware IT», «Forniture per ufficio» e «Servizi professionali». Questo attributo è fondamentale per analizzare la spesa e comprendere le modalità di approvvigionamento. Permette di filtrare il processo e analizzare come vengono gestite le diverse categorie, chi le approva e quali fornitori le forniscono. È una dimensione importante della Dashboard «Analisi del valore degli ordini di acquisto». Perché è importante Consente di segmentare il processo per categoria di prodotto o servizio, mettendo in luce differenze nel comportamento, nei tempi di ciclo o nei fornitori in base al tipo di spesa. Dove reperirli Tabella: EKPO, campo: MATKL Esempi 00101Hardware ITConsulenza | |||
| Importo dell’ordine OrderAmount | Valore monetario totale della singola posizione dell’ordine di acquisto. | ||
| Descrizione Questo attributo rappresenta il valore totale di una specifica posizione dell’ordine di acquisto, calcolato moltiplicando la quantità per il prezzo netto. Per ottenere il valore complessivo dell’ordine, occorre sommare gli importi delle singole posizioni. Analizzare il processo in base all’importo dell’ordine è fondamentale per individuare le transazioni di valore elevato, che possono richiedere controlli più rigorosi o percorsi di approvazione diversi. Questo attributo alimenta la Dashboard «Analisi del valore degli ordini di acquisto» e aiuta a dare priorità agli interventi di miglioramento sugli ordini di maggiore rilevanza finanziaria. Perché è importante Quantifica l’impatto finanziario di ogni acquisto e consente di dare priorità agli ordini di valore elevato o individuare opportunità di risparmio. Dove reperirli Tabella: EKPO, campo: NETWR (valore netto dell’ordine). Esempi 1500.00250.7512345.50 | |||
| Nome utente UserName | ID utente della persona che ha eseguito l’attività. | ||
| Descrizione Questo attributo registra il nome utente SAP della persona che ha creato, modificato o approvato un documento. Per i passaggi automatizzati, può indicare l’ID di un utente di sistema o batch. L’analisi per utente aiuta a individuare esigenze di formazione, persone con prestazioni elevate o potenziali problemi di conformità. È fondamentale per creare Dashboard sulla distribuzione del carico di lavoro, sul rispetto della matrice di approvazione e sulle prestazioni dei diversi team o delle singole persone. Perché è importante Associa le azioni degli utenti a persone specifiche, consentendo di analizzarne le prestazioni, il carico di lavoro e il rispetto delle procedure di conformità. Dove reperirli Tabella: EKKO, campo: ERNAM (creato da); tabella: CDHDR, campo: USERNAME (modificato da). Esempi JSMITHMBROWNBATCH_USER | |||
| Numero fornitore VendorNumber | Identificativo univoco del fornitore. | ||
| Descrizione È il codice che identifica in modo univoco il fornitore da cui si acquistano beni o servizi. È un dato anagrafico fondamentale nel processo di approvvigionamento. Questo attributo è essenziale per le analisi incentrate sui fornitori. Consente di valutare le prestazioni di consegna, confrontare i tempi di consegna tra fornitori diversi e analizzare le abitudini di spesa. È la dimensione principale della Dashboard «Prestazioni di consegna dei fornitori». Perché è importante Consente di analizzare le prestazioni dei fornitori e individuare quelli affidabili e quelli che causano ritardi o problemi di qualità. Dove reperirli Tabella: EKKO, campo: LIFNR Esempi 100345V-20598700112 | |||
| Società CompanyCode | Identificativo della persona giuridica o società che avvia l’acquisto. | ||
| Descrizione In SAP, la società rappresenta una persona giuridica indipendente. Tutte le transazioni vengono registrate a livello di società, che costituisce quindi un’unità organizzativa fondamentale. Analizzare il processo per società permette di confrontare l’efficienza degli acquisti e la conformità tra diverse unità aziendali o paesi. Aiuta a individuare le buone pratiche di una società che potrebbero essere adottate altrove e a identificare le unità che incontrano difficoltà nel processo. Perché è importante Rappresenta la persona giuridica e consente di confrontare le prestazioni del processo e verificare la conformità nelle diverse aree dell’organizzazione. Dove reperirli Tabella: EKKO, campo: BUKRS Esempi 10002100US01 | |||
| Tipo di documento DocumentType | Codice che classifica i diversi tipi di ordini di acquisto. | ||
| Descrizione In SAP, il tipo di documento è una configurazione che determina l’intervallo di numerazione, la selezione dei campi e il flusso complessivo del processo per un ordine di acquisto. Ad esempio, possono esistere tipi diversi per gli ordini standard, gli ordini di servizio o gli ordini di trasferimento delle scorte. Questo attributo è una dimensione di analisi importante, poiché tipi di documento diversi seguono spesso processi distinti per scelta. Filtrare per tipo di documento permette di confrontare in modo omogeneo i tempi di ciclo e i flussi di processo. Perché è importante Distingue i diversi tipi di processo di acquisto, ad esempio standard, servizi o resi, che spesso seguono percorsi e hanno aspettative di prestazione differenti. Dove reperirli Tabella: EKKO, campo: BSART Esempi Ordine standardOrdine quadroOrdine di trasferimento | |||
| Consegna puntuale IsOnTimeDelivery | Indicatore che segnala se i beni sono stati ricevuti entro la data di consegna richiesta. | ||
| Descrizione Questo attributo booleano è vero se la data e l’ora dell’attività «Entrata merci registrata» sono uguali o precedenti alla «Data di consegna richiesta». Fornisce un esito chiaro, positivo o negativo, sulla puntualità della consegna per ogni riga dell’ordine di acquisto. Questo attributo è alla base del KPI «Tasso di registrazione puntuale delle entrate merci». Semplifica l’analisi delle prestazioni dei fornitori e dell’efficienza interna del ricevimento, consentendo di aggregare e filtrare facilmente le consegne puntuali e quelle in ritardo. Perché è importante Fornisce una misura chiara dell’esito della puntualità delle consegne e supporta direttamente i KPI e le Dashboard sulle prestazioni dei fornitori. Dove reperirli È un attributo calcolato confrontando la data di registrazione dell’entrata merci (EKBE-BUDAT) con la data di consegna richiesta (EKPO-EINDT). Esempi truefalse | |||
| Data di consegna richiesta RequestedDeliveryDate | Data entro cui l’azienda ha richiesto al fornitore di consegnare i beni o i servizi. | ||
| Descrizione È la data di consegna prevista indicata nell’ordine di acquisto e costituisce la base di riferimento per misurare le prestazioni effettive di consegna. Questa data è essenziale per calcolare il KPI «Tasso di entrate merci puntuali». Confrontando la data effettiva di ricezione della merce con quella richiesta, le organizzazioni possono misurare quantitativamente l’affidabilità dei fornitori e l’efficienza interna nella ricezione, informazioni che alimentano direttamente la Dashboard «Prestazioni di consegna dei fornitori». Perché è importante È la data prevista per la consegna, essenziale per calcolare i KPI di puntualità e valutare l’affidabilità dei fornitori. Dove reperirli Tabella: EKPO, campo: EINDT Esempi 2023-06-102023-07-222023-08-01 | |||
| Gruppo acquisti PurchasingGroup | Acquirente o gruppo di acquirenti responsabile dell’attività di approvvigionamento. | ||
| Descrizione Il gruppo acquisti rappresenta la persona o il team di acquirenti responsabile di una determinata attività di acquisto. È il principale punto di contatto per i fornitori. Questo attributo consente un’analisi più dettagliata rispetto all’organizzazione acquisti. Aiuta a comprendere come è distribuito il carico di lavoro tra gli acquirenti e a individuare differenze nelle prestazioni a livello individuale, fornendo indicazioni utili per l’assegnazione delle risorse e le iniziative di formazione. Perché è importante Consente di vedere nel dettaglio chi è responsabile di un acquisto e di analizzare il carico di lavoro e le prestazioni a livello di buyer o di team. Dove reperirli Tabella: EKKO, campo: EKGRP Esempi 001002N01 | |||
| Modifica dopo l’approvazione IsPostApprovalChange | Indicatore che segnala se un ordine di acquisto è stato modificato dopo l’approvazione iniziale. | ||
| Descrizione Questo attributo booleano è vero se, per lo stesso ordine di acquisto, viene rilevata l’attività «Ordine di acquisto modificato» dopo l’attività «Ordine di acquisto approvato». Consente di isolare le modifiche problematiche apportate nelle fasi avanzate del processo. Questo campo calcolato alimenta direttamente il KPI «Tasso di modifica degli ordini di acquisto dopo l’approvazione» e la Dashboard «Rielaborazioni e modifiche degli ordini di acquisto». Aiuta a quantificare e mettere in evidenza le modifiche che causano ritardi e richiedono una nuova approvazione, segnalando possibili problemi nella definizione iniziale delle specifiche o dell’ambito. Perché è importante Misura direttamente le rielaborazioni successive all’approvazione, un KPI fondamentale per valutare la stabilità e l’efficienza del processo. Valori elevati indicano problemi nella definizione iniziale dei requisiti. Dove reperirli È un attributo calcolato in base alla sequenza delle attività nell’event log. Esempi truefalse | |||
| Motivo del rifiuto RejectionReason | Codice o testo che spiega perché una richiesta di acquisto o un ordine è stato rifiutato. | ||
| Descrizione Questo attributo registra il motivo specifico indicato quando un ordine di acquisto viene rifiutato durante il flusso di approvazione. È un’informazione fondamentale per comprendere le cause profonde delle rielaborazioni e dei ritardi. L’analisi dei motivi di rifiuto aiuta a individuare problemi ricorrenti, come prezzi errati, superamento del budget o selezione di fornitori non conformi. Queste informazioni consentono all’azienda di intervenire sulle cause profonde, migliorare la qualità degli ordini di acquisto iniziali e semplificare il processo di approvazione. Perché è importante Mostra direttamente perché le approvazioni non vanno a buon fine e consente di intervenire in modo mirato per ridurre le rielaborazioni e abbreviare i tempi del ciclo di approvazione. Dove reperirli Questa informazione può essere difficile da reperire. Potrebbe trovarsi in campi di testo lungo o dipendere dalla configurazione personalizzata del flusso di lavoro. Spesso è necessaria una conoscenza specifica dell’implementazione. Esempi Prezzo erratoBudget superatoRichiesta duplicata | |||
| Nome fornitore VendorName | Denominazione legale del fornitore. | ||
| Descrizione Denominazione descrittiva del fornitore, più intuitiva del numero fornitore. In genere, viene ricavata dai dati anagrafici dei fornitori. Il numero fornitore serve per i collegamenti e l’identificazione univoca, mentre il nome è fondamentale nelle Dashboard e nei report destinati agli utenti. Rende le analisi più intuitive e accessibili anche a chi non conosce i codici dei fornitori. Perché è importante Fornisce una denominazione leggibile del fornitore, rendendo le Dashboard e i report più comprensibili per gli utenti aziendali. Dove reperirli Tabella: LFA1, campo: NAME1. È necessario collegare EKKO-LIFNR a LFA1-LIFNR. Esempi Staples Inc.Global Tech SolutionsOffice Supply Co. | |||
| Organizzazione acquisti PurchasingOrganization | Unità organizzativa responsabile della negoziazione dei prezzi e dell’acquisto di materiali o servizi. | ||
| Descrizione In SAP, l’organizzazione acquisti è un’unità organizzativa fondamentale, responsabile delle attività di approvvigionamento. Può essere centralizzata per l’intera azienda oppure decentralizzata per stabilimento o area geografica. Analizzare le prestazioni del processo per organizzazione acquisti aiuta a individuare i team di approvvigionamento più efficienti. Consente di confrontare metriche come i tempi di ciclo, i tassi di rilavorazione e i costi tra diverse unità organizzative, mettendo in evidenza le buone pratiche e le aree che necessitano di supporto. Perché è importante Identifica il team responsabile degli acquisti e consente di confrontare le prestazioni e condurre analisi tra diverse unità organizzative. Dove reperirli Tabella: EKKO, campo: EKORG Esempi 1000US01DE01 | |||
| Richiesta di acquisto PurchaseRequisition | Identificativo della richiesta di acquisto che ha preceduto l’ordine. | ||
| Descrizione Questo attributo collega l’ordine di acquisto alla richiesta da cui ha avuto origine. Non tutti gli ordini sono preceduti da una richiesta. Il collegamento è fondamentale per analizzare la Dashboard «Dalla richiesta all’ordine» e il KPI «Tasso di conversione da richiesta a ordine». Consente di misurare l’efficienza del processo a monte, dalla richiesta iniziale alla creazione dell’ordine formale, e di individuare gli ordini non conformi creati senza una richiesta. Perché è importante Collega l’ordine alla richiesta di origine, consentendo di analizzare la conversione da richiesta a ordine e individuare gli ordini creati senza una richiesta precedente. Dove reperirli Tabella: EKPO, campo: BANFN Esempi 1001589010015891 | |||
| Sistema di origine SourceSystem | Sistema da cui sono stati estratti i dati. | ||
| Descrizione Questo attributo identifica l’origine dei dati, in genere un’istanza SAP ECC, ad esempio «ECC_PROD_100». Negli ambienti con più sistemi, consente di distinguere le diverse origini dei dati. Per la governance e la tracciabilità dei dati, è fondamentale conoscere il sistema di origine. Questo aiuta a garantire l’integrità dei dati e a risolvere i problemi di estrazione o qualità, soprattutto quando i dati provengono da sistemi o moduli ERP diversi. Perché è importante Identifica l’origine dei dati, un’informazione fondamentale per la governance, la convalida e la gestione delle analisi su più sistemi. Dove reperirli In genere, si tratta di un valore statico aggiunto durante l’estrazione per indicare il sistema di origine del set di dati. Esempi SAP_ECC_PRODECC_EU_100S4H_FIN | |||
| Stabilimento Plant | La sede fisica o lo stabilimento presso cui devono essere consegnati i beni. | ||
| Descrizione Lo stabilimento è un’unità organizzativa che rappresenta un impianto di produzione, un magazzino o un’altra sede in cui vengono ricevuti beni o servizi. L’analisi per stabilimento aiuta a comprendere le differenze geografiche nel processo di approvvigionamento. Può mettere in luce variazioni nei tempi di consegna dei fornitori in determinate sedi o individuare stabilimenti con processi di ricevimento inefficienti, facilitando l’analisi della puntualità nella registrazione delle entrate merci. Perché è importante Indica il luogo di consegna ed è utile per analizzare le differenze regionali nei processi e le prestazioni logistiche. Dove reperirli Tabella: EKPO, campo: WERKS Esempi 100011002000 | |||
| Ultimo aggiornamento dei dati LastDataUpdate | Marca temporale che indica quando i dati sono stati aggiornati l’ultima volta dal sistema di origine. | ||
| Descrizione Questo attributo registra la data e l’ora dell’estrazione o dell’aggiornamento più recente dei dati. Fornisce un’indicazione sull’aggiornamento dei dati analizzati. Mostrare questa informazione nelle Dashboard è fondamentale perché gli utenti possano capire se le informazioni si basano su dati quasi in tempo reale o su una fotografia storica. In questo modo si definiscono aspettative realistiche e si prendono decisioni sulla base di dati di cui si conosce l’età. Perché è importante Indica agli utenti quanto sono aggiornati i dati, aiutandoli a capire se l’analisi riflette lo stato più recente delle attività. Dove reperirli Questa marca temporale viene generata e aggiunta dal processo di estrazione o ETL al momento dell’esecuzione. Esempi 2023-10-27T02:00:00Z2023-10-28T02:00:00Z | |||
| Valuta Currency | Codice della valuta dell’importo dell’ordine di acquisto. | ||
| Descrizione Questo attributo specifica la valuta in cui è espresso il valore dell’ordine di acquisto, ad esempio USD, EUR o GBP. Fornisce il contesto necessario per interpretare gli importi. Per le organizzazioni internazionali, la valuta è essenziale per un’analisi finanziaria corretta. Consente di aggregare e confrontare adeguatamente i valori degli ordini; tutti i KPI monetari devono essere interpretati tenendo conto della valuta. Perché è importante Fornisce il contesto necessario per interpretare gli importi e garantire analisi finanziarie accurate, soprattutto nelle organizzazioni multinazionali. Dove reperirli Tabella: EKKO, campo: WAERS Esempi USDEURJPY | |||
Attività di Purchase to Pay - Ordine di acquisto
| Attività | Descrizione | ||
|---|---|---|---|
| Entrata merci registrata | Questa attività indica la ricezione fisica della merce dal fornitore in riferimento a uno specifico ordine di acquisto. La registrazione dell’entrata merci è un’azione esplicita, ad esempio tramite la transazione MIGO, che crea un documento materiale e aggiorna le scorte. | ||
| Perché è importante È un passaggio fondamentale per monitorare le prestazioni di consegna del fornitore e l’avvio del processo di verifica delle fatture. Serve a calcolare la percentuale di consegne puntuali e la tempestività della registrazione delle entrate merci. Dove reperirli L’evento viene registrato alla creazione di un documento materiale. La marca temporale corrisponde alla data di registrazione (MKPF-BUDAT) o alla data di creazione (MKPF-CPUDT) nella tabella di testata dei documenti materiali (MKPF), collegata all’ordine tramite la tabella delle posizioni (MSEG). Acquisizione Utilizzare la marca temporale di registrazione o creazione della tabella MKPF per i documenti materiali che fanno riferimento all’ordine di acquisto. Tipo di evento explicit | |||
| Ordine di acquisto approvato | Indica l’approvazione finale dell’ordine di acquisto, che ne autorizza l’invio al fornitore. Questo passaggio fondamentale viene in genere dedotto dalla modifica dello stato di rilascio dell’ordine a «rilasciato completamente» o «approvato». | ||
| Perché è importante Questa attività è fondamentale per calcolare il KPI relativo al tempo di ciclo dell’approvazione dell’ordine di acquisto e individuare i colli di bottiglia nel flusso di lavoro di approvazione. È un prerequisito per la maggior parte delle attività successive, come l’invio dell’ordine al fornitore. Dove reperirli L’evento viene dedotto monitorando i log delle modifiche (CDHDR/CDPOS) della tabella di testata degli ordini di acquisto (EKKO), per individuare quando viene applicato il codice di rilascio finale o quando l’indicatore dello stato di rilascio complessivo (EKKO-FRGKE) viene impostato su «rilasciato». Acquisizione Individuare la marca temporale in cui lo stato di rilascio complessivo dell’ordine di acquisto (EKKO-FRGKE) passa allo stato di approvazione finale. Tipo di evento inferred | |||
| Ordine di acquisto completato | Indica che una posizione dell’ordine di acquisto è considerata consegnata per intero. È un evento dedotto, in genere dall’impostazione automatica o manuale dell’indicatore «Consegna completata» sulla posizione dell’ordine. | ||
| Perché è importante Questa attività costituisce il punto di arrivo logico della fase di evasione dell’ordine. È essenziale per calcolare il tempo di ciclo complessivo dell’ordine di acquisto, dalla creazione al completamento. Dove reperirli L’evento viene dedotto dai documenti di modifica (CDHDR/CDPOS), che registrano quando l’indicatore «Consegna completata» (EKPO-ELIKZ) viene impostato su «X» per una posizione dell’ordine. Il completamento dell’ultima posizione può indicare che l’intero ordine è stato completato. Acquisizione Individuare nei documenti di modifica la marca temporale in cui viene impostato l’indicatore EKPO-ELIKZ. Tipo di evento inferred | |||
| Ordine di acquisto creato | Questa attività indica la creazione di un documento formale di ordine di acquisto, che costituisce un contratto vincolante con un fornitore. È un evento esplicito, registrato quando un utente crea e salva un ordine di acquisto, ad esempio tramite la transazione ME21N, con conseguente inserimento di voci nelle tabelle EKKO ed EKPO. | ||
| Perché è importante Segna l’inizio ufficiale del ciclo di vita dell’ordine di acquisto. È un riferimento importante per misurare sia il tempo di conversione da richiesta di acquisto a ordine di acquisto, sia il tempo complessivo di evasione dell’ordine. Dove reperirli Il dato viene ricavato dalla data di creazione (EKKO-AEDAT) nella tabella di testata degli ordini di acquisto (EKKO), per il numero d’ordine corrispondente (EKKO-EBELN). Acquisizione Utilizzare la marca temporale di creazione della tabella EKKO per ogni nuovo ordine di acquisto. Tipo di evento explicit | |||
| Ordine di acquisto inviato al fornitore | Questa attività segna il momento in cui l’ordine di acquisto approvato viene trasmesso ufficialmente al fornitore, ad esempio tramite EDI, e-mail o stampa. È un evento esplicito, registrato nelle tabelle di controllo dei messaggi quando un messaggio di output viene elaborato correttamente. | ||
| Perché è importante È un passaggio fondamentale, da cui inizia a decorrere il tempo di consegna del fornitore. Analizzare il tempo che intercorre tra questo evento e la ricezione della merce è essenziale per valutare le prestazioni del fornitore e la puntualità delle consegne. Dove reperirli L’evento viene registrato nella tabella dello stato dei messaggi (NAST). La marca temporale può essere ricavata da NAST-DATVR e NAST-UHRVR quando lo stato di elaborazione (NAST-VSTAT) è «1» (elaborato correttamente) per il tipo di messaggio di output dell’ordine pertinente. Acquisizione Utilizzare la marca temporale di elaborazione della tabella NAST per il messaggio di output dell’ordine di acquisto. Tipo di evento explicit | |||
| Richiesta di acquisto creata | Questa attività segna la creazione di una richiesta formale di beni o servizi. È un evento esplicito, registrato quando un utente salva un nuovo documento di richiesta di acquisto, ad esempio tramite la transazione ME51N, generando un record univoco nella tabella EBAN. | ||
| Perché è importante È il principale punto di avvio del processo di approvvigionamento. Analizzare il tempo che intercorre tra questo evento e la creazione dell’ordine di acquisto permette di misurare l’efficienza con cui la domanda interna viene trasformata in ordini operativi. Dove reperirli L’evento viene registrato quando si crea una voce nella tabella di testata delle richieste di acquisto (EBAN). La data di creazione (EBAN-BADAT) e l’ora corrispondente costituiscono la marca temporale dell’evento. Acquisizione Individuare le nuove voci nella tabella EBAN in base alla data di creazione. Tipo di evento explicit | |||
| Approvazione dell’ordine di acquisto richiesta | Indica che un ordine di acquisto appena creato o modificato è stato sottoposto ad approvazione secondo la strategia di rilascio configurata. L’evento viene dedotto quando si attiva la strategia di rilascio e l’ordine entra in uno stato di approvazione in sospeso. | ||
| Perché è importante Distinguere la creazione dell’ordine di acquisto dall’avvio del processo di approvazione consente di misurare con precisione il KPI relativo al tempo di ciclo dell’approvazione. In questo modo emerge l’eventuale ritardo prima dell’avvio del flusso di lavoro di approvazione. Dove reperirli L’evento viene dedotto dai documenti di modifica (CDHDR/CDPOS) dell’ordine di acquisto (oggetto EINKBELEG), che mostrano l’impostazione iniziale di uno stato di rilascio, oppure dalla prima assegnazione allo stato di rilascio complessivo (EKKO-FRGKE) di un valore che indica l’avvio del processo di approvazione. Acquisizione Individuare la prima voce nei documenti di modifica che attiva la strategia di rilascio dell’ordine di acquisto. Tipo di evento inferred | |||
| Conferma del servizio inserita | Per gli ordini di acquisto relativi a servizi, questa attività indica la conferma dell’avvenuta erogazione dei servizi. È un evento esplicito, registrato con la creazione di un foglio di registrazione dei servizi, ad esempio tramite la transazione ML81N. | ||
| Perché è importante Per i servizi, equivale all’entrata merci ed è essenziale per monitorare l’evasione degli ordini di servizio. Avvia il processo finanziario per il pagamento dei servizi. Dove reperirli Il dato viene ricavato dalla data di creazione (ESSR-ERDAT) nella tabella di testata dei fogli di registrazione dei servizi (ESSR). Il collegamento all’ordine di acquisto si trova nella tabella ESLL. Acquisizione Utilizzare la marca temporale di creazione della tabella ESSR per i fogli di registrazione dei servizi collegati all’ordine di acquisto. Tipo di evento explicit | |||
| Controllo qualità eseguito | Indica che la merce ricevuta è stata sottoposta a un controllo di qualità. In genere, l’attività viene dedotta quando a un lotto di controllo, creato al momento dell’entrata merci, viene assegnata una decisione d’uso nel modulo di gestione della qualità. | ||
| Perché è importante Nei settori in cui la qualità è fondamentale, questa attività permette di analizzare la durata e gli esiti del processo di controllo. I ritardi possono creare colli di bottiglia tra la ricezione della merce e la sua disponibilità per l’uso. Dove reperirli L’evento viene dedotto dal modulo di gestione della qualità. Al momento dell’entrata merci viene creato un lotto di controllo (tabella QALS); l’attività è contrassegnata dalla creazione di una decisione d’uso (tabella QAVE), che include una marca temporale. Acquisizione Individuare la marca temporale della decisione d’uso nella tabella QAVE per il lotto di controllo collegato al documento materiale. Tipo di evento inferred | |||
| Merce restituita | Indica la restituzione al fornitore di merce ricevuta in precedenza, spesso a causa di problemi di qualità o di una spedizione errata. È un evento esplicito, registrato con la creazione di un documento materiale che utilizza un tipo di movimento specifico per i resi. | ||
| Perché è importante Questa attività evidenzia problemi di qualità del fornitore o di accuratezza dell’ordine ed è un indicatore importante delle rilavorazioni del processo. È fondamentale per calcolare il KPI relativo al tasso di scostamento delle entrate merci. Dove reperirli L’evento viene registrato nelle tabelle dei documenti materiali (MKPF/MSEG) quando si utilizza un tipo di movimento di reso, ad esempio «122» per la restituzione della merce al fornitore. La data di registrazione (MKPF-BUDAT) costituisce la marca temporale. Acquisizione Individuare i documenti materiali con un tipo di movimento di reso, ad esempio 122, che fanno riferimento all’ordine di acquisto originale. Tipo di evento explicit | |||
| Ordine di acquisto eliminato | Indica l’annullamento o l’eliminazione logica di una posizione dell’ordine di acquisto, che impedisce ulteriori operazioni, come la registrazione delle entrate merci o la fatturazione. È un evento dedotto, registrato quando viene impostato l’indicatore di eliminazione sulla posizione dell’ordine. | ||
| Perché è importante È un’attività terminale che indica l’annullamento di un ordine. Analizzare perché e quando gli ordini vengono eliminati può far emergere problemi nella pianificazione della domanda o nella selezione dei fornitori. Dove reperirli L’evento viene dedotto dai documenti di modifica (CDHDR/CDPOS), che mostrano l’impostazione su «L» dell’indicatore di eliminazione (EKPO-LOEKZ) per una posizione dell’ordine di acquisto. Acquisizione Individuare nei documenti di modifica la marca temporale in cui viene impostato l’indicatore EKPO-LOEKZ. Tipo di evento inferred | |||
| Ordine di acquisto modificato | Indica qualsiasi modifica apportata a un ordine di acquisto dopo la creazione iniziale, ad esempio a quantità, prezzo o date di consegna. Queste modifiche vengono registrate esplicitamente nel sistema SAP dei documenti di modifica. | ||
| Perché è importante Le modifiche frequenti, soprattutto dopo l’approvazione, possono indicare inefficienze del processo, una pianificazione iniziale inadeguata o un ampliamento dell’ambito. Questa attività è essenziale per la Dashboard relativa a rilavorazioni e modifiche degli ordini di acquisto e per i KPI correlati. Dove reperirli L’evento viene registrato esplicitamente nelle tabelle di testata (CDHDR) e di posizione (CDPOS) dei documenti di modifica per l’oggetto ordine di acquisto (EINKBELEG). Ogni modifica genera una nuova voce con la relativa marca temporale. Acquisizione Estrarre gli eventi di modifica e le relative marche temporali dalle tabelle CDHDR e CDPOS collegate al numero dell’ordine di acquisto. Tipo di evento explicit | |||
| Ordine di acquisto rifiutato | Questa attività si verifica quando un approvatore rifiuta un ordine di acquisto durante il flusso di lavoro di approvazione. È un evento dedotto dai cambiamenti di stato nei dati della strategia di rilascio dell’ordine, che indicano l’avvenuto rifiuto. | ||
| Perché è importante Monitorare i rifiuti aiuta a individuare problemi nella qualità dei dati dell’ordine, violazioni delle politiche o criticità nella matrice di approvazione. Spesso comporta rilavorazioni e allunga il tempo di ciclo complessivo. Dove reperirli L’evento viene dedotto dai documenti di modifica (CDHDR/CDPOS) dello stato di rilascio dell’ordine di acquisto. In genere, il rifiuto viene registrato quando un codice di rilascio viene annullato o viene impostato uno specifico stato di rifiuto. Acquisizione Monitorare i log delle modifiche per rilevare l’annullamento di un codice di rilascio o un cambiamento di stato che indica un rifiuto. Tipo di evento inferred | |||
| Richiesta di acquisto approvata | Indica l’approvazione formale di una richiesta di acquisto, che ne autorizza la conversione in un ordine di acquisto. L’evento viene dedotto dalle modifiche ai campi dello stato di rilascio nei dati della richiesta, registrate dal flusso di lavoro della strategia di rilascio SAP. | ||
| Perché è importante Monitorare le approvazioni è fondamentale per individuare i colli di bottiglia nella fase precedente all’ordine e verificare il rispetto delle politiche di approvazione. I ritardi in questa fase incidono direttamente sul tempo di ciclo complessivo degli acquisti. Dove reperirli L’evento viene dedotto dai log delle modifiche della tabella delle richieste di acquisto (EBAN), monitorando in particolare i campi dello stato di rilascio, ad esempio EBAN-FRGZU, oppure analizzando i documenti di modifica in CDHDR/CDPOS per l’oggetto EBAN. Acquisizione Monitorare i documenti di modifica dei campi dello stato di rilascio in EBAN per individuare la marca temporale dell’approvazione finale. Tipo di evento inferred | |||
Guide all’estrazione
Passaggi
- Creare un programma ABAP: apra l’editor ABAP tramite il codice transazione SE38. Inserisca un nome per il nuovo programma, ad esempio Z_PM_PO_EXTRACT, e faccia clic su «Crea». Assegni un titolo, ad esempio «Estrazione dati ordini di acquisto per Process Mining», e imposti il tipo su «Programma eseguibile».
- Definire la schermata di selezione: nel programma, definisca i parametri della schermata di selezione, che consentono agli utenti di filtrare i dati da estrarre. Tra i parametri principali figurano l’intervallo di date di creazione dell’ordine di acquisto, il codice società (BUKRS) e il tipo di documento acquisti (BSART).
- Definire le strutture dati: dichiari una struttura di tabella interna conforme al formato finale dell’event log. Includa tutti gli attributi obbligatori e consigliati: PurchaseOrder, Activity, EventTime, UserName, VendorNumber, OrderAmount, MaterialGroup, CompanyCode e DocumentType.
- Implementare la logica di selezione dei dati: scriva la logica ABAP principale per selezionare i dati relativi a ciascuna delle 14 attività obbligatorie. Sarà necessario interrogare diverse tabelle SAP, tra cui EKKO, EKPO, EKBE, EBAN, CDHDR, CDPOS e NAST. Utilizzi una routine separata (PERFORM) per ogni attività, così da mantenere il codice organizzato.
- Selezionare i dati delle richieste di acquisto: interroghi la tabella EBAN per gli eventi «Richiesta di acquisto creata» e li colleghi agli ordini di acquisto tramite la tabella EKPO. Utilizzi le tabelle del registro delle modifiche (CDHDR, CDPOS) per individuare gli eventi «Richiesta di acquisto approvata», monitorando le modifiche ai campi dello stato di rilascio.
- Selezionare gli eventi principali degli ordini di acquisto: interroghi le tabelle EKKO ed EKPO per l’evento «Ordine di acquisto creato». Utilizzi le tabelle del registro delle modifiche (CDHDR, CDPOS) sull’oggetto EINKBELEG per estrarre gli eventi «Ordine di acquisto modificato», «Ordine di acquisto approvato», «Ordine di acquisto rifiutato», «Ordine di acquisto completato» e «Ordine di acquisto eliminato», in base alle modifiche di campi specifici come gli indicatori di rilascio e i flag di eliminazione.
- Selezionare gli eventi di comunicazione degli ordini di acquisto: interroghi la tabella NAST per trovare i record che indicano la trasmissione corretta dell’ordine di acquisto e registrare l’attività «Ordine di acquisto inviato al fornitore».
- Selezionare gli eventi relativi a beni e servizi: interroghi la tabella EKBE per individuare le registrazioni dei documenti materiale e identificare le attività «Entrata merci registrata» e «Merci restituite» in base alla categoria del tipo di movimento. Interroghi le tabelle ESSR ed ESLL per i fogli di registrazione dei servizi e registri l’attività «Conferma dei servizi inserita».
- Selezionare gli eventi di gestione della qualità: se è in uso il modulo di gestione della qualità, interroghi le tabelle QALS e QAVE per individuare quando è stata presa una decisione d’uso per un lotto di controllo collegato a un ordine di acquisto, registrando l’attività «Controllo qualità eseguito».
- Unire e formattare i dati: consolidi i dati di tutte le selezioni in un’unica tabella interna finale. Si assicuri che il campo EventTime abbia un formato coerente, ad esempio YYYY-MM-DDTHH:MI:SS.
- Implementare il download del file: aggiunga la funzione per scaricare la tabella interna finale come file. Si consiglia il formato TSV o CSV, ottenibile tramite il modulo funzione GUI_DOWNLOAD.
- Eseguire e salvare: esegua il programma tramite la transazione SE38 o SA38. Compili i criteri di selezione e avvii il report. Quando richiesto, salvi il file di output sul computer locale con estensione .csv, pronto per il caricamento.
Configurazione
- Intervallo di date: è fondamentale definire un intervallo di date specifico per l’estrazione, in genere basato sulla data di creazione dell’ordine di acquisto (EKKO-AEDAT). Un periodo di 3-6 mesi è spesso un buon punto di partenza per bilanciare il volume dei dati e le informazioni ricavabili sul processo.
- Codice società (BUKRS): filtri uno o più codici società per limitare l’estrazione alle entità giuridiche pertinenti. È un parametro importante per le prestazioni e la pertinenza dell’analisi.
- Tipo di documento acquisti (BSART): filtri tipi di documento specifici, ad esempio «NB» per un ordine di acquisto standard, per concentrarsi sui processi standard ed escludere, se necessario, i tipi di approvvigionamento speciali.
- Granularità dei dati: l’estrazione è progettata a livello di riga dell’ordine di acquisto. L’ID del caso corrisponde al numero dell’ordine di acquisto (EBELN). Tutti gli eventi, compresi quelli a livello di riga come le entrate merci, sono collegati a questo ID caso principale.
- Considerazioni sulle prestazioni: per i grandi insiemi di dati, pianifichi l’esecuzione del programma come processo in background (SM36) per evitare errori di timeout. Verifichi che siano presenti indici del database sui campi chiave utilizzati nelle clausole WHERE, in particolare nelle tabelle CDHDR e CDPOS.
- Prerequisiti: l’utente che esegue il report deve essere autorizzato ad accedere all’ambiente di sviluppo ABAP (SE38) e a eseguire il programma. Deve inoltre disporre dell’accesso in lettura a tutte le tabelle sottostanti, tra cui EKKO, EKPO, EKBE, CDHDR, CDPOS, EBAN, NAST, ESSR e le tabelle QM.
Query di esempio abap
REPORT Z_PM_PO_EXTRACT.
TABLES: ekko, ekpo, eban.
*&---------------------------------------------------------------------*
*& Data Structures for Event Log
*&---------------------------------------------------------------------*
TYPES: BEGIN OF ty_event_log,
purchaseorder TYPE ebeln,
activity TYPE string,
eventtime TYPE timestamp,
username TYPE ernam,
vendornumber TYPE lifnr,
orderamount TYPE netwr_ak,
materialgroup TYPE matkl,
companycode TYPE bukrs,
documenttype TYPE bsart,
END OF ty_event_log.
DATA: gt_event_log TYPE TABLE OF ty_event_log.
*&---------------------------------------------------------------------*
*& Selection Screen
*&---------------------------------------------------------------------*
SELECT-OPTIONS: s_aedat FOR ekko-aedat OBLIGATORY, " PO Creation Date
s_bukrs FOR ekko-bukrs, " Company Code
s_bsart FOR ekko-bsart, " PO Document Type
s_ebeln FOR ekko-ebeln. " PO Number
*&---------------------------------------------------------------------*
*& Main Processing Block
*&---------------------------------------------------------------------*
START-OF-SELECTION.
PERFORM get_po_headers.
IF gt_event_log IS NOT INITIAL.
PERFORM get_pr_created.
PERFORM get_pr_approved.
PERFORM get_po_created.
PERFORM get_po_release_events. " Approved, Rejected, Approval Requested
PERFORM get_po_sent_to_vendor.
PERFORM get_po_changed.
PERFORM get_goods_receipt_posted.
PERFORM get_services_confirmed.
PERFORM get_quality_inspection.
PERFORM get_goods_returned.
PERFORM get_po_completed.
PERFORM get_po_deleted.
PERFORM download_to_csv.
ELSE.
MESSAGE 'No Purchase Orders found for the given criteria.' TYPE 'I'.
ENDIF.
*&---------------------------------------------------------------------*
*& Form GET_PO_HEADERS (Base data)
*&---------------------------------------------------------------------*
FORM get_po_headers.
SELECT h~ebeln, h~lifnr, h~bukrs, h~bsart, p~netwr, p~matkl
FROM ekko AS h
INNER JOIN ekpo AS p ON h~ebeln = p~ebeln
INTO TABLE @DATA(lt_po_base)
WHERE h~aedat IN @s_aedat
AND h~bukrs IN @s_bukrs
AND h~bsart IN @s_bsart
AND h~ebeln IN @s_ebeln.
SORT lt_po_base BY ebeln.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PR_CREATED
*&---------------------------------------------------------------------*
FORM get_pr_created.
DATA: lt_pr_events TYPE TABLE OF ty_event_log.
SELECT p~ebeln AS purchaseorder,
'Purchase Requisition Created' AS activity,
b~erdat AS event_date,
'000000' AS event_time,
b~ernam AS username,
h~lifnr AS vendornumber,
p~netwr AS orderamount,
p~matkl AS materialgroup,
h~bukrs AS companycode,
h~bsart AS documenttype
FROM ekpo AS p
JOIN eban AS b ON p~banfn = b~banfn AND p~bnfpo = b~bnfpo
JOIN ekko AS h ON p~ebeln = h~ebeln
WHERE p~ebeln IN @s_ebeln
AND p~banfn IS NOT NULL AND p~banfn <> ''
AND h~aedat IN @s_aedat
AND h~bukrs IN @s_bukrs
AND h~bsart IN @s_bsart
INTO TABLE @DATA(lt_pr_created).
LOOP AT lt_pr_created ASSIGNING FIELD-SYMBOL(<fs_pr>).
DATA(ls_event) = CORRESPONDING ty_event_log(<fs_pr>).
CONCATENATE <fs_pr>-event_date <fs_pr>-event_time INTO DATA(lv_ts).
CONVERT DATE <fs_pr>-event_date TIME '000000' INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PR_APPROVED
*&---------------------------------------------------------------------*
FORM get_pr_approved.
DATA: lt_pr_list TYPE TABLE OF eban-banfn.
SELECT DISTINCT p~banfn FROM ekpo AS p
JOIN ekko AS h ON p~ebeln = h~ebeln
WHERE h~aedat IN @s_aedat
AND h~bukrs IN @s_bukrs
AND p~banfn IS NOT NULL AND p~banfn <> ''
INTO TABLE @lt_pr_list.
IF lt_pr_list IS INITIAL. RETURN. ENDIF.
SELECT h~objectid, h~username, h~udate, h~utime, p~fname, p~value_new
FROM cdhdr AS h
JOIN cdpos AS p ON h~objectid = p~objectid AND h~changenr = p~changenr
FOR ALL ENTRIES IN @lt_pr_list
WHERE h~objectclas = 'BANF'
AND h~objectid = @lt_pr_list-table_line
AND p~tabname = 'EBAN'
AND p~fname = 'FRGZU'
INTO TABLE @DATA(lt_cd_pr).
LOOP AT lt_cd_pr ASSIGNING FIELD-SYMBOL(<fs_cd>) WHERE <fs_cd>-value_new = 'X'.
SELECT SINGLE p~ebeln, p~netwr, p~matkl, h~lifnr, h~bukrs, h~bsart
FROM ekpo AS p
JOIN ekko AS h ON p~ebeln = h~ebeln
WHERE p~banfn = @<fs_cd>-objectid(10)
INTO @DATA(ls_po_info).
IF sy-subrc = 0.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = ls_po_info-ebeln
activity = 'Purchase Requisition Approved'
username = <fs_cd>-username
vendornumber = ls_po_info-lifnr
orderamount = ls_po_info-netwr
materialgroup = ls_po_info-matkl
companycode = ls_po_info-bukrs
documenttype = ls_po_info-bsart
).
CONVERT DATE <fs_cd>-udate TIME <fs_cd>-utime INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDIF.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_CREATED
*&---------------------------------------------------------------------*
FORM get_po_created.
LOOP AT lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>).
SELECT SINGLE aedat, ernam FROM ekko INTO @DATA(ls_ekko)
WHERE ebeln = @<fs_po>-ebeln.
IF sy-subrc = 0.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Purchase Order Created'
username = ls_ekko-ernam
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE ls_ekko-aedat TIME '000000' INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDIF.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_RELEASE_EVENTS
*&---------------------------------------------------------------------*
FORM get_po_release_events.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT h~objectid, h~username, h~udate, h~utime, p~value_new
FROM cdhdr AS h
JOIN cdpos AS p ON h~objectid = p~objectid AND h~changenr = p~changenr
WHERE h~objectclas = 'EINKBELEG'
AND h~objectid IN lt_ebeln
AND p~tabname = 'EKKO'
AND p~fname = 'FRGKE'
INTO TABLE @DATA(lt_cd_po).
LOOP AT lt_cd_po ASSIGNING FIELD-SYMBOL(<fs_cd>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_cd>-objectid.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
username = <fs_cd>-username
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_cd>-udate TIME <fs_cd>-utime INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
CASE <fs_cd>-value_new.
WHEN '2' OR 'R'. " Final Release
ls_event-activity = 'Purchase Order Approved'.
WHEN '1'. " Blocked
ls_event-activity = 'Purchase Order Rejected'.
WHEN OTHERS. " Any other change implies a pending state
ls_event-activity = 'Purchase Order Approval Requested'.
ENDCASE.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_SENT_TO_VENDOR
*&---------------------------------------------------------------------*
FORM get_po_sent_to_vendor.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT objky, erdat, eruhr, ernam
FROM nast
WHERE kapol = 'EF' AND objky IN lt_ebeln AND vstat = '1'
INTO TABLE @DATA(lt_nast).
LOOP AT lt_nast ASSIGNING FIELD-SYMBOL(<fs_nast>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_nast>-objky.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Purchase Order Sent to Vendor'
username = <fs_nast>-ernam
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_nast>-erdat TIME <fs_nast>-eruhr INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_CHANGED
*&---------------------------------------------------------------------*
FORM get_po_changed.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT DISTINCT objectid, username, udate, utime
FROM cdhdr
WHERE objectclas = 'EINKBELEG' AND objectid IN lt_ebeln AND tcode <> 'ME21N' AND tcode <> 'ME22'
INTO TABLE @DATA(lt_cdhdr_chg).
LOOP AT lt_cdhdr_chg ASSIGNING FIELD-SYMBOL(<fs_cd>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_cd>-objectid.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Purchase Order Changed'
username = <fs_cd>-username
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_cd>-udate TIME <fs_cd>-utime INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_GOODS_RECEIPT_POSTED
*&---------------------------------------------------------------------*
FORM get_goods_receipt_posted.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT k~ebeln, m~cpudt, m~cputm, m~usnam, k~bewtp
FROM ekbe AS k JOIN mkpf AS m ON k~belnr = m~mblnr AND k~gjahr = m~mjahr
WHERE k~ebeln IN lt_ebeln AND k~bewtp = 'E' AND k~shkzg = 'S'
INTO TABLE @DATA(lt_gr).
LOOP AT lt_gr ASSIGNING FIELD-SYMBOL(<fs_gr>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_gr>-ebeln.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Goods Receipt Posted'
username = <fs_gr>-usnam
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_gr>-cpudt TIME <fs_gr>-cputm INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_SERVICES_CONFIRMED
*&---------------------------------------------------------------------*
FORM get_services_confirmed.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT l~ebeln, h~erdat, h~eruhr, h~ernam
FROM essr AS h JOIN esll AS l ON h~lblni = l~lblni
WHERE l~ebeln IN lt_ebeln
INTO TABLE @DATA(lt_ses).
LOOP AT lt_ses ASSIGNING FIELD-SYMBOL(<fs_ses>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_ses>-ebeln.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Services Confirmation Entered'
username = <fs_ses>-ernam
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_ses>-erdat TIME <fs_ses>-eruhr INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_QUALITY_INSPECTION
*&---------------------------------------------------------------------*
FORM get_quality_inspection.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT q~ebeln, v~vdatum, v~vzeit, v~vname
FROM qals AS q JOIN qave AS v ON q~prueflos = v~prueflos
WHERE q~ebeln IN lt_ebeln
INTO TABLE @DATA(lt_qm).
LOOP AT lt_qm ASSIGNING FIELD-SYMBOL(<fs_qm>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_qm>-ebeln.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Quality Inspection Performed'
username = <fs_qm>-vname
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_qm>-vdatum TIME <fs_qm>-vzeit INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_GOODS_RETURNED
*&---------------------------------------------------------------------*
FORM get_goods_returned.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT k~ebeln, m~cpudt, m~cputm, m~usnam
FROM ekbe AS k JOIN mkpf AS m ON k~belnr = m~mblnr AND k~gjahr = m~mjahr
WHERE k~ebeln IN lt_ebeln AND k~bwart = '122'
INTO TABLE @DATA(lt_ret).
LOOP AT lt_ret ASSIGNING FIELD-SYMBOL(<fs_ret>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_ret>-ebeln.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Goods Returned'
username = <fs_ret>-usnam
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_ret>-cpudt TIME <fs_ret>-cputm INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_COMPLETED
*&---------------------------------------------------------------------*
FORM get_po_completed.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT h~objectid, h~username, h~udate, h~utime
FROM cdhdr AS h JOIN cdpos AS p ON h~changenr = p~changenr AND h~objectid = p~objectid
WHERE h~objectclas = 'EINKBELEG' AND h~objectid IN lt_ebeln AND p~tabname = 'EKPO' AND p~fname = 'ELIKZ' AND p~value_new = 'X'
INTO TABLE @DATA(lt_cd_comp).
LOOP AT lt_cd_comp ASSIGNING FIELD-SYMBOL(<fs_cd>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_cd>-objectid.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Purchase Order Completed'
username = <fs_cd>-username
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_cd>-udate TIME <fs_cd>-utime INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form GET_PO_DELETED
*&---------------------------------------------------------------------*
FORM get_po_deleted.
DATA: lt_ebeln TYPE RANGE OF ebeln, ls_ebeln LIKE LINE OF lt_ebeln.
LOOP AT lt_po_base INTO DATA(ls_po_base).
ls_ebeln-sign = 'I'. ls_ebeln-option = 'EQ'. ls_ebeln-low = ls_po_base-ebeln.
APPEND ls_ebeln TO lt_ebeln.
ENDLOOP.
IF lt_ebeln IS INITIAL. RETURN. ENDIF.
SELECT h~objectid, h~username, h~udate, h~utime
FROM cdhdr AS h JOIN cdpos AS p ON h~changenr = p~changenr AND h~objectid = p~objectid
WHERE h~objectclas = 'EINKBELEG' AND h~objectid IN lt_ebeln AND p~tabname = 'EKPO' AND p~fname = 'LOEKZ' AND p~value_new = 'L'
INTO TABLE @DATA(lt_cd_del).
LOOP AT lt_cd_del ASSIGNING FIELD-SYMBOL(<fs_cd>).
READ TABLE lt_po_base ASSIGNING FIELD-SYMBOL(<fs_po>) WITH KEY ebeln = <fs_cd>-objectid.
IF sy-subrc <> 0. CONTINUE. ENDIF.
DATA(ls_event) = VALUE ty_event_log(
purchaseorder = <fs_po>-ebeln
activity = 'Purchase Order Deleted'
username = <fs_cd>-username
vendornumber = <fs_po>-lifnr
orderamount = <fs_po>-netwr
materialgroup = <fs_po>-matkl
companycode = <fs_po>-bukrs
documenttype = <fs_po>-bsart
).
CONVERT DATE <fs_cd>-udate TIME <fs_cd>-utime INTO TIME STAMP ls_event-eventtime TIME ZONE sy-zonlo.
APPEND ls_event TO gt_event_log.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form DOWNLOAD_TO_CSV
*&---------------------------------------------------------------------*
FORM download_to_csv.
DATA: lv_filename TYPE string.
DATA: lt_fieldnames TYPE TABLE OF string.
APPEND 'PurchaseOrder' TO lt_fieldnames.
APPEND 'Activity' TO lt_fieldnames.
APPEND 'EventTime' TO lt_fieldnames.
APPEND 'UserName' TO lt_fieldnames.
APPEND 'VendorNumber' TO lt_fieldnames.
APPEND 'OrderAmount' TO lt_fieldnames.
APPEND 'MaterialGroup' TO lt_fieldnames.
APPEND 'CompanyCode' TO lt_fieldnames.
APPEND 'DocumentType' TO lt_fieldnames.
DATA(lv_header) = REDUCE string( INIT h = '' FOR f IN lt_fieldnames NEXT h = h && f && cl_abap_char_utilities=>horizontal_tab ).
REPLACE LAST OCCURRENCE OF cl_abap_char_utilities=>horizontal_tab IN lv_header WITH cl_abap_char_utilities=>cr_lf.
DATA(lv_file_content) = lv_header.
LOOP AT gt_event_log ASSIGNING FIELD-SYMBOL(<fs_log>).
DATA lv_line TYPE string.
DATA lv_eventtime_str TYPE string.
lv_eventtime_str = |{ <fs_log>-eventtime TIMESTAMP = ISO }|.
lv_line = <fs_log>-purchaseorder && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-activity && cl_abap_char_utilities=>horizontal_tab &&
lv_eventtime_str && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-username && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-vendornumber && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-orderamount && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-materialgroup && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-companycode && cl_abap_char_utilities=>horizontal_tab &&
<fs_log>-documenttype && cl_abap_char_utilities=>cr_lf.
CONCATENATE lv_file_content lv_line INTO lv_file_content.
ENDLOOP.
CALL METHOD cl_gui_frontend_services=>gui_download
EXPORTING
filename = 'C:\temp\po_event_log.csv'
filetype = 'ASC'
CHANGING
data_tab = lv_file_content. Passaggi
- Stabilire la connessione al database: ottenga credenziali di sola lettura e i dati di connessione (nome host, porta e nome del database) per il database sottostante di SAP ECC. Si assicuri di avere installato gli strumenti client necessari, come DBeaver, SQL Developer o SSMS.
- Individuare lo schema SAP: si colleghi al database e individui lo schema SAP principale in cui si trovano le tabelle. Spesso si chiama SAPSR3, SAPHANADB o ha un nome specifico del sistema simile. Se non è lo schema predefinito per il Suo utente, dovrà anteporlo a tutti i nomi delle tabelle nella query.
- Esaminare la query SQL: apra lo script SQL fornito nel client. Questa query completa è progettata per estrarre 14 attività distinte dal processo Purchase to Pay, unendo diverse tabelle SAP.
- Personalizzare i parametri della query: individui all’inizio dello script l’espressione di tabella comune (CTE) PO_BASE. Modifichi i valori segnaposto per definire l’ambito dell’estrazione:
- [START_DATE] e [END_DATE]: imposti l’intervallo di date per l’analisi, ad esempio «20230101» e «20230630». Si consiglia di filtrare in base al campo AEDAT (data di modifica).
- [COMPANY_CODE_1], [COMPANY_CODE_2]: specifichi i codici società SAP da includere.
- [DOC_TYPE_1], [DOC_TYPE_2]: specifichi i tipi di documento degli ordini di acquisto da includere.
- [Your SAP Schema]: sostituisca questo segnaposto con il nome effettivo dello schema SAP in tutto lo script.
- Eseguire la query: esegua lo script SQL personalizzato sul database SAP. Il tempo di esecuzione varia in base all’intervallo di date, al volume dei dati e alle prestazioni del database.
- Controllare i risultati: al termine della query, esegua un rapido controllo dell’output. Verifichi che il numero di righe sia ragionevole e che le colonne chiave, come PurchaseOrder, Activity ed EventTime, contengano i valori previsti.
- Esportare i dati in CSV: esporti l’intero insieme dei risultati dal client SQL in un file CSV. Utilizzi la codifica UTF-8 per evitare problemi con i caratteri.
- Preparare il caricamento: verifichi che le intestazioni delle colonne nel file CSV corrispondano esattamente ai nomi degli attributi richiesti: PurchaseOrder, Activity, EventTime, UserName, VendorNumber, OrderAmount, MaterialGroup, CompanyCode, DocumentType.
- Caricare i dati nello strumento di Process Mining: carichi il file CSV finale nell’applicazione di Process Mining per analizzare e visualizzare i dati.
Configurazione
- Prerequisiti: è necessario disporre di accesso diretto in sola lettura al database sottostante di SAP ECC. Gli utenti devono avere autorizzazioni sufficienti per interrogare tabelle come EKKO, EKPO, EKBE, EBAN, CDHDR, CDPOS e NAST.
- Filtro per intervallo di date: è fondamentale applicare un filtro per intervallo di date per limitare il volume dei dati. Un periodo di 3-6 mesi filtrato in base a EKKO.AEDAT (data di modifica dell’ordine di acquisto) è un punto di partenza comune. Intervalli più ampi possono comportare tempi di esecuzione delle query molto lunghi.
- Filtri sui dati chiave: per mantenere l’analisi mirata, applichi sempre un filtro su EKKO.BUKRS (codice società) e EKKO.BSART (tipo di documento). In questo modo l’ambito si limita alle entità giuridiche e ai processi aziendali pertinenti.
- Considerazioni sulle prestazioni: la query unisce diverse tabelle di grandi dimensioni, comprese quelle della cronologia delle modifiche (CDHDR, CDPOS), e può quindi richiedere molte risorse. Si consiglia vivamente di eseguire l’estrazione nelle ore di minore attività o su un database replicato non di produzione, per evitare ripercussioni sulle prestazioni del sistema.
- Registrazione delle modifiche ai documenti: l’accuratezza di attività come «Approvato», «Rifiutato», «Completato» e «Modificato» dipende dall’attivazione in SAP della registrazione delle modifiche per i campi pertinenti. Verifichi con l’amministratore SAP che la registrazione sia attiva tramite la transazione SCDO.
Query di esempio sql
WITH PO_BASE AS (
SELECT
H.EBELN, -- Purchase Order Number
I.EBELP, -- Purchase Order Item
H.LIFNR, -- Vendor Number
H.BUKRS, -- Company Code
H.BSART, -- Document Type
I.NETWR, -- Order Amount (Item Level)
I.MATKL, -- Material Group
I.BANFN, -- Purchase Requisition Number
I.BNFPO -- Purchase Requisition Item
FROM [Your SAP Schema].EKKO AS H
JOIN [Your SAP Schema].EKPO AS I ON H.EBELN = I.EBELN
WHERE H.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' -- Filter on PO Change Date, e.g., '20230101' and '20231231'
AND H.BUKRS IN ('[COMPANY_CODE_1]', '[COMPANY_CODE_2]') -- Specify Company Codes
AND H.BSART IN ('[DOC_TYPE_1]', '[DOC_TYPE_2]') -- Specify PO Document Types
)
-- 1. Purchase Requisition Created
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Requisition Created' AS "Activity",
TO_TIMESTAMP(CONCAT(pr.ERDAT, '000000'), 'YYYYMMDDHH24MISS') AS "EventTime", -- Time is not available in EBAN
pr.ERNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].EBAN pr ON po.BANFN = pr.BANFN AND po.BNFPO = pr.BNFPO
WHERE po.BANFN IS NOT NULL AND po.BANFN <> ''
UNION ALL
-- 2. Purchase Requisition Approved
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Requisition Approved' AS "Activity",
TO_TIMESTAMP(CONCAT(ch.UDATE, ' ', ch.UTIME), 'YYYYMMDD HH24MISS') AS "EventTime",
ch.USERNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].CDHDR ch ON ch.OBJECTCLASS = 'BANF' AND ch.OBJECTID = po.BANFN
JOIN [Your SAP Schema].CDPOS cp ON ch.OBJECTCLASS = cp.OBJECTCLASS AND ch.OBJECTID = cp.OBJECTID AND ch.CHANGENR = cp.CHANGENR
WHERE cp.TABNAME = 'EBAN' AND cp.FNAME = 'FRGZU' AND cp.VALUE_NEW = 'X' -- Release indicator set to 'released'
UNION ALL
-- 3. Purchase Order Created
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Order Created' AS "Activity",
TO_TIMESTAMP(CONCAT(ekko.ERDAT, ' ', ekko.ERZET), 'YYYYMMDD HH24MISS') AS "EventTime",
ekko.ERNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].EKKO ekko ON po.EBELN = ekko.EBELN
UNION ALL
-- 4. Purchase Order Approval Requested / 5. Approved / 6. Rejected (from Change Docs)
SELECT
po.EBELN AS "PurchaseOrder",
CASE
WHEN cp.VALUE_NEW > cp.VALUE_OLD THEN 'Purchase Order Approval Requested'
WHEN cp.VALUE_NEW = ekko.FRGKE AND ekko.FRGKE = 'R' THEN 'Purchase Order Approved'
ELSE 'Purchase Order Rejected' -- Simplified logic, may need adjustment
END AS "Activity",
TO_TIMESTAMP(CONCAT(ch.UDATE, ' ', ch.UTIME), 'YYYYMMDD HH24MISS') AS "EventTime",
ch.USERNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].EKKO ekko ON po.EBELN = ekko.EBELN
JOIN [Your SAP Schema].CDHDR ch ON ch.OBJECTCLASS = 'EINKBELEG' AND ch.OBJECTID = po.EBELN
JOIN [Your SAP Schema].CDPOS cp ON ch.OBJECTCLASS = cp.OBJECTCLASS AND ch.OBJECTID = cp.OBJECTID AND ch.CHANGENR = cp.CHANGENR
WHERE cp.TABNAME = 'EKKO' AND cp.FNAME = 'FRGZU' -- Release status
UNION ALL
-- 7. Purchase Order Sent to Vendor
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Order Sent to Vendor' AS "Activity",
TO_TIMESTAMP(CONCAT(na.ERDAT, ' ', na.ERUHR), 'YYYYMMDD HH24MISS') AS "EventTime",
na.USNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].NAST na ON na.OBJKY = po.EBELN AND na.KSCHL = '[Your PO Output Type]' -- e.g., 'NEU'
WHERE na.VSTAT = '1' -- Successfully processed
UNION ALL
-- 8. Purchase Order Changed
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Order Changed' AS "Activity",
TO_TIMESTAMP(CONCAT(ch.UDATE, ' ', ch.UTIME), 'YYYYMMDD HH24MISS') AS "EventTime",
ch.USERNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].CDHDR ch ON ch.OBJECTCLASS = 'EINKBELEG' AND ch.OBJECTID = po.EBELN
WHERE ch.TCODE IN ('ME22', 'ME22N') -- Filter for change transactions
UNION ALL
-- 9. Goods Receipt Posted
SELECT
ekbe.EBELN AS "PurchaseOrder",
'Goods Receipt Posted' AS "Activity",
TO_TIMESTAMP(CONCAT(mkpf.CPUDT, ' ', mkpf.CPUTM), 'YYYYMMDD HH24MISS') AS "EventTime",
mkpf.USNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM [Your SAP Schema].EKBE AS ekbe
JOIN [Your SAP Schema].MKPF AS mkpf ON ekbe.BELNR = mkpf.MBLNR AND ekbe.GJAHR = mkpf.MJAHR
JOIN PO_BASE AS po ON ekbe.EBELN = po.EBELN AND ekbe.EBELP = po.EBELP
WHERE ekbe.BEWTP = 'E' -- Goods Receipt
AND ekbe.SHKZG = 'S' -- Debit/Credit Indicator: Goods Receipt
UNION ALL
-- 10. Services Confirmation Entered
SELECT
po.EBELN AS "PurchaseOrder",
'Services Confirmation Entered' AS "Activity",
TO_TIMESTAMP(CONCAT(essr.ERDAT, ' ', essr.ERZET), 'YYYYMMDD HH24MISS') AS "EventTime",
essr.ERNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].EKBE ekbe ON po.EBELN = ekbe.EBELN AND po.EBELP = ekbe.EBELP
JOIN [Your SAP Schema].ESSR essr ON ekbe.LBLNI = essr.LBLNI
WHERE ekbe.BEWTP = 'L' -- Service Entry Sheet
UNION ALL
-- 11. Quality Inspection Performed
SELECT
po.EBELN AS "PurchaseOrder",
'Quality Inspection Performed' AS "Activity",
TO_TIMESTAMP(CONCAT(qave.VDATUM, ' ', qave.VZEIT), 'YYYYMMDD HH24MISS') AS "EventTime",
qave.VNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].EKBE ekbe ON po.EBELN = ekbe.EBELN AND po.EBELP = ekbe.EBELP
JOIN [Your SAP Schema].QALS qals ON qals.MBLNR = ekbe.BELNR AND qals.MJAHR = ekbe.GJAHR
JOIN [Your SAP Schema].QAVE qave ON qals.PRUEFLOS = qave.PRUEFLOS
WHERE ekbe.BEWTP = 'E' -- Linked to a Goods Receipt
UNION ALL
-- 12. Goods Returned
SELECT
ekbe.EBELN AS "PurchaseOrder",
'Goods Returned' AS "Activity",
TO_TIMESTAMP(CONCAT(mkpf.CPUDT, ' ', mkpf.CPUTM), 'YYYYMMDD HH24MISS') AS "EventTime",
mkpf.USNAM AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM [Your SAP Schema].EKBE AS ekbe
JOIN [Your SAP Schema].MKPF AS mkpf ON ekbe.BELNR = mkpf.MBLNR AND ekbe.GJAHR = mkpf.MJAHR
JOIN PO_BASE AS po ON ekbe.EBELN = po.EBELN AND ekbe.EBELP = po.EBELP
WHERE ekbe.BEWTP = 'E' -- Goods Movement
AND ekbe.SHKZG = 'H' -- Debit/Credit Indicator: Return
AND ekbe.BWART = '122' -- Movement type for return to vendor
UNION ALL
-- 13. Purchase Order Completed
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Order Completed' AS "Activity",
TO_TIMESTAMP(CONCAT(ch.UDATE, ' ', ch.UTIME), 'YYYYMMDD HH24MISS') AS "EventTime",
ch.USERNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].CDHDR ch ON ch.OBJECTCLASS = 'EINKBELEG' AND ch.OBJECTID LIKE CONCAT(po.EBELN, po.EBELP, '%')
JOIN [Your SAP Schema].CDPOS cp ON ch.OBJECTCLASS = cp.OBJECTCLASS AND ch.OBJECTID = cp.OBJECTID AND ch.CHANGENR = cp.CHANGENR
WHERE cp.TABNAME = 'EKPO' AND cp.FNAME = 'ELIKZ' AND cp.VALUE_NEW = 'X' -- Delivery completed indicator
UNION ALL
-- 14. Purchase Order Deleted
SELECT
po.EBELN AS "PurchaseOrder",
'Purchase Order Deleted' AS "Activity",
TO_TIMESTAMP(CONCAT(ch.UDATE, ' ', ch.UTIME), 'YYYYMMDD HH24MISS') AS "EventTime",
ch.USERNAME AS "UserName",
po.LIFNR AS "VendorNumber",
po.NETWR AS "OrderAmount",
po.MATKL AS "MaterialGroup",
po.BUKRS AS "CompanyCode",
po.BSART AS "DocumentType"
FROM PO_BASE po
JOIN [Your SAP Schema].CDHDR ch ON ch.OBJECTCLASS = 'EINKBELEG' AND ch.OBJECTID LIKE CONCAT(po.EBELN, po.EBELP, '%')
JOIN [Your SAP Schema].CDPOS cp ON ch.OBJECTCLASS = cp.OBJECTCLASS AND ch.OBJECTID = cp.OBJECTID AND ch.CHANGENR = cp.CHANGENR
WHERE cp.TABNAME = 'EKPO' AND cp.FNAME = 'LOEKZ' AND cp.VALUE_NEW = 'L'; -- Deletion indicator Passaggi
- Prerequisiti e connessione: si assicuri che lo strumento ETL di terze parti disponga del connettore certificato SAP installato e con licenza. Nella console di amministrazione dello strumento ETL, configuri una nuova connessione al sistema SAP ECC. Le serviranno l’host del server applicativo, il numero di sistema, l’ID client e un utente SAP dedicato con le autorizzazioni RFC e di lettura delle tabelle appropriate.
- Individuare le tabelle di origine: nel processo ETL o nel flusso di dati, definisca le tabelle SAP necessarie come origini dati. Le tabelle principali sono EKKO (testata ordine di acquisto), EKPO (riga ordine di acquisto), EBAN (richiesta di acquisto), CDHDR (testata documento di modifica), CDPOS (riga documento di modifica), MSEG (segmento documento materiale), MKPF (testata documento materiale), NAST (stato messaggio), ESSR (testata foglio di registrazione servizi) e QALS (lotto di controllo).
- Estrarre «Ordine di acquisto creato»: crei un flusso di dati con origine nella tabella EKKO. Filtri i record in base all’intervallo di date desiderato, ad esempio utilizzando AEDAT, e all’ambito organizzativo, ad esempio BUKRS per il codice società e BSART per il tipo di documento. Mappi EKKO.EBELN su PurchaseOrder, «Ordine di acquisto creato» su Activity e combini AEDAT ed ERZET per ottenere EventTime. Mappi anche gli altri attributi richiesti.
- Estrarre «Entrata merci registrata»: crei un flusso di dati separato con origine in MSEG e unione con MKPF tramite MBLNR e MJAHR. Applichi un filtro sui tipi di movimento pertinenti, ad esempio «101». Mappi MSEG.EBELN su PurchaseOrder, «Entrata merci registrata» su Activity e utilizzi MKPF.CPUDT e MKPF.CPUTM per EventTime.
- Estrarre gli eventi basati sulle modifiche (approvazioni, modifiche, eliminazioni): crei un flusso di dati con origine in CDHDR e CDPOS, unite tramite CHANGENR. Da questa singola origine è possibile ricavare più attività.
- Filtri OBJECTCLAS = 'EINKBELEG' e TABNAME = 'EKPO'.
- Per «Ordine di acquisto approvato», filtri le modifiche al campo dello stato di rilascio, ad esempio FNAME = 'FRGZU', in cui il nuovo valore (VALUE_NEW) indica l’approvazione finale.
- Per «Ordine di acquisto eliminato», filtri le modifiche all’indicatore di eliminazione (FNAME = 'LOEKZ') in cui il nuovo valore è 'L'.
- Per «Ordine di acquisto modificato», filtri le modifiche agli altri campi pertinenti, escludendo quelli di stato specifici utilizzati per le altre attività.
- Per tutti questi eventi, utilizzi CDHDR.UDATE e CDHDR.UTIME per EventTime.
- Estrarre gli eventi delle richieste di acquisto: crei un flusso di dati da EBAN per «Richiesta di acquisto creata». Per collegare l’evento al caso dell’ordine di acquisto, unisca EBAN a EKPO tramite il numero della richiesta (BANFN) e la riga (BNFPO). Per «Richiesta di acquisto approvata», utilizzi CDHDR/CDPOS con OBJECTCLAS = 'BANF'. È necessario mappare con attenzione i dati affinché l’evento sia associato all’ordine di acquisto corrispondente.
- Estrarre «Ordine di acquisto inviato al fornitore»: crei un flusso di dati con origine nella tabella NAST. Applichi un filtro su OBJECTKEY, che contiene il numero dell’ordine di acquisto, sul tipo di output pertinente (KSCHL) e sullo stato di elaborazione completata (VSTAT = '1'). Utilizzi ERDAT e UHR per EventTime.
- Unire i flussi di attività: utilizzi una trasformazione «Union» o «Merge» nello strumento ETL per unire i risultati dei singoli flussi di dati creati nei passaggi precedenti. Verifichi che i nomi delle colonne e i tipi di dati siano coerenti in tutti i flussi (PurchaseOrder, Activity, EventTime e così via).
- Convertire i tipi e i formati dei dati: verifichi che la colonna EventTime sia convertita in un formato data e ora coerente, ad esempio YYYY-MM-DD HH:MM:SS. Converta OrderAmount in un formato decimale standard.
- Definire la destinazione: configuri una destinazione, o «sink», per il flusso di dati combinato. In genere si tratta di un file semplice, ad esempio CSV o Parquet. Configuri il delimitatore, i qualificatori di testo e le opzioni per le intestazioni.
- Eseguire e convalidare: esegua l’intero processo ETL. Verifichi che il file di output contenga tutte le 14 attività, che il numero di righe sia ragionevole e che gli attributi chiave siano compilati correttamente.
- Pianificare ed esportare: dopo la convalida, pianifichi l’esecuzione periodica del processo ETL, ad esempio ogni notte, per mantenere aggiornati i dati. Il file generato è pronto per essere caricato nello strumento di Process Mining.
Configurazione
- Prerequisiti: uno strumento ETL commerciale (ad es. Informatica PowerCenter, Talend, SAP Data Services) con il relativo connettore certificato SAP per ECC. Un utente di dialogo o di sistema SAP con autorizzazioni S_RFC e S_TABU_DIS per le tabelle necessarie.
- Connessione SAP: il connettore deve essere configurato con il server applicativo SAP, il numero di sistema, il client, l’utente e la password. Si consiglia di utilizzare Secure Network Communications (SNC).
- Filtro per intervallo di date: è fondamentale applicare un filtro per intervallo di date, così da limitare il volume dei dati. Una prassi comune consiste nel filtrare EKKO.AEDAT (data di creazione dell’ordine di acquisto) per gli ultimi 3-12 mesi. Il filtro va applicato all’origine per evitare di estrarre da SAP una quantità eccessiva di dati.
- Filtri per ambito organizzativo: applichi sempre un filtro per EKKO.BUKRS (codice società) e valuti se filtrare anche per EKPO.WERKS (stabilimento) o EKKO.EKORG (organizzazione acquisti), così da circoscrivere l’analisi a una specifica unità aziendale.
- Filtro per tipo di documento: utilizzi EKKO.BSART per includere solo i tipi di ordine di acquisto pertinenti ed escludere i trasferimenti di stock o altri documenti interni che non rientrano nel processo P2P standard.
- Ottimizzazione delle prestazioni: l’estrazione dalle tabelle dei documenti di modifica (CDHDR, CDPOS) può essere lenta. Verifichi che siano applicati filtri su OBJECTCLAS, OBJECTID e UDATE. Regoli l’impostazione «Packet Size» nel connettore SAP per ottimizzare la velocità di trasferimento dei dati. Per i sistemi di grandi dimensioni, valuti un caricamento iniziale dei dati storici seguito da caricamenti delta pianificati.
Query di esempio sql
/*
This is a logical representation of the transformations performed within the ETL tool.
The tool's graphical interface will be used to configure these separate data flows, which are then combined with a UNION transformation.
Placeholders like [Your ETL Tool Functions] and [Filter Values] must be configured in the tool.
*/
-- 1. Purchase Requisition Created
SELECT
ekpo.EBELN AS PurchaseOrder,
'Purchase Requisition Created' AS Activity,
[Your ETL Tool Functions].DateTime(eban.ERDAT, eban.ERZET) AS EventTime,
eban.ERNAM AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM EBAN AS eban
INNER JOIN EKPO AS ekpo ON eban.BANFN = ekpo.BANFN AND eban.BNFPO = ekpo.BNFPO
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 2. Purchase Requisition Approved (inferred from change documents)
SELECT
ekpo.EBELN AS PurchaseOrder,
'Purchase Requisition Approved' AS Activity,
[Your ETL Tool Functions].DateTime(cdhdr.UDATE, cdhdr.UTIME) AS EventTime,
cdhdr.USERNAME AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM CDHDR AS cdhdr
INNER JOIN CDPOS AS cdpos ON cdhdr.CHANGENR = cdpos.CHANGENR
INNER JOIN EBAN AS eban ON cdhdr.OBJECTID = eban.BANFN
INNER JOIN EKPO AS ekpo ON eban.BANFN = ekpo.BANFN AND eban.BNFPO = ekpo.BNFPO
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE cdhdr.OBJECTCLAS = 'BANF' AND cdpos.TABNAME = 'EBAN' AND cdpos.FNAME = 'FRGZU' AND cdpos.VALUE_NEW = '[Final Release Indicator for PR]'
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 3. Purchase Order Created
SELECT
EBELN AS PurchaseOrder,
'Purchase Order Created' AS Activity,
[Your ETL Tool Functions].DateTime(AEDAT, ERZET) AS EventTime,
ERNAM AS UserName,
LIFNR AS VendorNumber,
NULL AS OrderAmount, -- Amount is at item level
NULL AS MaterialGroup, -- Attribute is at item level
BUKRS AS CompanyCode,
BSART AS DocumentType
FROM EKKO
WHERE AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 4. Purchase Order Approval Requested / 5. Approved / 6. Rejected (inferred from change documents)
SELECT
ekpo.EBELN AS PurchaseOrder,
CASE
WHEN cdpos.VALUE_NEW = '[Final Release Code]' THEN 'Purchase Order Approved'
WHEN cdpos.VALUE_NEW = '[Rejection Release Code]' THEN 'Purchase Order Rejected'
ELSE 'Purchase Order Approval Requested'
END AS Activity,
[Your ETL Tool Functions].DateTime(cdhdr.UDATE, cdhdr.UTIME) AS EventTime,
cdhdr.USERNAME AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM CDHDR AS cdhdr
INNER JOIN CDPOS AS cdpos ON cdhdr.CHANGENR = cdpos.CHANGENR
INNER JOIN EKKO AS ekko ON SUBSTRING(cdhdr.OBJECTID, 1, 10) = ekko.EBELN
INNER JOIN EKPO AS ekpo ON ekko.EBELN = ekpo.EBELN
WHERE cdhdr.OBJECTCLAS = 'EINKBELEG' AND cdpos.TABNAME = 'EKKO' AND cdpos.FNAME = 'FRGKE'
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 7. Purchase Order Sent to Vendor
SELECT
ekko.EBELN AS PurchaseOrder,
'Purchase Order Sent to Vendor' AS Activity,
[Your ETL Tool Functions].DateTime(nast.ERDAT, nast.UHR) AS EventTime,
nast.USNAM AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM NAST AS nast
INNER JOIN EKKO AS ekko ON nast.OBJKY = ekko.EBELN
INNER JOIN EKPO AS ekpo ON ekko.EBELN = ekpo.EBELN
WHERE nast.KAPPL = 'EF' AND nast.VSTAT = '1' AND nast.KSCHL IN ([Your PO Output Types])
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 8. Purchase Order Changed (inferred from change documents, simplified example)
SELECT DISTINCT
ekko.EBELN AS PurchaseOrder,
'Purchase Order Changed' AS Activity,
[Your ETL Tool Functions].DateTime(cdhdr.UDATE, cdhdr.UTIME) AS EventTime,
cdhdr.USERNAME AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM CDHDR AS cdhdr
INNER JOIN CDPOS AS cdpos ON cdhdr.CHANGENR = cdpos.CHANGENR
INNER JOIN EKKO AS ekko ON SUBSTRING(cdhdr.OBJECTID, 1, 10) = ekko.EBELN
INNER JOIN EKPO AS ekpo ON ekko.EBELN = ekpo.EBELN
WHERE cdhdr.OBJECTCLAS = 'EINKBELEG' AND cdpos.FNAME NOT IN ('FRGKE', 'FRGZU', 'LOEKZ', 'ELIKZ')
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 9. Goods Receipt Posted
SELECT
mseg.EBELN AS PurchaseOrder,
'Goods Receipt Posted' AS Activity,
[Your ETL Tool Functions].DateTime(mkpf.CPUDT, mkpf.CPUTM) AS EventTime,
mkpf.USNAM AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM MSEG AS mseg
INNER JOIN MKPF AS mkpf ON mseg.MBLNR = mkpf.MBLNR AND mseg.MJAHR = mkpf.MJAHR
INNER JOIN EKPO AS ekpo ON mseg.EBELN = ekpo.EBELN AND mseg.EBELP = ekpo.EBELP
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE mseg.BWART = '101' AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 10. Services Confirmation Entered
SELECT
essr.EBELN AS PurchaseOrder,
'Services Confirmation Entered' AS Activity,
[Your ETL Tool Functions].DateTime(essr.ERDAT, essr.ERZET) AS EventTime,
essr.ERNAM AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM ESSR AS essr
INNER JOIN EKKO AS ekko ON essr.EBELN = ekko.EBELN
INNER JOIN EKPO AS ekpo ON essr.EBELN = ekpo.EBELN AND essr.EBELP = ekpo.EBELP
WHERE ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 11. Quality Inspection Performed
SELECT
qals.EBELN AS PurchaseOrder,
'Quality Inspection Performed' AS Activity,
[Your ETL Tool Functions].DateTime(qals.PASTRTERM, '000000') AS EventTime, -- Time is often not available
qals.PRUEFER AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM QALS AS qals
INNER JOIN EKKO AS ekko ON qals.EBELN = ekko.EBELN
INNER JOIN EKPO AS ekpo ON qals.EBELN = ekpo.EBELN AND qals.EBELP = ekpo.EBELP
WHERE qals.VCODE <> '' -- A usage decision code exists
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 12. Goods Returned
SELECT
mseg.EBELN AS PurchaseOrder,
'Goods Returned' AS Activity,
[Your ETL Tool Functions].DateTime(mkpf.CPUDT, mkpf.CPUTM) AS EventTime,
mkpf.USNAM AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM MSEG AS mseg
INNER JOIN MKPF AS mkpf ON mseg.MBLNR = mkpf.MBLNR AND mseg.MJAHR = mkpf.MJAHR
INNER JOIN EKPO AS ekpo ON mseg.EBELN = ekpo.EBELN AND mseg.EBELP = ekpo.EBELP
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE mseg.BWART = '122' AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 13. Purchase Order Completed (inferred from change documents)
SELECT
ekpo.EBELN AS PurchaseOrder,
'Purchase Order Completed' AS Activity,
[Your ETL Tool Functions].DateTime(cdhdr.UDATE, cdhdr.UTIME) AS EventTime,
cdhdr.USERNAME AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM CDHDR AS cdhdr
INNER JOIN CDPOS AS cdpos ON cdhdr.CHANGENR = cdpos.CHANGENR
INNER JOIN EKPO AS ekpo ON SUBSTRING(cdhdr.OBJECTID, 1, 10) = ekpo.EBELN AND SUBSTRING(cdhdr.OBJECTID, 11, 5) = ekpo.EBELP
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE cdhdr.OBJECTCLAS = 'EINKBELEG' AND cdpos.TABNAME = 'EKPO' AND cdpos.FNAME = 'ELIKZ' AND cdpos.VALUE_NEW = 'X'
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]);
UNION ALL
-- 14. Purchase Order Deleted (inferred from change documents)
SELECT
ekpo.EBELN AS PurchaseOrder,
'Purchase Order Deleted' AS Activity,
[Your ETL Tool Functions].DateTime(cdhdr.UDATE, cdhdr.UTIME) AS EventTime,
cdhdr.USERNAME AS UserName,
ekko.LIFNR AS VendorNumber,
ekpo.NETWR AS OrderAmount,
ekpo.MATKL AS MaterialGroup,
ekko.BUKRS AS CompanyCode,
ekko.BSART AS DocumentType
FROM CDHDR AS cdhdr
INNER JOIN CDPOS AS cdpos ON cdhdr.CHANGENR = cdpos.CHANGENR
INNER JOIN EKPO AS ekpo ON SUBSTRING(cdhdr.OBJECTID, 1, 10) = ekpo.EBELN AND SUBSTRING(cdhdr.OBJECTID, 11, 5) = ekpo.EBELP
INNER JOIN EKKO AS ekko ON ekpo.EBELN = ekko.EBELN
WHERE cdhdr.OBJECTCLAS = 'EINKBELEG' AND cdpos.TABNAME = 'EKPO' AND cdpos.FNAME = 'LOEKZ' AND cdpos.VALUE_NEW = 'L'
AND ekko.AEDAT BETWEEN '[START_DATE]' AND '[END_DATE]' AND ekko.BUKRS IN ([YOUR_COMPANY_CODES]); È pronto a iniziare?
Con questo template ha a disposizione una traccia per ottimizzare in SAP ECC il processo Purchase to Pay - Ordine di acquisto. Inizi a utilizzare i Suoi dati per individuare informazioni utili e migliorare l’efficienza.
Ottimizzi gli ordini di acquisto P2P: inizi oggi la prova gratuita
Elimini i colli di bottiglia e riduca il tempo di ciclo del 30% o più.
Non è necessaria una carta di credito. Inizi in pochi minuti.