hastalavista8
Goto Top

Bestimmte Zeilen aus PDF Datei in CSV einfügen automatisch

Hallo zusammen, gibt es eine Möglichkeit bestimmte Zeilen aus PDF Rechnungen automatisch in deine CSV Datei einzufügen.

Es wird das Bestelldatum, Bestellnummer, Lieferdatum und Preis in einer CSV Zeile benötigt.

Gibt es solch ein Programm schon auf dem Markt, vielleicht ein PDF Tool wo ich individuell bestimmte Zeilen kopieren kann und anschließend in die CSV Datei einfügt ?

Wäre sehr dankbar, beste Grüße

Content-ID: 3361383966

Url: https://administrator.de/contentid/3361383966

Ausgedruckt am: 17.11.2024 um 19:11 Uhr

andreas65m
Lösung andreas65m 17.07.2022 um 11:53:36 Uhr
Goto Top
Hallo,
ist es eine Rechnung laut ZUGFeRD Spezifikation?
Dieser Typ Rechnungen enthält die Daten auch als XML
https://de.wikipedia.org/wiki/ZUGFeRD#ZUGFeRD-Konzept
Du solltest die XML-Datei per
https://www.xpdfreader.com/pdfdetach-man.html
extrahieren können um sie dann weiterverwenden zu können.

Wenn es nicht um eine ZUGFeRD-Datei, wird es wohl schwierig.

Grüße
Andreas
Crusher79
Lösung Crusher79 17.07.2022 aktualisiert um 12:10:08 Uhr
Goto Top
Hallo,

ja das geht! Mache es selber. mit pdf2text.

ACHTUNG: Je nach Aufbau kann man PDF-TXT zeilenbasiert oder RAW importieren. Entweder sowas wie:

Re.-Nr.: xxxxxx
ODER
Re.-Nr.:
xxxxx

Genau hier kann es Probleme bei RAW geben. Wenn z.B. Auftragsnummer oder Sachbearbeiter leer sind. Du must kurz schauen ob der Aufbau immer gleich ist.

Steht es in einer Zeile - und zwar immer - kann man es auch als Objekt mit PowerShell importieren.


pdftotext


Das war Quick and Dirty. Kann man schöner machen. War am Anfang nur ein Beleg. Gab ein paar Test. Natürlich nimmt man innerhalb normal Vars etc.

Aber ja - so funktioniert es mit Regular Expression. Wenn Sachbearbeiter fehlt etc. - also der Regex nicht greift kommt "MANUELL ZURORDNEN".

Hier wurde dann noch Hintergrund hinzugefügt. Entfällt bei dir. Unten mal ein altes Archiv Sytem mit einer Leitdatei.

Die Leitdatei für den Import entnimmt aus PDF einen String, der zwar angedruckt wird, aber mit weiß-auf-weiß unsichtbar ist.

Der Vorteil von versteckten Metadaten ist, dass man damit eigentlich immer einen 100% Treffer landet. Reguläre Ausdrücke sind ggf. etwas ungenau und müssen exakt stimmen und Ausreißer kenntlich machen.


# Definition der Parameter übergeben von PDFCretator Action
Param(
    [string]$PDFFullPath,
    [string]$ClientComputer,
    [string]$ClientUsername
)

Function Global:FindBelegNr($PDFToTextFile)
    {
		#PDF in durchsuchbaren Text umwandeln. simple2 und clip zum "normalisieren" 
        Start-Process -NoNewWindow -Wait $pdftotext -ArgumentList "-simple2", "-clip", "-f 1", "-l 1", $PDFToTextFile, $TempTextFile  

        $texttest = Get-Content -Path $TempTextFile -Raw

        #$patternBelegRe = "Rech.-Nr. " 
        #$patternBelegAb = "Auf.-Nr. " 
        [string] $DokBelegAbRe =""  
        [string] $DokBelegAn =""  
        [string] $DokBelegLs =""  
                
        #Angebot Nr in einer Zeile
        $regex_An = "(ANGEBOT )(Kunden-Nr\. )(Angebot-Nr\. )(Datum )(Seite)\r\n([\d]+)\s([\d]+)"                  
        #Auf ODER Rech übermehrere Zeilen
        $regex_AbRe = "(.*)\r\n(Ihr Ansprechpartner: )(Kunden-Nr\. )((Auf|Rech)\.-Nr\. )(Datum )(Seite)\r\n(.*)\s([\d]+)\s([\d]+)"  
        #Nur Lieferschein
        $regex_Ls = "(LIEFERSCHEIN)\r\n(Lieferschein-Nr\. )(Lieferanten-Nr\. )(Datum )(Seite)\r\n([\d]+)\s([\d]+)"  
        #Nur Bestellschein
        $regex_Bs = "(.*)(Lieferanten-Nr. )(Bestell-Nr. )(Datum )(Seite)\r\n([\d]+)\s([\d]+)"  
                
        $texttest | select-string -Pattern $regex_AbRe -AllMatches | % { $DokBelegAbRe = $_.Matches.Groups[1].Value + "_" + $_.Matches.Groups[10].Value }  
        $texttest | select-string -Pattern $regex_An -AllMatches | % { $DokBelegAn = $_.Matches.Groups[1].Value + "_" + $_.Matches.Groups[7].Value }  
        $texttest | select-string -Pattern $regex_Ls -AllMatches | % { $DokBelegLs = $_.Matches.Groups[1].Value + "_" + $_.Matches.Groups[6].Value }  
        $texttest | select-string -Pattern $regex_Bs -AllMatches | % { $DokBelegBs = $_.Matches.Groups[1].Value + "_" + $_.Matches.Groups[7].Value }  

        IF ($DokBelegAbRe.length -gt 0) { $Script:Belegnr = $DokBelegAbRe }
        IF ($DokBelegAn.length -gt 0) { $Script:Belegnr = $DokBelegAn }
        IF ($DokBelegLs.length -gt 0) { $Script:Belegnr = $DokBelegLs }
        IF ($DokBelegBs.length -gt 0) { $Script:Belegnr = $DokBelegBs }        
    }

$pdftk = "C:\Program Files (x86)\PDFtk Server\bin\pdftk.exe"  
$pdftotext = "C:\ps\pdftotext.exe"  
$backgroundfile = "C:\ps\FL_Briefbogenv4.pdf"  
[string] $PDFPath = (Split-Path -Path $PDFFullPath) + "\"  
$PDFFile = Split-Path -Path $PDFFullPath -Leaf -Resolve
$PDFCombinedFileName = "new_" + $PDFFile  
$PDFCombined = $PDFPath + $PDFCombinedFileName
$CharArray = $PDFCombinedFileName.Split("_")  
$TempTextFile = "C:\ps\" + $CharArray[4] + "_" + $CharArray[1] + ".txt"  

#pdftk zum Hinzufuegen des Hintergrund PDFs
Start-Process -NoNewWindow -Wait $pdftk -ArgumentList $PDFFullPath, 'background', $backgroundfile, 'output', $PDFCombined  

#Belegnummer und Art aus PDF ermitteln
FindBelegNr($PDFCombined)

#Leerzeichen entfernen und vorhandensein der Nummer pruefen
$Belegnr = $Belegnr -replace '\s',''  
IF ($Belegnr.Length -eq 0) { $Belegnr = "MANUELL_ZUORDNEN" }  

#PDF an Client PC uebergeben
$PDFClientPath = "Microsoft.PowerShell.Core\FileSystem::\\" + $ClientComputer + "\c$\Users\" +$ClientUsername + "\Desktop\" + $Belegnr + "_DruckID_" + ($CharArray[4] -replace '^0+(?=[^.])') + ".pdf"  
Copy-Item -Path $PDFCombined -Destination $PDFClientPath

Sleep 2

Remove-Item $PDFFullPath -Force
Remove-Item $PDFCombined -Force
Remove-Item $TempTextFile -Force


Zeilenbasiert für ein Archivsastem das mitte ls EOB Files importiert.

# Definition der Parameter übergeben von PDFCretator Action
Param(
    [string]$PDFFullPath,
    [string]$ClientComputer,
    [string]$ClientUsername
)

Function Global:FindBelegNr($PDFToTextFile)
    {
		#PDF in durchsuchbaren Text umwandeln. simple2 und clip zum "normalisieren" 
        Start-Process -NoNewWindow -Wait $pdftotext -ArgumentList "-simple2", "-clip", $PDFToTextFile, $TempTextFile  
		
        $PdfTxt = Get-Content -Path $TempTextFile  | Select-Object -Skip 3 
        $BelegTyp = $PdfTxt.Split(",")  
        $FieldVal = $PdfTxt+",`r`n^"  
        $MatchCode = $PdfTxt | Select-Object -Skip 1

        #$CountFF = $(Select-String -InputObject $texttest -Pattern "\f" -AllMatches).Matches.Count         
        #$txtFieldId = "1110" 
        #for ($num = 1 ; $num -le $CountFF ; $num++){ $textFieldId += $(","+$textFieldId); Write-Host "test"; }              
          
        [object[]] $eob = @("@IMPHDR,$($BelegTyp[5]),1001,1002,1003,1004,1005,1006,1007,1008,1009,1110,3000")  
        [object[]] $FileLocation = @("^,`r`n^$ArchivPathOutLocal$FinalPdfFile^")  
        $eob += $FieldVal
        $eob += $MatchCode | %{ $_.Replace("`f","") }   
        $eob += $FileLocation
        $eob | Set-Content -Path $PreFinalTextFile
     
    }
     
$ArchivPathOut = "archiv01\d$\Printportal\OUT\"  
$ArchivPathOutLocal = "D:\Printportal\OUT\"  

$pdftotext = "$PSScriptRoot\pdftotext.exe"  
[string] $PDFPath = (Split-Path -Path $PDFFullPath) + "\"  
$PDFFile = Split-Path -Path $PDFFullPath -Leaf -Resolve
$PDFCombinedFileName = "new_" + $PDFFile  
$PDFCombined = $PDFPath + $PDFCombinedFileName
$CharArray = $PDFCombinedFileName.Split("_")  
$TempTextFile = "$PSScriptRoot\tmp_" + $CharArray[4] + "_" + $CharArray[1] + ".txt"  
$PreFinalTextFile = "$PSScriptRoot\" + $CharArray[4] + "_" + $CharArray[1] + ".txt"  
$FinalTextFile = "BM_FLDIAF_" + $CharArray[4] + "_" + $CharArray[1] + ".EOU"  
$FinalPdfFile = $CharArray[4] + "_" + $CharArray[1] + ".PDF"  

#Belegnummer und Art aus PDF ermitteln
FindBelegNr($PDFFullPath)

#PDF an Archiv uebergeben
$PDFTextPath = "Microsoft.PowerShell.Core\FileSystem::\\" + $ArchivPathOut + $FinalTextFile  
Copy-Item -Path $PreFinalTextFile -Destination $PDFTextPath
$PDFArchivPath = "Microsoft.PowerShell.Core\FileSystem::\\" + $ArchivPathOut + $FinalPdfFile  
Copy-Item -Path $PDFFullPath -Destination $PDFArchivPath

Sleep 2

Remove-Item $PDFFullPath -Force
Remove-Item $PreFinalTextFile -Force
Remove-Item $TempTextFile -Force
Crusher79
Lösung Crusher79 17.07.2022 um 12:14:55 Uhr
Goto Top
PS: Es geht auch mit OCR.

Tesseract OCR

Nimmt Bitfarm auch. Damit kannst du auch Felder über die Bereiche legen, die gelesen werden sollen.

Auch Kommandozeilenl basiert.

Das Beispiel oben ist normal in < 1 Std. zu schaffen. Bzw. wenn du die Vorlage abwandelst noch schneller! Regurlary Exrpession kannst du mit Tools deiner Wahl erstellen und prüfen. Oder von Hand.

Wenn eine der Mehtoden greift - hast du Ruhe.

Wie gesagt: wenn oben Sachbearbeiter fehlt etc. also z.b. 3. Zahlenblock von links nicht der 3. sondern der 1. ist komtm sowas wie "MANUELL ZORDNEN".


Du kannst gerne auch mal mit pdftotext die Beispiele hier posten!

Wir brauchen nicht deine org. Rechnung! Es reichen die Header mit ggf. abweichenden Positionen.

Das ist reine Logik und schnell gemacht.
HastaLaVista8
HastaLaVista8 17.07.2022 aktualisiert um 16:59:06 Uhr
Goto Top
Es handelt sich konkret um viele Amazon Rechnungen, die wir für den Betrieb einkaufen.

Geht darum, dass es in die CSV Zeile eingefügt werden soll um die Buchhaltung teilweise zu automatisieren.

Wäre ewig dankbar, weil alles händisch zu machen wäre ein Todesurteil.

Die CSV Zeile müsste so aussehen:

11/07/2022,304-6796875-0668341,11/07/2022,EUR,"31,80",DE23YB4ZUAEUI,

Es ist verständlicher wenn man sich die Screenshots im Anhang.
Die rot markierten Bereiche sind die wichtigste, es müssen nicht die Wörter Bestelldatum Lieferdatum Bestellnummer übernommen werden, sondern nur die Nummern die aus Datum, Bestellnr, Lieferdatum, Preis und Rechnungsnummern bestehen.

Muss auch erwähnen in der Amazon Rechnung steht als Bestelldatum und Rechnungsdatum/Lieferdatum 08. Juli.
Brauche es in der CSV Datei als Nummern also 08/07/2022

Jetzt die ultimative Frage, ist das wirklich alles machbar ? face-smile


Danke liebe Leute
amazon rechnung
csv
Crusher79
Lösung Crusher79 17.07.2022 um 18:22:27 Uhr
Goto Top
Hi,

denke ja! Schau es mir später mal an.

Amazon aht ja für OPs etc. eigene CSV Ausgabe im Web. Aber auch hier dürfte es kein Problem sein.

Beispiel sollte reichenl Amazon Rechnungen hab ich genug. Gibt auch API Anbieter aber sehe da gerade nicht so das Problem.

Muss mir wie gesagt kurz die Format ansehen.
Crusher79
Lösung Crusher79 17.07.2022 aktualisiert um 19:05:17 Uhr
Goto Top
Nachtrag:

Habe es nochmal durgespielt. RAW einlesen scheint bei Amazon am beste zu gehen. Das Ergebnis einer Business Rechnung nach nicht mal 1 Sekunde.

Bestelldatum 12 Juli 2022
Bestellnummer 028-1223456-7890123
Auftraggeber Maik xxxxxxxx
Zahlbar innerhalb von 30 Tagen
Verkauft von Administrator.de GmbH
USt-IDNr. DE12345678
Rechnungsdatum
/Lieferdatum 13 Juli 2022
Rechnungsnummer INV-DE-123456789-2022-01234
Zahlungsbedingungen 30 Tage netto
Kundennummer ABCDEFGHIJK
Zahlbetrag 10,86 

Befehl:
pdftotext.exe -raw AmazonBusinessRechnungsnrINV-DE-123456789-2022-01234.pdf

Zeit: < 1 Sekunde
amaon
HastaLaVista8
HastaLaVista8 18.07.2022 um 09:46:24 Uhr
Goto Top
Leider haben wir kein Business Konto und möchten darauf verzichten.

Werde es heute es Abend mal versuchen mit pdftotext, vielen dank erstmal.

Eine Berichterstattung wird es nachher geben
Crusher79
Lösung Crusher79 18.07.2022 um 09:53:39 Uhr
Goto Top
Hallo,

also was auch klar sein sollte:

1. Bsp. oben ändert nur den Dateinamen.
2. Wurden die Texte für die Verschlagwortung in EOB Datei für Easyware Archivsystem gestellt

Statt der EOB einfach die CSV mit einer Zeile erstellen. Es gibt bei pdftotext einige Parameter. Bei Crystal Reports etc. liegen die Felder mitunter nicht untereinander oder neben einander.

-RAW brachte bei meiner Amazon das beste Ergenis. Das einzige was dann noch gemacht werden muss, ist die TXT Datei einzulesen und die Nummern/ Datum hinter den Begriffen zu extrahieren. Dann kann man sie einfach in 1. Zeile bringen und fertig.

Re. Nummer hat ja immer einen bestimmten Aufbau. Damit kann man arbeiten
HastaLaVista8
HastaLaVista8 18.07.2022 aktualisiert um 10:03:04 Uhr
Goto Top
Wie stelle ich das an, dass so eine Zeile dabei rauskommt?

11/07/2022,304-6796875-0668341,11/07/2022,EUR,"31,80",DE23YB4ZUAEUI,

Habe damit Null erfahrung face-smile Muss ich wohl rumbasteln

Also reicht nur pdftotext, was ist bitfarm?
Crusher79
Lösung Crusher79 18.07.2022 um 10:23:28 Uhr
Goto Top
Bitfarm ist OpenSource DMS.

Hatte es nur wegen der Scan Enging - bzw. OCR - erwähnt. DMS kommen auf das gleiche heraus. Müssen auch angepasst werden.


Poste einfach die Ergebnisse von Tool hier. Kannst ja anonymisieren. Dann sind wir nicht in Bereich allg. "Entwicklung", sondenr bei Powershell.

Text lesen, Werte extrahieren und in Datei - CSV - schreiben. Im Prinzip steht oben alles schon so drin. Auch wenn mein Code teils Sch. aussieht - funktioniert.

Mit PS kann dir hier jeder helfen. Mach mal aber paar TXT als Testlauf, und schau ob es dann so hin kommt.

Wenn die Grundlage IMMER gleich ist, sollte es kein Problem sein.

Wenn nciht ist auch nicht schlimm, solange wir dann Fehler in die CSV einbauen können. Damit dein Import halt scheitert. Doof wäre es wenn falsche Werte eingehen. Daher besser mit Fehler abbrechen. Das wäre es eig. schon ....