Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

PDF.js CORS issue

Tags:

javascript

pdf

I'm having an issue with PDF.js and CORS configuration.

From domain A I'm loading PDF.js into an iframe with a file as parameter (full path to the server, which will return a pdf document). PDF.js will create a request to the server at domain B with origin: domain A. The server at domain B returns the pdf document with header Access-Control-Allow-Origin: domain A, so far so good.

In my network tab I see the request to the server, which is returning a 200 status OK, but PDF.js is throwing an error Unexpected server response (0) while retrieving PDF <url>.

The question is, what's going on here, CORS seems to be ok, but I can't really get any more info from PDF.js what the real reason is the PDF is failing to load. Is there anyone who encountered the same?

like image 972
jcbvm Avatar asked Sep 07 '16 15:09

jcbvm


2 Answers

PDF.js community is not helpful, and years later still no definitive answer to get the viewer.html working, with cors. To bypass all the JS code preventing you from cross browser issues, you can do these steps:

This solution is to use their default viewer.html, which is already nicely done, with css and all features), and NOT HAVE TO build your entire viewer itself.

  1. Ensure when you use pdf.js, your request sends header - ORIGIN
  2. Ensure whatever server you are using, you can append headers for CORS,

IE: Access-Control-Allow-Origin *

As you know, to use the viewer, you should use: https://yourserver/dir/viewer.html?file=PDF_URL

the URL of pdf should be urlencoded so when you pass the link, use the code:

var urlEncoded = encodeURI(url);

Edit viewer.js

  1. Search for the function which loads your PDF file/URL (line ~1325): "var loadingTask = (0, _pdfjsLib.getDocument)" or "getDocument"

  2. Above that line, get the url for the pdf from the get params, when you called viewer.html?file=url (which may have get params, if you use CDN servers):

/*
fetch the filename and params from the [viewer.html?file=some.place/on.the/internet/somefile.pdf?Expiry=2343243&somekey=3342343&other], which is the part [some.place/on.the/internet/somefile.pdf?Expiry=2343243&somekey=3342343&other]
Note: Use regex if you please.... Here is just for simplicity sake
*/
let _realURL =  window.location.href;

// split away the html and get the file=xxxx
let getParamsIndex = _realURL.indexOf("?");
let fileParamKeyValue = _realURL.substring(getParamsIndex+1);

// get the pdf file plus all it's required get params (if exists)
let getEqualsIndex = fileParamKeyValue.indexOf("=");
let pdfFile = fileParamKeyValue.substring(getEqualsIndex+1);


//original line to search
loadingTask = (0, _pdfjsLib.getDocument)(parameters);
  1. Now you have the pdf file, you change the existing code as below:

//don't use this which breaks if your pdf requires get parameters
//var loadingTask = (0, _pdfjsLib.getDocument)(parameters);
//uses the pdfFile url link we created above
var loadingTask = (0, _pdfjsLib.getDocument)(pdfFile);
  1. Search for "throw new Error('file origin does not match", about line 1865
  2. Comment out this javascript check for file origin

 if (fileOrigin !== viewerOrigin) {
        //don't throw the error, allow the file to be retrieved!!!!
        //throw new Error('file origin does not match viewer\'s');
 }
  1. Note: on line 1853, you will see -

var HOSTED_VIEWER_ORIGINS = ['null', 'http://mozilla.github.io', 'https://mozilla.github.io'];

You could use this to specify specific servers to allow for CORS, but by disabling the throws exception, you can accept any server. Anyways, why would they even put this HOSTED_VIEWER_ORIGINS in the base code, if they wanted us to use it?

like image 119
sboy Avatar answered Sep 19 '22 01:09

sboy


CORS issue also comes to me with PDF.js when I was providing the path to my PDF file in pdfjslib.getDocument. I resolved this issue by providing data URI of pdf file in getDocument method. I make data URI of pdf file as:

dataURI = "data:text/plain;base64," + (Get base64 of PDF from online tool or you can generate it by javascript as well);
like image 37
YATIN GUPTA Avatar answered Sep 21 '22 01:09

YATIN GUPTA