Display generated PDF file on iFrame with Java server-side - javascript

I'm currently developping a Java application, using Play! Framework 2.
In some page, I need to generate a PDF file on my server, then send it to the browser and display it, on an iframe or an embed tag.
I'm sending the file to the client-side using Play! result mechanism :
File resultFile = new File(outputFilePath);
response().setHeader("Content-Length", Long.toString(resultFile.length()));
return ok(resultFile).as("application/pdf");
On the client-side, I receive the file, and use createObjectUrl in order to get an URL to pass to my iframe
window.URL = window.URL || window.webkitURL;
var file = new window.Blob([result], { type: 'application/pdf' });
var fileUrl = window.URL.createObjectURL(file);
$("#displayDoc").attr("data", fileUrl);
The result of all of this is quite weird : the iFrame is displayed, shows as many pages as there is in my document, but all the pages are empty. And I get this error on the Dev Tools plugin of Chrome :
resource interpreted as document but transferred with mime type application/pdf chrome
Does anybody have an idea of what's going on?
Thanks!
Lauris

There's a few ways you can approach this.
The first way, and what might fit in better with your actual question.
Generate the PDF server side, then convert it to HTML
This is not nearly as difficult as it sounds however, and there are a number of tools out there to do it, such as 'PDF2DOM' ( http://cssbox.sourceforge.net/pdf2dom/ ), which will take an existing PDF representation and create an HTML dom from it, this HTML can then just be injected straight into the document using normal JavaScript techniques.
The second way (Especially if your using Java) is
Use a browser based plugin that can consume and display a PDF
Since your already developing in Java you could develop a Java Applet that can consume the PDF sent to it, and display it in the IFrame as required, you could also extend this Idea to use a Flash based PDF component, or anything else that the browser can run as a Plugin.
The Problem your going to have with this approach, is the growing trend of browser manufacturers to embrace HTML5 and move away from allowing 3rd party content in the Browser. Chrome & FF still support some, as does IE11, but as we go forward , especially into the brave new world of tablet computing, many browsers will not allow Plugins to be run, which means in the long term, this might work now, but may not for long.
The Third approach is
Take advantage of Native Browser Support
Both Chrome and Firefox today have built in PDF readers, and can display PDF documents directly in a browser tab just as though it was a regular HTML page.
The key here however is "In a TAB", in most cases browsers that can display PDF's will want to try and display them as a full tab resource.
It is possible to render PDF's in an IFrame, but the support vary's greatly from browser to browser, with IE8 and below, only displaying IF you have a plugin such as Adobe Acrobat installed.
One possible route you could try is to render the content out as an inline object using something like 'PDFObject' ( http://cssbox.sourceforge.net/pdf2dom/ ) , this will at least try to get the browser to see the PDF as an object in HTML5 which you may then be able to process using some other code in JS on the client.
My advice to you however, is for compatibility reasons, and if you want to leverage server side as much as possible, then option one is probably your best bet.
As for your chrome document type error, well that's quite an easy one to work out. :-)
You sent your content using the correct MIME Type (application/pdf) , but as far as chrome was concerned, when it received it, the document didn't look like a PDF file.
This often happens when you set the mime-type as PDF with the intention of sending a PDF, then send HTML (EG: Beacuse a server side error occurred and the web server sent an error page instead)
Hopefully something here will steer you in the right direction.

Related

What is the best way to display webpage content for a given URL using javascript?

I am developing a small labeling tool that given a URL should display a document hosted on that URL and allow a user to choose a label for that document.
I want to display the contents of the URL for this purpose. As far as I know, I can either get the URL content, parse the contents, and display or use an iframe option.
Without using parser
Iframes are not enabled for the target URL, the contents of which I want to display. Is there any other way to do this using javascript without using parser?
Using parser
I can crawl the contents of the URL, get everything between and dump it in the webpage area.
I'm new to javascript and front end development so I am not sure whether these are the only options.
Are there other options to do this?
If the parser is the only option, Can I dump the HTML that I get from the remote URL? I understand that images and other media that may be within on remote url won't be displayed. Is there any other caveat to this method? More importantly, Is this the best way to do this?
Most sites do it via the iframe like you mentioned like codepen.
Also, you can use Puppeteer ( a headless browser ) to do these sort of things. Get the contents using web scraping or take a screenshot or print a pdf. Pretty nifty library.
Most things that you can do manually in the browser can be done using
Puppeteer! Here are a few examples to get you started:
Generate screenshots and PDFs of pages. Crawl a SPA (Single-Page Application) and generate pre-rendered content (i.e. "SSR"
(Server-Side Rendering)).
Automate form submission, UI testing, keyboard input, etc. Create an up-to-date, automated testing environment.
Run your tests directly in the latest version of Chrome using the latest JavaScript and browser features.
Hope this helps !

Show local pdf inside webapplication [w/o remote server]

I'm developing a HTML5/.net POC in which I have a local HTML5 webapp shown inside a .net (C#) WebBrowser control.
The page is developed in asp.net MVC, downloaded as a single .htm file (using Chrome's SingleFile extension) and saved in a DB (or stored in a filesystem, doesn't matter), loaded and shown inside a .net webbrowser control.
[almost] Everything works: the page is rendered correctly, i can invoke js functions from C#, etc.
But now I have to show some pdf inline inside the page. The pdf is not served from a remote server (there's no server at all), but will be loaded from the filesystem (e.g. a temp file). The idea I have is to make a js function like showPdf(path, pageNum) in the html5 app and call it from .net.
The problem is that it looks there's no way (at least I couldn't find it) to load local pdf, both using Mozilla's pdf.js or html tags, I get "Not allowed to load local resource" in Chrome console/"Access denied" alert in IE.
Is there some kind of component I can try/option I can set to allow the browser to load local pdfs?
The WebBrowser component uses IE to render the page, so maybe some kind of IE option/key registry I can change (the machines that will eventually use this webapp are known, we can configure them as we want)?.
You could try a traditional anchor element (<a href="file:...">) and then enable the File Protocol Navigation feature control for your app. (And, though it may seem obvious, it's probably worth confirming that IE feature controls do not to enable functionality in other browsers.)
I don't know that this would work, but it seems like a possible solution given the question.
Note that accessing file objects may permission to access local file system objects may be disabled by other policies or security measures. More info/research may be needed.
Hope this helps...
-- Lance
I forgot to write here how I solved it:
well, it was a webapp shown inside a WinForm WebBrowser control, so I used this article to call a C# method from JS. The C# method used the default OS pdf reader to show the pdf inside the form.

JavaScript downloader

I want to allow a web site users to be able to download files from my site, but with the help of a client-side downloader with an ability to continue an interrupted download.
For example, I want to sent a person a file with a size of 30+ Meg. I want the user to have the best downloading experience, so I can't afford him downloading 25 Meg and then getting the download dropped due to the network problems on his side.
Therefore, I want to have a javascript downloader rendered on a download page, that will show the actual client-side file delivery, and when it is downloaded, to give an ability to a user to save the file.
Or is it not possible due to the fact that javascript won't be able to open a save file dialog and save to a file system?
I'm afraid that is not possible with JavaScript and that's why:
To continue downloading from the certain point you should send to the server the position number to start downloading from. And as JavaScript has no access to local file system, you can't get that position.
UPD: it seems that I was too hurrying with the reply.
The file size can be gotten using the HTML5 File API and after getting the file size you can pass it to the server which should support the partial downloading.
But anyway, after downloading another part of the file you should sew two pieces together in some way; standard web browser dialog will only suggest to overwrite the file.
UPD2: to work with files in some Internet Explorers you can use FileSystemObject:
var fso;
fso = new ActiveXObject("Scripting.FileSystemObject");
I'd look into making a plugin or extension. Like those DownloadThemAll extensions for firefox and Google chrome. Another alternative would be to use Flash, either alone or integrating it with javascript like hinted here: http://www.communitymx.com/content/article.cfm?cid=0922A

HTML5 / JavaScript: open text file, load into textarea / save textarea content to text file

I want to do two things in my browser:
Load a text file into a textarea (has to be choosen via dialog box)
Save the content of a textarea into a text file (has to be choosen via dialog box again)
Load a video file and grab the file path to use it with a video player (1)
I've been looking around for a while on the internet. There are some solutions for IE only via ActiveXObjects, which I can't use (IE, seriously?). HTML5 file API has limited usability because I can't access the selected file's path.
I also found save dialogs for textareas, but they ignored line breaks for some strange reason and I don't know how to fix that, if possible at all.
So here are my requirements and options:
Support for FF and Chrome
JavaScript, HTML5 (and PHP, if it has to be)
possibly Silverlight, but I'm not very familiar with it and may only copy and paste :-/
it has to work on Mac as well
There is a dirty hack that gets the job done without resorting to Flash or Silverlight, or using a server, and it works in most browsers:
var uriContent = "data:application/octet-stream," + encodeURIComponent(fileContentsAsString);
window.open(uriContent, 'Save Your File');
JS runs in a sandbox. That means: no access to files on the filesystem. HTML5 file API is the first „native” (as in not flash nor activex) attempt to grant limited access to the users file system.
The File API is HTML that would allow you to access data, after which you can manipulate binary blobs in JavaScript, but as written this is not possible in pure JS and HTML based on your requirements.
The big blocker is "saving to a text file." The only way I've been able to do this is by opening up an iFrame that calls a server side language (such as PHP) to set the content type in the header to a type that prompts a download.
Flash and Silverlight are "client" technologies that run outside of the sandbox, which sounds like your only option at this point.
My ideas:
Load a text file: Use a normal HTML upload form (if you want to script, maybe submit it via AJAX)
Save a text file: Use a textarea and upon submitting, create the file server-side and then offer it to download. (As mentioned before, client-side scripts do not have access to the computer's file system)
Load a video file: Is the video on the server already? Otherwise will need an upload just like the text file. Then use a flash plugin to play the file from the server (the URI should be known to you then)
All of these are relatively simple to achieve using PHP. Line breaks from a textarea stay as \n in PHP.
Tutorials: Form handling in PHP, File upload in PHP
Edit: Since PHP runs server-side you should not run into a lot of problems because of browser diversity. Alternatively, you can do all of these in Flash or Silverlight as well, although from my point of view that takes more learning and is less comfortable for the user.

How can javascript stream some contents to the user?

I need a Javascript sample which reads contents from a url and creates a file in the client with same contents when some button is clicked. I also understand that Javascript cannot be allowed to access the local file system (Unless you use ActiveX objects). I do not want to rely on ActiveX objects (since my client is not IE always).
So here is what I did. I used the standard XmlHttpRequest made a request and got my bytes. Now I thought I could kinda stream this contents to the user, first by opening a standard dialog box (the box that pops up when you attempt download something from internet with options like Open/Save/Cancel) and then asking the user to save it somewhere.
I know how to do the read part, can someone show some javascript/html sample on "How to stream open a confirm dialog box to the user and stream some contents?"
PS: Not too sure if this could be done in javascript at all but with Javascript you never know what is possible and what is not :)
Rather than using Javascript to stream the content, which is not possible for obvious security reasons, you need to point the browser at a URL that will return a 'Content-Type' header of 'application/octet-stream'. In most cases this will force the browser to initiate a 'save as' operation and ask the user what to do with it.
I believe it is possible to do this using an iframe in the same page, such that the user will not have to navigate away from the page or open a new tab/window.
See it this way: if you could read/write to users' computers using JavaScript, then no computer would be safe from browsing the web.
Having said so, you cannot read/write client-side files using JavaScript.
But you could if you use Flash / a Java applet; in those cases the embedded objects asks for your permission before doing such actions.
You may want to have a look at TiddlyWiki that claims it can write itself to the disk...
If I understand what your question is, then you want to use JavaScript to write data like a server-side script would (PHP, Python, Java, etc..) but in browser?
If so, then what your asking isn't possible with in browser JavaScript.
However if for some reason you wanted to do this with server-side JavaScript, then yes the "streaming" part is possible.

Categories

Resources