7 Replies Latest reply: Apr 16, 2013 10:45 AM by 888525 RSS

    write to a pdf file from a servlet response

    888525
      I have a servlet which is connecting to a url.i want to display the contents of this url which is a pdf file
      in the browser.How do I achieve this in the servlet?
      I was thinking if I could write to a sample pdf file placed at a location the response from the servlet and then show that file in the browser.Is there any direct way to display the pdf directly from the servlet in the browser.
      B elow the servlet code I am using. I am sure i am missing something.I am geting the response back but nothing is written to the test.pdf file.How can I use the response I am geting back from the url to show as a pdf file?


      public void doPost(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {

      try {
      DefaultHttpClient http = new DefaultHttpClient();
      final String username = "doamin\\userid";
      final String password = "password";
      UsernamePasswordCredentials c = new UsernamePasswordCredentials(username, password);
      BasicCredentialsProvider cP = new BasicCredentialsProvider();
      cP.setCredentials(AuthScope.ANY, c);
      http.setCredentialsProvider(cP);
      String urlString = "http://mymachine/TestServer/Pages/ReportViewer.aspx?"
      + "/TestReport&rs:Command=Render&param1=1"
      + "&rs:format=pdf";
      URL url = new URL(urlString);
      HttpPost post = new HttpPost(url.toURI());
      HttpResponse response1 = http.execute(post);
      HttpEntity entity = response1.getEntity();
      System.out.println(" The statusline is" + response1.getStatusLine());
      System.out.println("the content is" + entity.getContent());
      File tempPDFFile = new File("//mymachine//testreports/test.pdf");

      try {

      FileInputStream fileInputStream = new FileInputStream(tempPDFFile);
      OutputStream responseOutputStream = response.getOutputStream();
      int bytes;
      while ((bytes = fileInputStream.read()) != -1) {
      responseOutputStream.write(bytes);
      }
      System.out.println("Servlet sucessfully completed");
      } catch (Exception e) {
      e.printStackTrace();
      System.err.println("document: " + e.getMessage());
      }
      } catch (Exception ex) {
      System.out.println("The exception is" + ex);
      }
      }
      Please help.

      Thanks,
        • 1. Re: write to a pdf file from a servlet response
          DrClap
          885522 wrote:
          I was thinking if I could write to a sample pdf file placed at a location the response from the servlet and then show that file in the browser.
          No, don't do that.
          Is there any direct way to display the pdf directly from the servlet in the browser.
          Yes, simply copy the response from that URL to your servlet's response output stream. No need to muck about with temporary files. Don't forget to set the response headers correctly (before you send the response data).
          • 2. Re: write to a pdf file from a servlet response
            888525
            Thanks for the reply.I modified my code to just write the output stream but how will this help in displaying the pdf.the pdf just wont show up.

            Below is the modified servlet code

            public void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {

            try {
            DefaultHttpClient http = new DefaultHttpClient();
            final String username = "domain\\userid";
            final String password = "password";
            UsernamePasswordCredentials c = new UsernamePasswordCredentials(username, password);
            BasicCredentialsProvider cP = new BasicCredentialsProvider();
            cP.setCredentials(AuthScope.ANY, c);
            http.setCredentialsProvider(cP);
            String urlString = "http://mymachine/TestServer/Pages/ReportViewer.aspx?"
            + "/TestReport&rs:Command=Render&param1=1"
            + "&rs:format=pdf";
            URL url = new URL(urlString);
            HttpPost post = new HttpPost(url.toURI());
            HttpResponse response1 = http.execute(post);
            HttpEntity entity = response1.getEntity();
            System.out.println(" The statusline is" + response1.getStatusLine());
            System.out.println("the content is" + entity.getContent());
            InputStreamReader ir = new InputStreamReader(entity.getContent());
            BufferedReader rd = new BufferedReader(ir);
            response.setContentType("application/pdf");
            BufferedOutputStream bos = new BufferedOutputStream(response.getOutputStream());
            String line = "";
            while ((line = rd.readLine()) != null) {
            System.out.println("inside while");
            bos.write(line.length());
            }
            bos.close();
            ir.close();
            System.out.println("Servlet sucessfully completed");
            } catch (Exception e) {
            e.printStackTrace();
            System.err.println("document: " + e.getMessage());
            }
            } catch (Exception ex) {
            System.out.println("The exception is" + ex);
            }
            }



            The call to the servlet is

            public static synchronized Object callServletReportMethodTest(URL servletURL)
            throws RemoteServletException {
            Object returnValue = null;

            Cursor defaultCursor = Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR);
            RootPaneContainer comp = TestMenuView.getInstance();
            if (comp != null) {
            comp.getGlassPane().addMouseListener(new MouseAdapter() {
            });
            comp.getGlassPane().setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
            comp.getGlassPane().setVisible(true);

            }
            try {

            // Connect - returns URLConnection
            conn = servletURL.openConnection();
            conn.setDoOutput(true);
            conn.setUseCaches(false);
            conn.setRequestProperty("Content-Type", "application/octet-stream");
            //Write to the output stream
            returnValue = conn.getInputStream();
            // Open input stream, read the data and close the stream]
            ObjectInputStream in = new ObjectInputStream(conn.getInputStream());
            returnValue = in.readObject();
            in.close();
            // Attempt if 'timed-out'

            } catch (Exception ex) {
            System.out.println("Exception in calling" + ex);
            } finally {
            if (comp != null) {
            // comp.getGlassPane().setCursor(defaultCursor);
            comp.getGlassPane().setVisible(false);
            }
            }

            return returnValue;
            }

            No pdf opens up and i get the below exception on client code

            Exception in callingjava.io.StreamCorruptedException: invalid stream header: 003F061A

            Can someone point out what the mistake i am making
            Thanks,
            • 3. Re: write to a pdf file from a servlet response
              gimbal2
              while ((line = rd.readLine()) != null) {
              A PDF is not a text file and thus does not contain lines. You will want to research how to do regular input/output stream reading and writing, working on BINARY data.
              bos.write(line.length());
              and here you're writing the LENGTH of the line, not the line itself :s
              • 4. Re: write to a pdf file from a servlet response
                888525
                Thanks for the reply.I have modified my code and now I am using buffered stream for writing.
                Below is the modified code

                public void doPost(HttpServletRequest request, HttpServletResponse response)
                throws ServletException, IOException {

                try {
                DefaultHttpClient http = new DefaultHttpClient();
                final String username = "domain
                userid";
                final String password = "password";
                UsernamePasswordCredentials c = new UsernamePasswordCredentials(username, password);
                BasicCredentialsProvider cP = new BasicCredentialsProvider();
                cP.setCredentials(AuthScope.ANY, c);
                http.setCredentialsProvider(cP);
                String urlString = "http://mymachine/TestServer/Pages/ReportViewer.aspx?"
                + "/TestReport&rs:Command=Render&param1=1"
                + "&rs:format=pdf";
                URL url = new URL(urlString);
                HttpPost post = new HttpPost(url.toURI());
                HttpResponse response1 = http.execute(post);
                HttpEntity entity = response1.getEntity();
                System.out.println(" The statusline is" + response1.getStatusLine());
                System.out.println("the content is" + entity.getContent());
                forwardResponse(response1, response);

                } catch (Exception e) {
                e.printStackTrace();
                System.err.println("document: " + e.getMessage());
                }
                } catch (Exception ex) {
                System.out.println("The exception is" + ex);
                }
                }




                private void forwardResponse(HttpResponse reportCon, HttpServletResponse clientResponse) throws ServletException, IOException {
                // Take the report server's response and forward it to the client.

                try {

                clientResponse.setContentType("application/pdf");
                clientResponse.setHeader("Content-disposition", "inline");
                clientResponse.setBufferSize(1024);
                InputStream repInStream = reportCon.getEntity().getContent();
                ObjectOutputStream out = new ObjectOutputStream(clientResponse.getOutputStream());
                // Use a buffered stream to send all binary formats.
                BufferedInputStream bis = new BufferedInputStream(repInStream);
                BufferedOutputStream bos = new BufferedOutputStream(out);
                byte[] buff = new byte[8 * 1024];
                int bytesRead;
                while (-1 != (bytesRead = bis.read(buff, 0, 8 * 1024))) {
                bos.write(buff, 0, bytesRead);
                }
                bis.close();
                bos.close();
                bos.flush();
                System.out.println("After reading the file");

                repInStream.close();
                out.close();
                } catch (Exception ex) {
                System.out.println("the exception in servlet is" + ex);
                }
                }
                The pdf still doesnt opens up in the browser.Is this code sufficient to open the pdf or I have to write some other code
                where I am calling the servlet as in my post to show the pdf.I am having an applet and from the applet I am forming a url to servlet and this servlet should open up a pdf so any other changes required to make it work or something wrong with this code.
                Please help.Your comments have helped me reach till here.

                Thanks,
                • 5. Re: write to a pdf file from a servlet response
                  gimbal2
                  Please use \
                   tags when posting code.
                  
                  
                  while (-1 != (bytesRead = bis.read(buff, 0, 8 * 1024))) {
                  This should be enough:
                  while ((bytesRead = bis.read(buff)) != -1) {
                  bos.close();
                  bos.flush();
                  Don't you think that flushing a stream AFTER you close it is kind of odd or to be more precise: WRONG? Not that it matters, closing a stream will flush it first. But this kind of thing just proves that you are copy/pasting code from places without really understanding what it does. That just won't work. In stead of trying to do this in the servlet, why don't you try to create a little java program that simple copies a file from A to B? If you can get that to work properly, the same code should be used to do your servlet. Much easier to test that way.                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               
                  • 6. Re: write to a pdf file from a servlet response
                    888525
                    Thanks for the reply.I am new to working with streams .
                    May be I am wrong.Actually copying from location A to B will not work for me.
                    The url i am hitting generates a random report (adhoc) on the fly and is not saved anywhere .
                    The url is of a report server so I have to show the reports on the fly.

                    My only concern is how to show this pdf file to the browser.If I type the url I am trying to hit in my browser ,the reports
                    opens up as a pdf but not with Java code.

                    Thanks,
                    • 7. Re: write to a pdf file from a servlet response
                      888525
                      DrClap thanks for your reply.This is exactly what i want to acieve display the report from the servlet response in a browser.Can you see my code and tell what am i doing wrong

                      Thanks,