Emissão de relatórios em sistema web

Como o nosso colega renanreismartins disse, e eu uso tbém seria desta forma:


bytes = JasperRunManager.runReportToPdf(relatorioJasper,parametros,conexao.MinhaConexao);   
		     
		      // envia o relatório em formato PDF para o browser   
		      res.setContentType("application/pdf");
		      
		      res.setContentLength(bytes.length);   
		      ServletOutputStream ouputStream = res.getOutputStream();   
		      ouputStream.write(bytes, 0, bytes.length);   
		      ouputStream.flush();   
		      ouputStream.close();    

[quote=Paezani]Como o nosso colega renanreismartins disse, e eu uso tbém seria desta forma:

[code]

bytes = JasperRunManager.runReportToPdf(relatorioJasper,parametros,conexao.MinhaConexao);

	      // envia o relatório em formato PDF para o browser   
	      res.setContentType("application/pdf");
	      
	      res.setContentLength(bytes.length);   
	      ServletOutputStream ouputStream = res.getOutputStream();   
	      ouputStream.write(bytes, 0, bytes.length);   
	      ouputStream.flush();   
	      ouputStream.close();    

[/code][/quote]

Então, mas se eu fizer dessa forma (com mais algumas particularidades do JSF) ele vai mandar salvar no disco do cliente.
Isso é por causa do meu plugin do PDF? To no ubuntu e com ctz não tenho aquele plugin da adobe.

Abraços.

Tchello testa numa maquina com o adobe instalado. pq realmente eh necessario o plugin

[quote=celia fernandes]Bom, eu na minha Servlet criei um botão ‘Relatorio’ assim:
PS: Coloque seu projeto no mesmo caminho que vc especificar no código…
[/quote]

Oi pessoal, voltei…
Então fiz o codigo para gerar o relatorio…
fiz q nem a celia fernandes colocou no dela…
fiz a mesma coisa no meu servlet…
e nao deu certo… alguem pode me auxiliar???

[code]protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

	byte[] bytes = null;
	
	try{
		JasperReport relatorioJasper = (JasperReport) JRLoader.loadObject("F:\\PortalCorporativoWebTCC\\PortalCorporativoWebTCC\\WebContent\\Relatorios\\geral.jasper");
		
		Map<String, Object> params = new HashMap<String, Object>();
		//params.putAll(arg0);
		
		bytes = JasperRunManager.runReportToPdf(relatorioJasper, params);		
	}catch (JRException e){
		e.printStackTrace();
	}
		if(bytes != null && bytes.length > 0){
			response.setContentType("application/pdf");
			response.setContentLength(bytes.length);
		
			ServletOutputStream outPutStream = response.getOutputStream();
			outPutStream.write(bytes, 0, bytes.length);
			outPutStream.flush();
			outPutStream.close();
		}		
}[/code]

Na hora que eu clico no botao relatorio na minha tela (JSP), chama essa servlet… e nisso da um erro… :?

javax.servlet.ServletException: Error instantiating servlet class br.santacruz.tcc.servlet.RelatorioGeralServlet org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293) org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:849) org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583) org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:454) java.lang.Thread.run(Unknown Source)

Não faço menor ideia do q seja…

O que tem no construtor dessa classe?

UHm… nao tenho construtor nessa classe… =/
Continuando o erro q da… tem algo com construtor no erro mesmo… =/
Como arrumo isso??? :idea:

[code]java.lang.NoClassDefFoundError: net/sf/jasperreports/engine/JRException
java.lang.Class.getDeclaredConstructors0(Native Method)
java.lang.Class.privateGetDeclaredConstructors(Unknown Source)
java.lang.Class.getConstructor0(Unknown Source)
java.lang.Class.newInstance0(Unknown Source)
java.lang.Class.newInstance(Unknown Source)
org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293)
org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:849)
org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583)
org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:454)
java.lang.Thread.run(Unknown Source)

[/code]

Coloquei o construtor… mas continua dando o mesmo erro

[code] public RelatorioGeralServlet() {

}[/code]

Eve, a aplicação não consegue encontrar alguma classe que está sendo usada.
Quais jars voc adicionou a sua aplicação?
Faça uma experiência: coloque na lib do seu jboss/tomcat os jars da sua aplicação, principalmente os do JasperReports, que aparentemente são os que estão faltando.

oi meu anjo… testa esse cara aqui:



//import br.gov.treap.util.Conexao;
import java.io.IOException;
import java.io.StringReader;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;
import java.util.HashMap;

import net.sf.jasperreports.engine.JasperManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperReport;
import net.sf.jasperreports.engine.design.JasperDesign;
import net.sf.jasperreports.view.JasperViewer;

/* Primeira parte */
public class Relatorio {

    private Connection con = null;
    private String driver = &quot;oracle.jdbc.driver.OracleDriver&quot;;
    private String endereco = &quot;jdbc:oracle:thin:@host:1521:sid&quot;;
    private String user = &quot;user&quot;;
    private String pass = &quot;senha&quot;;
    private ResultSet rs = null;
    private String valores[] = new String[10];
//    private int chamada = 1;

//    Localizar pasta que contém os relatórios:
//    private String dir = System.getProperty(&quot;user.dir&quot;) + &quot;/web/&quot;;
    private String dir = &quot;Aqui o diretorio do seu projeto ou utilizar a linha anterior&quot;;
//    private StringReader stream;
    /*Segunda parte */

    public void GeraRelatorio(String sql, String relatorio) {
        /* Efetua a conexao a base de dados e coleta os valores da base de dados armazenando-os
        em um array para ser futuramente utilizado */
        try {
            if (con == null) {
                Class.forName(driver);
                con = DriverManager.getConnection(endereco, user, pass);
                Statement statement = con.createStatement();
                rs = statement.executeQuery(sql);
                HashMap teste = new HashMap();
                while (rs.next()) {
                    //for até o numero de campos da tabela
                    for (int i = 1; i &lt; 10; i++) {
                        valores[i] = rs.getString(i);
                    }
                }
            }
        } catch (Exception e) {
            System.err.println(&quot;Problemas apresentados na operacao de conexao&quot;);
            e.printStackTrace();
        }
        /* Inicio do bloco que ira gerar nossos relatorios e 3ª parte */
        try {
            //String array[] = valores;
            JasperDesign design = JasperManager.loadXmlDesign(dir + &quot;relatorios/comprovante_rendimentos1.jrxml&quot;);
            JasperReport jr = JasperManager.compileReport(design);
            HashMap parameters = new HashMap();
            parameters.put(&quot;PAR_PEDID&quot;, 1);
            //parameters.put(&quot;PARAMETRO_2&quot;, array[2]);
            //parameters.put(&quot;PARAMETRO_3&quot;, array[5]);
            //parameters.put(&quot;PARAMETRO_4&quot;, array[4]);
            //parameters.put(&quot;PARAMETRO_5&quot;,array[9]);
            JasperPrint impressao = JasperManager.fillReport(jr, parameters, con);
            JasperViewer jrviewer = new JasperViewer(impressao, false);
            jrviewer.show();
            con.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

aqui ele funciona q é uma beleza!
abraço

[quote=phmjunior]oi meu anjo… testa esse cara aqui:



//import br.gov.treap.util.Conexao;
import java.io.IOException;
import java.io.StringReader;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;
import java.util.HashMap;

import net.sf.jasperreports.engine.JasperManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperReport;
import net.sf.jasperreports.engine.design.JasperDesign;
import net.sf.jasperreports.view.JasperViewer;

/* Primeira parte */
public class Relatorio {

    private Connection con = null;
    private String driver = &quot;oracle.jdbc.driver.OracleDriver&quot;;
    private String endereco = &quot;jdbc:oracle:thin:@host:1521:sid&quot;;
    private String user = &quot;user&quot;;
    private String pass = &quot;senha&quot;;
    private ResultSet rs = null;
    private String valores[] = new String[10];
//    private int chamada = 1;

[/quote]

UHm vou tentar… só me diga mais uma coisa…rs
Pra isso eu crio outra classe, e faço esse código? e na minha servlet chamo esse metodo???
ou esse código eu coloco na servlet…
ja tinha visto um exemplo parecido com esse em outro site, mas nao tentei, por essa duvida q tenho…

[quote=phmjunior]oi meu anjo… testa esse cara aqui:



//import br.gov.treap.util.Conexao;
import java.io.IOException;
import java.io.StringReader;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;
import java.util.HashMap;

import net.sf.jasperreports.engine.JasperManager;
import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperReport;
import net.sf.jasperreports.engine.design.JasperDesign;
import net.sf.jasperreports.view.JasperViewer;

/* Primeira parte */
public class Relatorio {

    private Connection con = null;
    private String driver = &quot;oracle.jdbc.driver.OracleDriver&quot;;
    private String endereco = &quot;jdbc:oracle:thin:@host:1521:sid&quot;;
    private String user = &quot;user&quot;;
    private String pass = &quot;senha&quot;;
    private ResultSet rs = null;
    private String valores[] = new String[10];
//    private int chamada = 1;

//    Localizar pasta que contém os relatórios:
//    private String dir = System.getProperty(&quot;user.dir&quot;) + &quot;/web/&quot;;
    private String dir = &quot;Aqui o diretorio do seu projeto ou utilizar a linha anterior&quot;;
//    private StringReader stream;
    /*Segunda parte */

    public void GeraRelatorio(String sql, String relatorio) {
        /* Efetua a conexao a base de dados e coleta os valores da base de dados armazenando-os
        em um array para ser futuramente utilizado */
        try {
            if (con == null) {
                Class.forName(driver);
                con = DriverManager.getConnection(endereco, user, pass);
                Statement statement = con.createStatement();
                rs = statement.executeQuery(sql);
                HashMap teste = new HashMap();
                while (rs.next()) {
                    //for até o numero de campos da tabela
                    for (int i = 1; i &lt; 10; i++) {
                        valores[i] = rs.getString(i);
                    }
                }
            }
        } catch (Exception e) {
            System.err.println(&quot;Problemas apresentados na operacao de conexao&quot;);
            e.printStackTrace();
        }
        /* Inicio do bloco que ira gerar nossos relatorios e 3ª parte */
        try {
            //String array[] = valores;
            JasperDesign design = JasperManager.loadXmlDesign(dir + &quot;relatorios/comprovante_rendimentos1.jrxml&quot;);
            JasperReport jr = JasperManager.compileReport(design);
            HashMap parameters = new HashMap();
            parameters.put(&quot;PAR_PEDID&quot;, 1);
            //parameters.put(&quot;PARAMETRO_2&quot;, array[2]);
            //parameters.put(&quot;PARAMETRO_3&quot;, array[5]);
            //parameters.put(&quot;PARAMETRO_4&quot;, array[4]);
            //parameters.put(&quot;PARAMETRO_5&quot;,array[9]);
            JasperPrint impressao = JasperManager.fillReport(jr, parameters, con);
            JasperViewer jrviewer = new JasperViewer(impressao, false);
            jrviewer.show();
            con.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

aqui ele funciona q é uma beleza!
abraço[/quote]

Cara, então, estamos em java para web(jsp, servlets, jsf…), creio que isso não vá funcionar nesse contexto, correto?

Ola,

o erro:

java.lang.NoClassDefFoundError: net/sf/jasperreports/engine/JRException 

significa que essa classe não foi encontrada. Por que? Porque ela faz parte do jasper reports.Então vc precisa colocar os jars necessarios no CLASSPATH do seu projeto.

[]´s

de onde vc tirou essa conclusão q isso não funciona para web?
vc só pode ta de brincadeira né amigo? :wink:

ou vc não sabe chamar um metodo de classe em um servlet?
caso não saiba eu posto aqui o servlet q completa essa classe.

de onde vc tirou essa conclusão q isso não funciona para web?
vc só pode ta de brincadeira né amigo? :wink:[/quote]
Não, não estou de brincadeira, mas pelo que pude observar esse componente do JR exibe uma GUI e como os managedbean/servlets são executados server-side…
Posso estar equivocado, por favor me corrija caso isso se afirme, seria até bom já que resolveria de vez meu problema.
Você o usa com servlets?

OK… posso usar isso na servlet???

claro q sim!!!
você cria a chamada em sua servlet. observem q o método GeraRelatorio vem com void, por tanto podendo ser chamado em um servlet
segue exemplo:

import java.io.IOException;
import java.io.PrintWriter;
import java.sql.SQLData;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 *
 * @author Pedro Junior
 * @creator in 26/10/2009
 */
public class chamarMetodoRelatorio extends HttpServlet {
   
    protected void processRequest(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {

// essa parte seria o comando para chamar o quiser na servlet
// estou usando o cmd=relat para chamar essa parte do servlet
    String cmd = request.getParameter("cmd");
//caso ele esteja nulo vem o principal. pode ignorar isso se preferir retirando essa pasrte
    if(cmd == null)
        cmd = "principal";

// aqui fica o nome do relatorio chamado
    String relatorio = "comprovante_rendimentos1";//request.getParameter("relat")

// a instrução selct para quem utiliza relatório dinamico
    String sql = "select * from chamado";

// aqui segue a chamada do metodo da classe Relatorio
        try {
      if (cmd.equalsIgnoreCase("relato")){
// instâncio a classe
          Relatorio relatorios = new Relatorio();

//chamo o metodo
          relatorios.GeraRelatorio(sql, relatorio);
      }


        }catch(Exception e){
            e.printStackTrace();
        }
    } 

pronto moçada, agora pode pagar o lanche. rsrsrsrs

já ia esquecendo…
vocês já devem saber mas posto assim mesmo.

deve configurar o web.xml para chamar o servlet:

&lt;servlet&gt;
        &lt;servlet-name&gt;chamarMetodoRelatorio&lt;/servlet-name&gt;
        &lt;servlet-class&gt;br.gov.treap.relatorios.chamarMetodoRelatorio&lt;/servlet-class&gt;
&lt;/servlet&gt;
&lt;servlet-mapping&gt;
        &lt;servlet-name&gt;chamarMetodoRelatorio&lt;/servlet-name&gt;
        &lt;url-pattern&gt;/chamarMetodoRelatorio.do&lt;/url-pattern&gt;
&lt;/servlet-mapping&gt;

ai vcs chamam o cara assim: http://meusite.com.br/chamarMetodoRelatorio.do?cmd=relat

agora sim vcs podem pagar a pizza. desculpe a onda mas é costume aqui no trampo o cara pagar um lanche para o colega q ajuda a resolver galhos.

abraço moçada

Cara, to falando que não da.
O JasperView tenta abrir uma interface gráfica que ocorre no lado do servidor, quando executei aqui deu o seguinte erro:

Erro ao enviar impressao: No X11 DISPLAY variable was set, but this program performed an operation which requires it. 

Acompanhando com o depurador nota-se que uma HeadlessException é lançada com essa mensagem acima.
Lembrando que estou usando JSF, portando o método é executado num ManagedBean e a aplicação está num JBoss instalado num ubuntu server (sem X11, o que justifica a exception acima, por que o ManagedBean é processado no lado do servidor).
Entendeu onde eu quero chegar?
Gostaria muito de puder executar um JasperView pela web, tem mais alguma sugestão?

Eu sempre crio um diretório dentro da pasta WEB e ma referencio a ele através do getRealPath, pois nem sembre é sabido onde o sistema e qual ambiente o sistema estará implantado.

String relatorio = request.getRealPath("WEB/jasper/ModeloGuia.jasper"); try { java.util.Map parametro = new java.util.HashMap(); parametro.put("idemitida", idguia); JasperReport jr = (JasperReport) JRLoader.loadObject(relatorio); byte buffer[] = JasperRunManager.runReportToPdf(jr, parametro, banco.ConnectionFactory.getConnection()); response.setContentType("application/pdf"); response.setContentLength(buffer.length); ServletOutputStream outputStream = response.getOutputStream(); outputStream.write(buffer, 0, buffer.length); outputStream.flush(); outputStream.close(); } catch (JRException ex) { Logger.getLogger(bbIndex.class.getName()).log(Level.SEVERE, null, ex); }

[quote=ivesbertoli]Eu sempre crio um diretório dentro da pasta WEB e ma referencio a ele através do getRealPath, pois nem sembre é sabido onde o sistema e qual ambiente o sistema estará implantado.

String relatorio = request.getRealPath("WEB/jasper/ModeloGuia.jasper"); try { java.util.Map parametro = new java.util.HashMap(); parametro.put("idemitida", idguia); JasperReport jr = (JasperReport) JRLoader.loadObject(relatorio); byte buffer[] = JasperRunManager.runReportToPdf(jr, parametro, banco.ConnectionFactory.getConnection()); response.setContentType("application/pdf"); response.setContentLength(buffer.length); ServletOutputStream outputStream = response.getOutputStream(); outputStream.write(buffer, 0, buffer.length); outputStream.flush(); outputStream.close(); } catch (JRException ex) { Logger.getLogger(bbIndex.class.getName()).log(Level.SEVERE, null, ex); }[/quote]

Já uso esse recurso do realPath.
Tenho um código muito semelhante a esse e o mais estranho e que quando obtenho o ServletOutPutStream e dou um “write” com meu vetor de bytes (devidamente populado e válido) é lançado um NPE.
O ServletOutputStream não é nulo, mas fazendo um debug pude notar que as streams que ele contém são nulas.
Isso que me deixa mais intrigado!