「ビューの更新」の問題について助けを求めたいです ;)
データベース内のデータをチェックするアプリケーションがあります。プロセス全体には1時間に1時間かかるため、特定の瞬間に何が起こっているかをユーザーに通知したいと思います(fe要素1がチェックされ、要素2がチェックされたなど..)。私の問題は、「チェックプロセス」がBeanで機能しているときにそれを行う方法です。
ダイアログ付きのテンプレートが1つあり、コマンドボタンは開始時にそれを呼び出し、メソッドが終了すると非表示にします。これは正常に動作しますが、このダイアログに sth のようなログ情報を入力したいときに問題が発生します。
コード:
テンプレート
<h:body styleClass="workBody" onload="logToggle();"> <h:form id="form"> <p:ajaxStatus onstart="dialog.show();" onsuccess="dialog.hide();"/> <p:poll interval="2" update="logScroll" global="false"/> <p:dialog id="dialog" header="LOADING.." widgetVar="dialog" resizable="false" width="400" modal="true" showEffect="clip" closable="false" hideEffect="fold"> <br /> <p:scrollPanel style="height:300px" id="logScroll" mode="native"> <p:dataTable id="logPanel" var="log" value="#{viewBean.log}"> <p:column headerText="Log"> <h:outputText value="#{log}" /> </p:column> </p:dataTable> </p:scrollPanel> <p:graphicImage value="resources/images/ajax-loader.gif" /> </p:dialog> <p:layout fullPage="true" id ="layout"> <p:layoutUnit position="center" id="center"> <ui:insert name="center"></ui:insert> </p:layoutUnit> </p:layout> </h:form>
UI挿入
<ui:define name="center"> <p:panel > <p:commandButton value="Check" action="#{actionClass.checkProject}" /> </p:panel> </ui:define>
アクションクラス
public class AccionClass { static Logger logger = Logger.getLogger(actionBean.class); private ArrayList<String> log; public ArrayList<String> getLog() { return log; } public void setLog(ArrayList<String> log) { this.log = log; } public void checkProject() { try { logger.info("Project Checking : started"); for (String sequence : selectedNodes) { logger.info("Project Checking : node " + sourceNode.getName()); LinkedHashMap<String, Item> nodeElements = getNodeItems(sequence) for (WsItem item : nodeElements.values()) { checkItem(item); } } } catch (Exception ex) { logger.info("Check project exception", ex); } } public void checkItem(Item item) { logger.info("Checking item : started"); try { Item itemToClone = sourceInstance.getApi().getVersionItem(version); logger.info("Checking item : item " + itemToClone.getName() + " with version " + version); log("info", "Checking item : item " + itemToClone.getName() + " with version " + version, false); } catch (Exception e) { messages.put("error in check item with version " + version, "Error"); logger.info("error in check item with version " + version); } } public void log(String severity, String message, Boolean isMessage) { log.add(message); } }
ViewBean
@SessionScoped @ManagedBean public class ViewBean { private ArrayList<String> log; static Logger logger = Logger.getLogger(ViewBean.class); public ActionClass action = new ActionClass(); public ArrayList<String> getLog() { if (page.equals("checkProject")) { return action.getLog(); } else return log; } public void setLog(ArrayList<String> log) { this.log = log; } }
私の考えは、checkProject 呼び出しの後、プロセスが機能し (actionClass のループの場合)、ajax ポーリングが viewBean getLog を使用してデータテーブルでダイアログを更新するというものでした。
この時点でのデータ フローは次のようになります。
- viewBean の getLog が 2 秒ごとに呼び出されます。コマンドボタンをクリックする前に。
- commandButton をクリックした後、ダイアログボックスが表示され、値のないログが取得されます - データテーブルは空です。
- checkProject は機能しており、log4j ロガーと actionClass ログに書き込まれていますが、viewBean.getLog は呼び出していません。
- メソッド終了後、ビューが更新され、ダイアログが閉じられます。
actionClass でログをクリアせずにこのメソッドを再度実行すると、2 番目のステップで最後の呼び出しから値を取得したため、メソッドが機能します。
手伝ってくれてありがとう..