[RESOLVIDO] Exibir pdf na pagina ou imprimir diretamente JSF 2.0 + primefaces

Olá a todos, bom estou tentando sem sucesso exibir um relatório em pdf diretamente na pagina, sei que existem milhoes de exemplos de códigos por ai, mas o fato é q eu já tentei vários, e simplesmente não acontece nd ao clicar no meu commandbutton.
é assim, em determinada parte do site, o usuario faz um pedido de orçamento, e ao salvar, eu usei o compomente p:filedownload do prime, para dar opção do usuario baixar o pdf do relatorio, mas em outra parte do site, os funcionarios da empresa devem ter uma opção de visualizar esse relatório diretamente na pagina, sem precisar fazer (download, salvar e dai abrir), ou então imprimir ele também diretamente sem vizualizar, e isso eu nao estou conseguindo fazer, já tentei usar vários codigos como o abaixo, com pequenas diferenças, mas quando executa, nada acontece no browser…
Lembrando q estou usando jsf 2.0 e primefaces, será q tem algo a ver com a forma q o navegador do jsf trata as requisições, atraves de forward ? se sim, alguem tem idéia de como resolver? [code]public void visualizarRelatorio() {
try {
System.out.println(“entrou no visualizar relatorio”);
if (orcamentoSelecionado == null) {
return;
}
//---------- gera o relatorio ----------
HashMap parametros = new HashMap();
parametros.put(“orcamento”, orcamentoSelecionado);

        JasperReport jasperReport = JasperCompileManager.compileReport(getClass().getResourceAsStream("/relatorios/PedidoDeOrcamento.jrxml"));
        JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport, parametros, new JRBeanCollectionDataSource(itens));
        byte[] b = JasperExportManager.exportReportToPdf(jasperPrint); 

        HttpServletResponse res = (HttpServletResponse) FacesContext.getCurrentInstance().getExternalContext().getResponse();
        res.setContentType("application/pdf");
        //Código abaixo gerar o relatório e disponibiliza diretamente na página 
        res.setHeader("Content-disposition", "inline;filename=arquivo.pdf");
        //Código abaixo gerar o relatório e disponibiliza para o cliente baixar ou salvar 
        //res.setHeader("Content-disposition", "attachment;filename=arquivo.pdf");
        res.getOutputStream().write(b);
        res.getCharacterEncoding();
        FacesContext.getCurrentInstance().responseComplete();
        System.out.println("saiu do visualizar relatorio");
    } catch (Exception ex) {
        ex.printStackTrace();
    }
}[/code]***EDIT *** faltou o código do commandbutton[code]<p:commandButton value="Visualizar relatório"
                         action="#{mBConsultarOrcamentos.visualizarRelatorio()}" 
                         style="width: 50px;font-family: Tahoma;font-size: 12px"/>[/code]Desde já grato ! t+

mude o comandButton de p para h!

<h:commandButton value="Visualizar relatório" action="#{mBConsultarOrcamentos.visualizarRelatorio()}" style="width: 50px;font-family: Tahoma;font-size: 12px"/>
Quanto a ver o PDF direto no browser tem mais haver com o pdf reader que voce instalaou por exemplo o foxit te da opcao de visualizar o pdf no browser. Acho que a resposta chega ao browser (com o tipo) a decisao de abrir direto no browser ou nao e dependente do browser e dos aplicativos instalados na maquina do usuario.

hahaha valeu dreampeppers99, mudar do commandbutton do prime para o do jsf resolveu, eu uso o acrobat reader aqui, ele abriu certinho no browser, só q o command button perdeu a formatação do theme do primefaces, ficou cinza normal…

e para imprimir diretamente, vc tem idéia de como se faz?

Nao :frowning:

para vc executar o metodo do relatorio com p:commandButton, vc tem q setar a opção ajax para false.

flw

Pra exibir diretamente, podes usar o JasperViewer, mas vai abrir janela.
Pra exibir o pdf diretamente na página, inclusive com controle, eu indico sempre o icePDF.
Abraço!

valeu alissonvla, funcionou, e quanto a imprimir direto, vou deixar quieto, vou disponibilizar somente um botão “vizualizar” e dai se quizer imprimir, o cara imprime pelo plugin pdf instalado no browser, no meu caso o adobe…

desculpe as nubice ai pessoal, sei que esses detalhes sao coisas simples, mas o fato é q eles acabam atrapalhando e muito a vida de quem tah começando a programar pra web como eu

vlw a ajuda ai t+

leoramos, mas se usar o jasperviewer, nao vai exibir no lado servidor?

Resolvi o meu problema utilizando Servlet.

[code]import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.ServletOutputStream;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import net.sf.jasperreports.engine.JRDataSource;
import net.sf.jasperreports.engine.JasperExportManager;
import net.sf.jasperreports.engine.JasperFillManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.data.JRBeanCollectionDataSource;

/**
*

  • @author Paulo Vinícius Moreira Dutra
  • @version 1.0

*/
@WebServlet(name = “RelatorioServlet”, urlPatterns = {"/RelatorioServlet"})
public class RelatorioServlet extends HttpServlet {

public static final String IMAGES_DIR = "/br/requisitebuilder/relatorios/";  

public static final String IMAGE_LOGO = "logo.png";         

protected void processRequest(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {
    
    response.setHeader("application/pdf", "Content-Type");  
    response.setContentType("application/pdf");
    
    //Para download
    //   response.setContentType("application/vnd.ms-excel");  
    //response.setHeader("Content-Disposition","attachment;filename=relatorioExcel.xls"); 
    InputStream caminho = null;
    
    ServletOutputStream ouputStream = null;               
    
    try{                         
         
         List listagem = new ArrayList();

         HttpSession session = request.getSession(true);                          
         
         Object attribute = session.getAttribute("listagem");
         String relatorio = session.getAttribute("relatorio").toString();           
         
         System.out.println(attribute);
         System.out.println(relatorio);
         
         if (attribute instanceof List);             
            listagem = (List)attribute;
         
         if (listagem == null)
             listagem = new ArrayList();
         
         String logoPath = IMAGES_DIR + IMAGE_LOGO;
         
         caminho = Report.class.getResourceAsStream(relatorio);
         
         System.out.println(caminho);
         
         HashMap parametros = new HashMap();
         parametros.put("IMAGE_TOPO", logoPath );
             
         JRDataSource jrds = new JRBeanCollectionDataSource(listagem);  
         JasperPrint preencher = JasperFillManager.fillReport(caminho, parametros, jrds);
                    
         byte[] bytes = JasperExportManager.exportReportToPdf(preencher);
       
         response.setContentLength(bytes.length);                   
         
         ouputStream = response.getOutputStream();  
         ouputStream.write(bytes, 0, bytes.length);               
         
         ouputStream.flush();
         
     }catch(Exception e){
         e.printStackTrace();         
     }finally {
        
        if (caminho != null)
            caminho.close();
        
        if (ouputStream != null)
            ouputStream.close();
        
     }
    
}

@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {
    processRequest(request, response);
}

@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {
    processRequest(request, response);
}

@Override
public String getServletInfo() {
    return "Short description";
}// </editor-fold>[/code]

Na minha classe ManagedBean adicionei um método para redirecionar o o servelt

[code] protected void redirect(String page){

    FacesContext ctx = FacesContext.getCurrentInstance();
    ExternalContext ec = ctx.getExternalContext();                
            
    try {
        ec.redirect(ec.getRequestContextPath() + page);
    } catch (IOException ex) {
        addMessageErro(ex.getMessage());
    }

}   

public void imprimirRelatorio() throws Exception{  

     try
     {
         
        FacesContext ctx = FacesContext.getCurrentInstance();
        HttpSession session = (HttpSession) ctx.getExternalContext().getSession(false);                         
        session.setAttribute("listagem", listagem);
        session.setAttribute("relatorio", "Requisitos.jasper");
        
        redirect("/RelatorioServlet");

     }catch(Exception ex){
         addMessageErro(ex.getMessage());             
     }
     
}[/code]

Na minha página JSF o comandButton do primefaces

     <p:commandButton id="btnRelatorio"
                                   value="Relatório"
                                   immediate="false"
                                    action="#{requisitoMB.imprimirRelatorio}"
                                    styleClass="btnNovo"
                                    style="text-align: center; width: 100px; 
                                     margin: 0 auto; border-style: solid; ">
     </p:commandButton> 

show de bola, paulo!
Mas me diga uma coisa pq n colocou ajax=“false” no componente do prime? vc colocou immediat=“false” são a mesma coisa?

[quote=gambazinho]show de bola, paulo!
Mas me diga uma coisa pq n colocou ajax=“false” no componente do prime? vc colocou immediat=“false” são a mesma coisa?[/quote]

Na verdade você pode omitir o parâmetro immediate=false, pois eu estava realizando alguns teste.

Abraços

Eu preciso fazer a mesma coisa contudo quero dar a opção pro usuário abrir/baixar o arquivo .pdf em vez de exibir em tela. Se eu alterar a linha:

 //Código abaixo gerar o relatório e disponibiliza diretamente na página 
            res.setHeader("Content-disposition", "inline;filename=arquivo.pdf");

para:

//Código abaixo gerar o relatório e disponibiliza para o cliente baixar ou salvar 
            //res.setHeader("Content-disposition", "attachment;filename=arquivo.pdf");

Vai resolver ou preciso alterar mais alguma coisa?

Outra dúvida, o teu diretório: “/relatorios/PedidoDeOrcamento.jrxml” está abaixo diretamente da raíz da aplicação?

gRoOve, salvo engano, nao precisa alterar mais nada não…

quanto ao diretório, ele esta na raiz do projeto, junto com outros diretorios como util, cfg, beans, dao, enfim…

vlw t+

Por favor, alguém consegue me ajudar, já estou 2 semanas tentando fazer esse relatório e não consigo =((
Meu código executa sem erro mas não acontece NADAA.

public void gerarRelatorio() throws IOException {
		try {
			System.out.println("entrou no visualizar relatorio");

			InputStream is = getClass().getResourceAsStream("RelatorioCategoriaPorNome.jasper");

			Map<String, Object> parametro = new HashMap<String, Object>();
			parametro.put("nomeCategoria", "bar");

			JasperPrint jasperPrint = JasperFillManager.fillReport(is, parametro, ConnectionFactory.getTurismoGuiadoConnection());
			byte[] b = JasperExportManager.exportReportToPdf(jasperPrint);

			HttpServletResponse res = (HttpServletResponse) FacesContext.getCurrentInstance().getExternalContext().getResponse();
			res.setContentType("application/pdf");
			//Código abaixo gerar o relatório e disponibiliza diretamente na página   
			res.setHeader("Content-disposition", "attachment;filename=arquivo.pdf");
			res.getOutputStream().write(b);
			res.getCharacterEncoding();
			FacesContext.getCurrentInstance().responseComplete();
			System.out.println("saiu do visualizar relatorio");
		} catch (Exception ex) {
			ex.printStackTrace();
		}
	}

Com relação ao botão do primefaces sem o css do componente, na verdade você não precisa usar o <h:commandButton> pode utilizar o <p:commandButton ajax="false" /> vai funcionar.

Boa tarde,
estou tentando usar essa forma que vc colocou acima, poderia me falar certinho qual as bibliotecas tem que importar.

Bom dia

Desculpe reabrir a discussão ai. Sua solução esta funcionando perfeitamente aqui para mim paulofafism.

					<p:column style="width:30px;" headerText="Texto">
						<p:commandButton action="#{proposicaoBean.imprimirDocumento}" icon="ui-icon-circle-zoomin" title="Texto" 
							ajax="false" onclick="this.form.target='_blank'" 
							style="width:20px;height:20px;">							
							<f:setPropertyActionListener value="#{obj}"	target="#{proposicaoBean.legRotinaWrapperSelecionada}"/>							
						</p:commandButton>
					</p:column>	

Tenho isso dentro de um grid paginado ( paginação padrão do prime ). Listo 20 registros por página, se clicar em um por um visualiza tudo beleza.

Ao mudar de página (vou para a página 5 da listagem por exemplo), ao clicar no botão visualizar ele abre uma página nova no primefaces, ou seja ignorando minhas funções. A página aberta é a mesma daonde eu cliquei só que volta para a pagina 1.

Alguma dica do que poderia ser?