1

I've been fighting for days with this problem:insert file into database with Spring Boot, JPA Hibernate and Vue.js frontend. (Yes I know it's better to store the location to retrieve the file and not the file itself, but I have to store the file, so move on.) I tried different solutions but I didn't manage. First I passed the file path from fontend to backend as a normal field of my json data and used:

        String path= json.get("file_name").asText();
        File file = new File(path);
        byte[] fileInBytes = new byte[(int) file.length()];
        FileInputStream fileInputStream = new FileInputStream(file);
        fileInputStream.read(fileInBytes);
        fileInputStream.close();
        c.setFile(fileInBytes);

It worked only if I passed the explicit path, because from my HTML input type=file I always got C:/fakepath/filename and the backend didn't find the file obviously. Is there any way to pass the explicit path? I've searched for a while but I couldn't find a solution, so I changed my mind.

Now I'm passing the base64 encode of the file from the frontend in Vue with this code (thanks to How to convert file to base64 in JavaScript?):

getBase64(file, onLoadCallback) {
  return new Promise(function(resolve, reject) {
            var reader = new FileReader();
            reader.onload = function() { resolve(reader.result); };
            reader.onerror = function(error) {
            console.log('Error when converting file to base64: ', error);
            };
           reader.readAsDataURL(file);
    });
},

uploadFile: function(event) {
  this.input_file = document.getElementById("challenge_file").files[0];
  this.base64_file = this.getBase64(this.input_file);
  this.base64_file.then(function(result) {
      console.log(result);

     this.File=JSON.stringify({'file': this.base64_file});

     axios.post("/uploadfile", 
                this.File, 
                { headers: {
                      'Content-type': 'application/json',
                      }
                }).then(function(response){
                    location.reload(true);
                }).catch(function (error){
                    console.log(error);
                });

             });
}

this code works and I get a base64 string also in the backend, in which I try to convert it in bytes[] because my file is a @Lob private byte[] file;. This is my code in the backend controller:

     System.out.println(json.get("file"));
     //print "data:text/plain;base64,aVZCT1J..."
     int init= json.get("file").asText().lastIndexOf(",");
     String base64file=json.get("file").asText().substring(init+1);
     //I get only the part after 'base64,' *(see below) 
     System.out.println(base64file);
     byte[] decodedByte =  Base64.getDecoder().decode(base64file); 
     //I decode it into bytes[]
     c.setFile(decodedByte);    

*I get only the the part after 'base64,' otherwise if I use all the String I get this error: enter java.lang.IllegalArgumentException: Illegal base64 character 3a

This code has no errors, but the Blob in the database is empty, while in the first way I could open the file preview from Hibernate, but only if I wrote the correct real path, not retrieving it from the input. Any suggestion? What should I do?

SOLVED: Thanks to an answer to this question I changed my backend into:

     System.out.println(json.get("file"));
     String data= json.get("file").asText();
      String partSeparator = ",";
     if (data.contains(partSeparator)) {
        String encodedImg = data.split(partSeparator)[1];
        byte[] decodedImg = Base64.getDecoder().decode(encodedImg.getBytes(StandardCharsets.UTF_8));
        c.setFile(decodedImg); 
     }

and now I see the correct file in the db.

chln
  • 97
  • 1
  • 2
  • 10
  • 1
    As the exceptions says this is not Base64. Do you maybe have an issue with the encoding of the string? https://stackoverflow.com/questions/28584080/base64-java-lang-illegalargumentexception-illegal-character – Simon Martinelli Aug 13 '18 at 16:02
  • I'm such an idiot! I found the same question some days ago but I didn't try all the answer... one of them resolved my issue (the one by @Matthias Braun)! So thank you!! I have to pay more attention to all the answers. – chln Aug 13 '18 at 18:29
  • Great. Can you add the answer please – Simon Martinelli Aug 13 '18 at 18:40

0 Answers0