CSV mit Text und Binärdaten auslesen

Bitte aktiviere JavaScript!
Hallo zusammen,

Ich hab Folgendes Problem. Ich hab eine CSV Datei bekommen die ich auslesen und weiterverarbeiten muss. Soweit kein Problem. Das Problem ist das eine Spalte der CSV binärcodierte PDF Dateien enthält. in etwa so: "column1";"[binäre PDF Daten]";"pdf_datei_name";"colum3";"column4";"column5"; usw.

Mein bisheriger Ansatz war die Datei komplett als byte[] einzulesen, dann byte für byte durchzugehen und zu prüfen ob ich einen Zeilenumbruch finde, damit ich eine Zeile hab die ich dann Weiter in die Einzelnen Columns aufsplitten kann. Um zu Verhindern das ein Zeilenumbruch innerhalb der PDF-Daten als Zeilentrenner erkannt wird, prüfe ich ob das PDF Start-Tag bzw End-Tag verarbeitet hab. Solange ich in den PDF Daten bin Ignorier ich alle Zeichenübrüche. Die einzelne Zeile Verarbeite ich dann auf die gleiche Art, nur das ich hier nach einem Semikolon als Trennzeichen suche.
Leider sind die PDF-Dateien die bei mir am Ende Rauskommen nicht Lesbar und ich finde den Fehler nicht.

Mein Parser
Java:
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import my_package.FileReader

public class CSVParser {

    private static final int LINE_BREAK = 10;
    private static final int SEMICOLON = 59;

    public List<CSVRow> parseFile(File csvFile) throws IOException {
        byte[] fileContent = new FileReader().readFile(csvFile);
        int rowStartIndex = 0;
        boolean isInPDFData = false;
        List<CSVRow> rows = new ArrayList<>();
        for(int i = 0; i < fileContent.length; i++) {
            if (fileContent[i] == LINE_BREAK && isInPDFData == false) {
                rows.add(parseRow(Arrays.copyOfRange(fileContent,rowStartIndex, i+1)));
                rowStartIndex = i;
            }
            else if (isPDFStart(fileContent, i)) {
                isInPDFData = true;
            }
            else if (isPDFEnd(fileContent, i) && isInPDFData) {
                isInPDFData = false;
            }
            if(rows.size() == 6) {
                break;
            }
        }
        return rows;
    }

    private CSVRow parseRow(byte[] data) {
        int columnStartIndex = 0;
        boolean isInPDFData = false;
        List<byte[]> columnData = new ArrayList<>();
        for(int i = 0; i < data.length; i++) {
            if (data[i] == SEMICOLON && isInPDFData == false) {
                columnData.add(Arrays.copyOfRange(data,columnStartIndex, i+1));
                columnStartIndex = i;
            }
            else if (isPDFStart(data, i)) {
                isInPDFData = true;
            }
            else if (isPDFEnd(data, i) && isInPDFData) {
                isInPDFData = false;
            }
        }
        byte[] fileData = Arrays.copyOfRange(columnData.get(1),2, columnData.get(1).length -2);
        String fileName = new String(columnData.get(2));
        return new CSVRow(fileName, fileData);
    }


    private boolean isPDFStart(byte[] fileContent, int i) {
        if(i - 5 < 0) {
            return false;
        }
        byte[]  b = Arrays.copyOfRange(fileContent,i-5, i);
        return new String(b).equals("%PDF-");
    }

    private boolean isPDFEnd(byte[] fileContent, int i) {
        if(i -7 < 0) {
            return false;
        }
        byte[]  b = Arrays.copyOfRange(fileContent,i-7, i);
        return new String(b).equals("%%EOF\\\n");
    }

}
Filewriter
Java:
import java.io.FileOutputStream;
import java.io.IOException;

public class FileWriter {

    public void writeFile(String fileName, byte[] data) throws IOException {
        FileOutputStream outputStream = new FileOutputStream(fileName);
        outputStream.write(data);
        outputStream.close();

    }
}
Meine Main
Java:
import java.io.File;
import java.io.IOException;
import java.util.List;

public class Main {

    public static void main(String args[]) {
        File csvFile = new File("daten.csv");
        CSVParser parser = new CSVParser();
        try {
            List<CSVRow> rows = parser.parseFile(csvFile);
            rows.forEach(row -> {
                try {
                    new FileWriter().writeFile(row.getFilename(), row.getFiledata());
                } catch (IOException e) {
                    e.printStackTrace();
                }
            });
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
Da ich das Projekt nur für einen Einmaligen Datenimport benötige war ich mit der Lesbarkeit ein wenig schluderig *schande über mein Haupt*

Danke schonmal im vorraus für eure Hilfe.
 
A

Anzeige




Vielleicht hilft dir unser Kurs hier weiter —> (hier klicken)
Also ich durchschaue das jetzt noch nicht. Eine CSV Datei kann keine binären Daten einfach so führen. Denn selbstverständlich kann eine binäre Datei auch Newlines und Kommas/Semikolons enthalten! Daher ist eine solche Auswertung schlicht nicht möglich.

Daher wäre meine Vermutung, dass die Binären Daten durchaus irgendwie codiert wurden.

Da würde ich an Deiner Stelle noch einmal nachhaken.
 
Genau auf das Problem bin ich auch gestoßen. Deshalb prüfe ich auch ob ich die Sequenz "%PDF-" treffe die Markiert den begin einer PDF Datei. Sobald ich diese Sequenz gefunden haben ignorier ich alle New Lines/Semikolons/Kommas/ etc. Solange bis ich auf die Sequenz "%%EOF" Treff welche das Ende einer PDF Datei markiert.
 
Das Problem ist das eine Spalte der CSV binärcodierte PDF Dateien enthält.
Wer macht denn sowas?!? Da muss man sich ja schon was brechen, um die Datei richtig zu erzeugen (in Java als OutputStream, dann die Strings einzeln in Bytes konvertieren...)

Leider sind die PDF-Dateien die bei mir am Ende Rauskommen nicht Lesbar und ich finde den Fehler nicht.
Hast Du schon einmal die Bytes des PDFs ohne Parser (zu Fuß) herausgelesen und abgespeichert? Funktioniert die PDF dann?
 
Wer macht denn sowas?!? Da muss man sich ja schon was brechen, um die Datei richtig zu erzeugen
Als ich das gesehen hab war mein erster Gedanke auch "Was stimmt denn nicht mit euch" :eek:

Wie meinst du das mit PDF zu Fuß auslesen? CSV als byte[] einlesen und druchlaufen -> wenn das Start-Tag kommt in einer Datei schreiben -> Wenn das End-Tag kommt aufhören in eine Datei zu schreiben.

Oder meinst du was anderes?
 
Ich habs jetzt mal mit einem Hex-Editor versucht. Danke für für den Tipp, auf den Simplen Test bin ich echt nicht gekommen *facepalm*. Die Dateien lassen sich aber auch leider mit der Methode nicht öffnen. Da die Dateien offensichtlich beschädigt sind werd ich jetzt nochmal nachhaken ob ich die Dateien nicht auch anders bekommen kann.
Danke für die Hilfe :)
 
Es könnte natürlich sein (bzw. davon ist auszugehen), dass die Binärdaten kodiert (z. B. UTF-8) geschrieben wurden... Würg.
 
Passende Stellenanzeigen aus deiner Region:

Neue Themen

Oben