6

I am using the jspdf library along with Angular 5 to generate a PDF on the client side. I am adding a png image to the pdf.

I have generated my .png file using dataurl.net. When I add it to the pdf and use doc.save(), it downloads locally and it looks great and works perfectly. However, I am trying to upload it directly to s3, using doc.output() instead, and when it gets there it looks like this: https://i.stack.imgur.com/yHP6B.jpg

My code to PUT in to s3 looks like this:

const headers = new HttpHeaders().set('Content-Type', 'application/pdf')
this.http.put(url, file, {headers})

with file = doc.output()

Anyone have any ideas of what may cause this?

Westwick
  • 2,367
  • 3
  • 28
  • 51
  • I've actually noticed that saving the result of doc.output() locally has the same problem, so I suspect it is a problem with the jspdf library or the way I I am calling doc.output(), and nothing to do with angular/s3 or the upload process – Westwick Feb 01 '18 at 17:41
  • looks like there is some difference in the character encoding or something of the stream data, you can see the diff here: https://quickdiff.net/?unique_id=9084579D-3251-D1F4-F253-FF170459FA69 – Westwick Feb 05 '18 at 15:49
  • jsfiddle with the problem: https://jsfiddle.net/96qcc4bd/ – Westwick Feb 05 '18 at 15:50
  • Seems like the data is same, but since it has binary stream in between. Converting it to string creates a problem here. Your best bet is to use the base64 data here and then send it to [aws](https://stackoverflow.com/questions/7511321/uploading-base64-encoded-image-to-amazon-s3-via-node-js) – Tarun Lalwani Feb 05 '18 at 17:34
  • I've tried sending the base64 version as well, but amazon doesn't seem to do anything on their end with that so it stays base64 encoded and results in 'corrupt pdf file' – Westwick Feb 05 '18 at 18:59
  • How did you send the base64 data? Can you open the file in text and decode the base64 and see if there are no issues? – Tarun Lalwani Feb 05 '18 at 19:02
  • I am `PUT`ting it as outlined in the original question, have tried passing it different ways either as the raw data or the b64 encoded data. It has the same problem when I b64 decode the data, as you mentioned I do think that is a problem with converting it to a string – Westwick Feb 05 '18 at 19:20
  • I meant to ask did you use `doc.output('datauristring')`? The cut the initial string to get the actual base64 data – Tarun Lalwani Feb 05 '18 at 19:26
  • yea I've tried that as well, as well as using it in combination with `new Buffer()`, `.toString('ascii')`, `.toString('binary')`, etc. none of which are working :( – Westwick Feb 05 '18 at 19:37

3 Answers3

6

I had to pass the ArrayBuffer to s3 to get it to work.

So the only code change was using doc.output('arraybuffer')

Westwick
  • 2,367
  • 3
  • 28
  • 51
1

You need to pass the ArrayBuffer to s3 to get it to work.

Only need to change doc.output('arraybuffer')

Peter Horton
  • 148
  • 9
0

I ran into an issue when I tried to pass an ArrayBuffer to s3. Instead I was able to convert the jspdf ArrayBuffer to a Buffer and send that as content to s3 like so:

const arrayBuffer = doc.output('arraybuffer');
doc.close();

// convert to Buffer
const pdfBuffer = Buffer.from(new Uint8Array(arrayBuffer));
Kyle B
  • 1
  • 1