Update page after download

Asked

Viewed 752 times

2

I am working on a JSF page and I need to download a .pdf. When downloading the object is changed and I need to update it as I cannot allow the same download more than once. But if I use <f:ajax> download does not work.

   <h:commandLink actionListener="#{repositorioCobrancaAddMB.clear}" 
                  title="${messages['label.print']}" 
                  rendered="#{repositorioCobrancaAddMB.podeGeraBoleto(bean)}"
                  class="btn btn-white">
             <span class="fa fa-file-pdf-o"/>
             <f:ajax event="click" execute="@this" render="@all" listener="#{repositorioCobrancaAddMB.geraBoleto(bean)}"/>
     </h:commandLink> 

Without using ajax the download happens, but does not update my page!

     <h:commandLink action="#{repositorioCobrancaAddMB.geraBoleto(bean)}" 
                    actionListener="#{repositorioCobrancaAddMB.clear}" 
                    title="${messages['label.print']}" 
                    rendered="#{repositorioCobrancaAddMB.podeGeraBoleto(bean)}"
                    class="btn btn-white">
           <span class="fa fa-file-pdf-o"/>
      </h:commandLink> 

Method defining whether or not the user can generate the billet and billet generation methods.

   public boolean podeGeraBoleto(Titulo bean) {
        return tituloBC.podeGeraBoleto(bean);
    }

    public String geraBoleto(Titulo bean) {
//        return "titulo_list.jsf";
        TituloTO tituloTO = tituloBC.geraTituloTO(bean);
        if (bean.getNossoNumero() == null || bean.getNossoNumero().isEmpty()) {
            tituloBC.geraNossoNumero(bean, tituloTO);
        } else {
            tituloTO.buildNossoNumeroTO();
        }
        if (tituloTO.getNossoNumeroTO() == null) {
            getMessageContext().add(getResourceBundle().getString("banco.msg.null"), SeverityType.WARN);
            return null;
        }

        byte[] pdf = GeraBoleto.gera(tituloTO);

        this.geraPDF(pdf, bean);

        return null;
    }

    public void geraPDF(byte[] pdf, Titulo bean) {
        if (pdf == null) {
            return;
        }

        FacesContext context = FacesContext.getCurrentInstance();
        HttpServletResponse response = (HttpServletResponse) context.getExternalContext().getResponse();

        response.setHeader("Expires", "0");
        response.setHeader("Cache-Control", "must-revalidate, post-check=0, pre-check=0");
        response.setHeader("Pragma", "public");
        response.setContentType("application/pdf");
        response.setHeader("Content-Disposition", "attachment; filename=" + bean.getNumero() + " - " + bean.getParcela() + ".pdf");

        try {
            OutputStream out = response.getOutputStream();
            out.write(pdf);
            out.flush();
            out.close();
        } catch (IOException ex) {
            CriareLog.log(ex);
        }
    }

Titulobc

public boolean podeGeraBoleto(Titulo bean) {
        if (bean.getSituacao().isLiquidado()) {
            return false;
        }
        return bean.getPortador().getBanco().isCobranca() && bean.getPortador().getBloquetoEmissao().isCliente();
    }

Someone would know how to download and, at the end of it, refresh the page?

  • But does it have to be at the end of the download? It can’t be sooner?

  • It is that during the download process I change some information of the boleto, in this case, I inform that it has already had the boleto generated and already has banking information. As long as this change happens, it can be both sooner and later.

  • You are using Jsf 2.0?

  • I am using JSF version 2.2.11

  • @Gilvanandré Keep up the trouble?

  • Good morning... sorry it took me so long to answer. This problem is occurring in my work, and where I live is holiday on Monday, so I spent 3 days without having anything to do! I am resuming activities today. Even so thank you for the answers and again I apologize!

Show 1 more comment

3 answers

0

Replace with this :

public void geraBoleto(Titulo bean) {

    TituloTO tituloTO = tituloBC.geraTituloTO(bean);
    if (bean.getNossoNumero() == null || bean.getNossoNumero().isEmpty()) {
        tituloBC.geraNossoNumero(bean, tituloTO);
    } else {
        tituloTO.buildNossoNumeroTO();
    }
    if (tituloTO.getNossoNumeroTO() == null) {
        getMessageContext().add(getResourceBundle().getString("banco.msg.null"), SeverityType.WARN);
        return null;
    }

    byte[] pdf = GeraBoleto.gera(tituloTO);

    this.geraPDF(pdf, bean);

    FacesContext.getCurrentInstance().getExternalContext().
    redirect("nomeDaSuaPagina.jsf");


}
  • erased the other

  • Hello. I made the changes you suggested, but I still have the same problem! Thank you

0


It is not possible to give 2 answers, one being the file download and the other redirect. Another thing, with ajax will not work because it does not respond with the file download.

One possum is to create a condition in your .jsf to run the download after updated.

In his managedBean create a new variable

private boolean downloadPronto = false;

In his method geraBoleto(Titulo bean)

public String geraBoleto(Titulo bean)
{
    TituloTO tituloTO = tituloBC.geraTituloTO(bean);
    if (bean.getNossoNumero() == null || bean.getNossoNumero().isEmpty()) {
        tituloBC.geraNossoNumero(bean, tituloTO);
    } else {
        tituloTO.buildNossoNumeroTO();
    }
    if (tituloTO.getNossoNumeroTO() == null) {
        getMessageContext().add(getResourceBundle().getString("banco.msg.null"), SeverityType.WARN);
        return null;
    }

    // IMPORTATE NÃO GERAR O DOWNLOAD AINDA, SE NÃO SEU ATUALIZAR QUEBRA
    //byte[] pdf = GeraBoleto.gera(tituloTO);

    //this.geraPDF(pdf, bean);

    // CRIE ESSE ATRIBUTO INICILIZANDO COM `false` 
    // E ATUALIZE PRA SABER QUANDO ESTÁ PRONTO
    this.downloadPronto = true;

    return null;
}

Done that, on your .jsf create a condition:

<c:if test="#{seuManagedBean.downloadPronto}">
     <script>
          window.onload = function() {
               document.getElementById('formDownload:link').onclick();
          }
     </script>

     /* pode deixar escondido visualmente, serve apenas pra disparar o download */
     <h:form id="formDownload">
          <h:commandLink id="link" action="#{seuManagedBean.downloadDireto()}"/>
     </h:form>
</c:if>

And in your code create the method downloadDireto

public String downloadDireto() {
    TituloTO tituloTO = tituloBC.geraTituloTO(bean);

    byte[] pdf = GeraBoleto.gera(tituloTO);
    this.geraPDF(pdf, bean);

    this.downloadPronto = false; // reseta variavel

    return null;
}

Basically how it works, when you click on the button you already have it will update the values and update the new variable downloadPronto for real, when you return to the page he will enter in the condition of c:if and will call the click from the button to download without having to update the values.

  • for example "repositorio_edit.jsf? faces-redirect=true"?

  • Not yet tested, I will test now. One minute

  • I tested and unfortunately it didn’t work!

  • This way runs the method, only does not download the file

  • I kept him in commandlik

  • Using it with ajax? without ajax did not work

  • I rephrased my entire answer, take a look :)

  • 1

    From that I made some adaptations and it worked! It’s not exactly how I would like, but what interests me most is the functioning!

  • 1

    For now I thank!

Show 5 more comments

-1

Try to use the update:

<h:commandLink action="#{repositorioCobrancaAddMB.geraBoleto(bean)}" 
                    actionListener="#{repositorioCobrancaAddMB.clear}" 
                    title="${messages['label.print']}" 
                    rendered="#{repositorioCobrancaAddMB.podeGeraBoleto(bean)}"
                    class="btn btn-white"
                    update=":SEU_FORM">
           <span class="fa fa-file-pdf-o"/>
      </h:commandLink> 
  • 1

    I am not using the Primefaces component. JSF component does not have this option.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.