jsf primefaces progressbar update value while action method is running

11,656

this solution (using async) is a hack, but it works:

<p:commandButton id="executeButton" action="#{myBean.longOperation}"
    async="true" process="@form" value="start import"
    onclick="progress.start()" global="false" />

<br />

<p:progressBar ajax="true" widgetVar="progress" value="#{myBean.progress}"
    labelTemplate="{value}%" styleClass="animated" global="false" />

<br />

<p:outputPanel id="result" autoUpdate="true">
    <h:outputText value="#{myBean.message}" />
</p:outputPanel>

with this kind of bean

@ManagedBean
@ViewScoped
public class MyBean implements Serializable
{
    private static final long serialVersionUID = 1L;

    private double progress = 0d;
    private String message = "ready";

    public String longOperation() throws InstantiationException, IllegalAccessException
    {
        for(int i = 0; i < 100; i++)
        {
            // simulate a heavy operation
            progress++;
            message = "processing [" + i + "]";
            Thread.sleep(1000);
        }

        message = "completed";

        return "result";
    }

    public double getProgress()
    {
        return progress;
    }

    public void setProgress(double progress)
    {
        this.progress = progress;
    }

    public String getMessage()
    {
        return message;
    }

    public void setMessage(String message)
    {
        this.message = message;
    }
}
Share:
11,656
Niko
Author by

Niko

Updated on June 04, 2022

Comments

  • Niko
    Niko almost 2 years

    I have a submit-button on the bottom of my JSF-page, which submits all the inputs (texts, files etc.) to the database and server. Due to the duration this action takes, I want to show the user the progress of the operation, and on finish redirect him on the finish-site.

    My bean looks like:

    <h:form enctype="multipart/form-data">
        <p:commandButton widgetVar="submitButton" value="Save to DB" action="#{bean.submit}" onclick="PF('submitButton').disable();" />
        <p:progressBar widgetVar="pbAjax" ajax="true" value="#{bean.saveProgress}" interval="1000" labelTemplate="{value}%" styleClass="animated" />            
    </h:form>
    

    and my code:

    private int saveProgress;
    
    public String submit(){
        for(int i = 0; i < 100; i++){ //dummy values
            //DB operations
            //file uploads
            saveProgress = i;
            System.out.println("Progress: " + saveProgress);
        }
    
        return "finished.xhtml";
    }
    
    //getter for saveProgress
    

    the problem is, that neither the progressbar updates nor the pages navigates to finished.xhtml when done.

    What am I doing wrong here? is this a thread-problem (because submit is not thread-safe?) How can I solve this problem?

  • Niko
    Niko about 10 years
    the progressbar works now, but the navigation is not done :(. do you know for this also a solution?
  • Michele Mariotti
    Michele Mariotti about 10 years
    it's very strange... for me navigation is working too. does progressBar reach 100%?
  • Makky
    Makky about 10 years
    @MicheleMariotti Its a neat solution not a hack. async attribute is too good !
  • Niko
    Niko about 10 years
    the navigation can't work in your example, because it does not return string (action method)... PS: it reaches 100%, but the redirect is not executed to the xhtml page
  • Niko
    Niko about 10 years
    ok, I solved it; the problem is that I used external urls as result in action(). I replaced it with "../../somepage.xhtml?faces-redirect=true"; now it works. one last question; should I include the busy operation in the actionListener or action-method?