diff --git a/org.adempiere.base.process/src/org/adempiere/process/InOutGenerateRMA.java b/org.adempiere.base.process/src/org/adempiere/process/InOutGenerateRMA.java index bb686c2fa6..1ef4438ed7 100644 --- a/org.adempiere.base.process/src/org/adempiere/process/InOutGenerateRMA.java +++ b/org.adempiere.base.process/src/org/adempiere/process/InOutGenerateRMA.java @@ -35,6 +35,7 @@ import org.compiere.process.ProcessInfoParameter; import org.compiere.process.SvrProcess; import org.compiere.util.DB; import org.compiere.util.Env; +import org.compiere.util.Msg; /** * Generate shipment for Vendor RMA. @@ -228,6 +229,7 @@ public class InOutGenerateRMA extends SvrProcess private void generateShipment(int M_RMA_ID) { MRMA rma = new MRMA(getCtx(), M_RMA_ID, get_TrxName()); + statusUpdate(Msg.getMsg(getCtx(), "Processing") + " " + rma.getDocumentInfo()); MInOut shipment = createShipment(rma); MInOutLine shipmentLines[] = createShipmentLines(rma, shipment); diff --git a/org.adempiere.base.process/src/org/adempiere/process/InvoiceGenerateRMA.java b/org.adempiere.base.process/src/org/adempiere/process/InvoiceGenerateRMA.java index 2490b57f42..bc805b4447 100644 --- a/org.adempiere.base.process/src/org/adempiere/process/InvoiceGenerateRMA.java +++ b/org.adempiere.base.process/src/org/adempiere/process/InvoiceGenerateRMA.java @@ -32,6 +32,7 @@ import org.compiere.process.ProcessInfoParameter; import org.compiere.process.SvrProcess; import org.compiere.util.DB; import org.compiere.util.Env; +import org.compiere.util.Msg; /** * Generate invoice for Vendor RMA @@ -189,6 +190,7 @@ public class InvoiceGenerateRMA extends SvrProcess private void generateInvoice(int M_RMA_ID) { MRMA rma = new MRMA(getCtx(), M_RMA_ID, get_TrxName()); + statusUpdate(Msg.getMsg(getCtx(), "Processing") + " " + rma.getDocumentInfo()); MInvoice invoice = createInvoice(rma); MInvoiceLine invoiceLines[] = createInvoiceLines(rma, invoice); diff --git a/org.adempiere.base.process/src/org/compiere/process/InOutGenerate.java b/org.adempiere.base.process/src/org/compiere/process/InOutGenerate.java index d4b5090eb4..24bf010747 100644 --- a/org.adempiere.base.process/src/org/compiere/process/InOutGenerate.java +++ b/org.adempiere.base.process/src/org/compiere/process/InOutGenerate.java @@ -34,6 +34,7 @@ import org.compiere.model.MStorage; import org.compiere.util.AdempiereUserError; import org.compiere.util.DB; import org.compiere.util.Env; +import org.compiere.util.Msg; /** * Generate Shipments. @@ -214,6 +215,8 @@ public class InOutGenerate extends SvrProcess while (rs.next ()) // Order { MOrder order = new MOrder (getCtx(), rs, get_TrxName()); + statusUpdate(Msg.getMsg(getCtx(), "Processing") + " " + order.getDocumentInfo()); + // New Header different Shipper, Shipment Location if (!p_ConsolidateDocument || (m_shipment != null diff --git a/org.adempiere.base.process/src/org/compiere/process/InvoiceGenerate.java b/org.adempiere.base.process/src/org/compiere/process/InvoiceGenerate.java index 46cf40e1c2..0577c6f696 100644 --- a/org.adempiere.base.process/src/org/compiere/process/InvoiceGenerate.java +++ b/org.adempiere.base.process/src/org/compiere/process/InvoiceGenerate.java @@ -41,6 +41,7 @@ import org.compiere.util.DB; import org.compiere.util.DisplayType; import org.compiere.util.Env; import org.compiere.util.Language; +import org.compiere.util.Msg; /** * Generate Invoices @@ -196,6 +197,7 @@ public class InvoiceGenerate extends SvrProcess while (rs.next ()) { MOrder order = new MOrder (getCtx(), rs, get_TrxName()); + statusUpdate(Msg.getMsg(getCtx(), "Processing") + " " + order.getDocumentInfo()); // New Invoice Location if (!p_ConsolidateDocument diff --git a/org.adempiere.base/src/org/adempiere/util/IProcessMonitor.java b/org.adempiere.base/src/org/adempiere/util/IProcessMonitor.java new file mode 100644 index 0000000000..b2cd750e65 --- /dev/null +++ b/org.adempiere.base/src/org/adempiere/util/IProcessMonitor.java @@ -0,0 +1,33 @@ +package org.adempiere.util; + +import org.compiere.process.ProcessInfo; + +public interface IProcessMonitor { + + /** + * Lock User Interface. + * Called from the Worker before processing + * @param pi process info + */ + public void lockUI (ProcessInfo pi); + + /** + * Unlock User Interface. + * Called from the Worker when processing is done + * @param pi process info + */ + public void unlockUI (ProcessInfo pi); + + /** + * Is the UI locked + * @return true, if UI is locked + */ + public boolean isUILocked(); + + /** + * + * @param message + */ + public void statusUpdate(String message); + +} diff --git a/org.adempiere.base/src/org/adempiere/util/ProcessUtil.java b/org.adempiere.base/src/org/adempiere/util/ProcessUtil.java index 1164944227..06543c68f9 100644 --- a/org.adempiere.base/src/org/adempiere/util/ProcessUtil.java +++ b/org.adempiere.base/src/org/adempiere/util/ProcessUtil.java @@ -134,6 +134,17 @@ public final class ProcessUtil { * @return boolean */ public static boolean startJavaProcess(Properties ctx, ProcessInfo pi, Trx trx, boolean managedTrx) { + return startJavaProcess(ctx, pi, trx, managedTrx, null); + } + + /** + * @param ctx + * @param pi + * @param trx + * @param managedTrx false if trx is managed by caller + * @return boolean + */ + public static boolean startJavaProcess(Properties ctx, ProcessInfo pi, Trx trx, boolean managedTrx, IProcessMonitor processMonitor) { String className = pi.getClassName(); if (className == null) { MProcess proc = new MProcess(ctx, pi.getAD_Process_ID(), trx.getTrxName()); @@ -196,7 +207,8 @@ public final class ProcessUtil { boolean success = false; try - { + { + process.setProcessMonitor(processMonitor); success = process.startProcess(ctx, pi, trx); if (success && trx != null && managedTrx) { diff --git a/org.adempiere.base/src/org/compiere/model/GridTab.java b/org.adempiere.base/src/org/compiere/model/GridTab.java index 9142b3cdab..a20151b254 100644 --- a/org.adempiere.base/src/org/compiere/model/GridTab.java +++ b/org.adempiere.base/src/org/compiere/model/GridTab.java @@ -207,6 +207,8 @@ public class GridTab implements DataStatusListener, Evaluatee, Serializable private DataStatusEvent m_lastDataStatusEvent; + private String m_parsedWhere; + // Context property names: public static final String CTX_KeyColumnName = "_TabInfo_KeyColumnName"; public static final String CTX_LinkColumnName = "_TabInfo_LinkColumnName"; @@ -694,6 +696,23 @@ public class GridTab implements DataStatusListener, Evaluatee, Serializable } // isDetail m_extendedWhere = where.toString(); + + if (m_extendedWhere.indexOf("@") > 1) + { + String s = Env.parseContext(Env.getCtx(), getWindowNo(), m_extendedWhere, false); + if (s != null) + { + if (!(s.equals(m_parsedWhere))) + { + refresh = false; + } + } + else + { + refresh = false; + } + m_parsedWhere = s; + } // Final Query if (m_query.isActive()) diff --git a/org.adempiere.base/src/org/compiere/model/MPayment.java b/org.adempiere.base/src/org/compiere/model/MPayment.java index 12e68dbdc0..0a38e6afc0 100644 --- a/org.adempiere.base/src/org/compiere/model/MPayment.java +++ b/org.adempiere.base/src/org/compiere/model/MPayment.java @@ -28,6 +28,7 @@ import java.util.Properties; import java.util.logging.Level; import org.adempiere.exceptions.AdempiereException; +import org.adempiere.util.IProcessMonitor; import org.compiere.process.DocAction; import org.compiere.process.DocumentEngine; import org.compiere.process.ProcessCall; @@ -1590,6 +1591,7 @@ public final class MPayment extends X_C_Payment private String m_processMsg = null; /** Just Prepared Flag */ private boolean m_justPrepared = false; + private IProcessMonitor m_processMonitor; /** * Unlock Document. @@ -2598,5 +2600,11 @@ public final class MPayment extends X_C_Payment return getWriteOffAmt(); return getPayAmt(); } // getApprovalAmt + + + @Override + public void setProcessMonitor(IProcessMonitor processMonitor) { + m_processMonitor = processMonitor; + } } // MPayment diff --git a/org.adempiere.base/src/org/compiere/model/MYear.java b/org.adempiere.base/src/org/compiere/model/MYear.java index 669f2bde71..140350baee 100644 --- a/org.adempiere.base/src/org/compiere/model/MYear.java +++ b/org.adempiere.base/src/org/compiere/model/MYear.java @@ -27,6 +27,7 @@ import java.util.StringTokenizer; import java.util.logging.Level; import org.adempiere.exceptions.FillMandatoryException; +import org.adempiere.util.IProcessMonitor; import org.compiere.process.SvrProcess; import org.compiere.util.Env; import org.compiere.util.Language; @@ -232,6 +233,7 @@ public class MYear extends X_C_Year cal.set(Calendar.MILLISECOND, 0); // + IProcessMonitor processMonitor = Env.getProcessMonitor(getCtx()); for (int month = 0; month < 12; month++) { @@ -255,6 +257,10 @@ public class MYear extends X_C_Year period.setStartDate(start); period.setEndDate(end); } + if (processMonitor != null) + { + processMonitor.statusUpdate(period.toString()); + } period.saveEx(get_TrxName()); // Creates Period Control // get first day of next month cal.add(Calendar.DAY_OF_YEAR, 1); diff --git a/org.adempiere.base/src/org/compiere/process/ProcessCall.java b/org.adempiere.base/src/org/compiere/process/ProcessCall.java index fb377bd6f0..cddeaf08fd 100644 --- a/org.adempiere.base/src/org/compiere/process/ProcessCall.java +++ b/org.adempiere.base/src/org/compiere/process/ProcessCall.java @@ -18,6 +18,7 @@ package org.compiere.process; import java.util.Properties; +import org.adempiere.util.IProcessMonitor; import org.compiere.util.Trx; /** @@ -45,4 +46,9 @@ public interface ProcessCall */ public boolean startProcess (Properties ctx, ProcessInfo pi, Trx trx); + /** + * @param processMonitor + */ + public void setProcessMonitor(IProcessMonitor processMonitor); + } // ProcessCall diff --git a/org.adempiere.base/src/org/compiere/process/SvrProcess.java b/org.adempiere.base/src/org/compiere/process/SvrProcess.java index eafcc99f81..a3ec472311 100644 --- a/org.adempiere.base/src/org/compiere/process/SvrProcess.java +++ b/org.adempiere.base/src/org/compiere/process/SvrProcess.java @@ -25,9 +25,9 @@ import java.sql.Timestamp; import java.util.Properties; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; import org.compiere.model.MPInstance; import org.compiere.model.PO; -import org.compiere.util.CLogMgt; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.Env; @@ -51,6 +51,9 @@ import org.compiere.util.Trx; */ public abstract class SvrProcess implements ProcessCall { + public static final String PROCESS_INFO_CTX_KEY = "ProcessInfo"; + public static final String PROCESS_MONITOR_CTX_KEY = "ProcessMonitor"; + /** * Server Process. * Note that the class is initiated by startProcess. @@ -72,6 +75,7 @@ public abstract class SvrProcess implements ProcessCall private PO m_lockedObject = null; /** Process Main transaction */ private Trx m_trx; + private IProcessMonitor processMonitor; /** Common Error Message */ protected static String MSG_SaveErrorRowNotFound = "@SaveErrorRowNotFound@"; @@ -102,32 +106,43 @@ public abstract class SvrProcess implements ProcessCall // lock(); - boolean success = process(); - // - if (localTrx) + boolean success = false; + + try { - if (success) - { - try - { - m_trx.commit(true); - } catch (Exception e) - { - log.log(Level.SEVERE, "Commit failed.", e); - m_pi.addSummary("Commit Failed."); - m_pi.setError(true); - } - } - else - m_trx.rollback(); - m_trx.close(); - m_trx = null; + m_ctx.put(PROCESS_INFO_CTX_KEY, m_pi); + m_ctx.put(PROCESS_MONITOR_CTX_KEY, processMonitor); + success = process(); } + finally + { + m_ctx.remove(PROCESS_INFO_CTX_KEY); + m_ctx.remove(PROCESS_MONITOR_CTX_KEY); + if (localTrx) + { + if (success) + { + try + { + m_trx.commit(true); + } catch (Exception e) + { + log.log(Level.SEVERE, "Commit failed.", e); + m_pi.addSummary("Commit Failed."); + m_pi.setError(true); + } + } + else + m_trx.rollback(); + m_trx.close(); + m_trx = null; + } - unlock(); - - // outside transaction processing [ teo_sarca, 1646891 ] - postProcess(!m_pi.isError()); + unlock(); + + // outside transaction processing [ teo_sarca, 1646891 ] + postProcess(!m_pi.isError()); + } return !m_pi.isError(); } // startProcess @@ -518,5 +533,22 @@ public abstract class SvrProcess implements ProcessCall return m_trx.getTrxName(); return null; } // get_TrxName + + @Override + public void setProcessMonitor(IProcessMonitor monitor) + { + processMonitor = monitor; + } + /** + * publish status update message + * @param message + */ + protected void statusUpdate(String message) + { + if (processMonitor != null) + { + processMonitor.statusUpdate(message); + } + } } // SvrProcess diff --git a/org.adempiere.base/src/org/compiere/util/ASyncProcess.java b/org.adempiere.base/src/org/compiere/util/ASyncProcess.java index d637300df0..601d44daa3 100644 --- a/org.adempiere.base/src/org/compiere/util/ASyncProcess.java +++ b/org.adempiere.base/src/org/compiere/util/ASyncProcess.java @@ -16,6 +16,7 @@ *****************************************************************************/ package org.compiere.util; +import org.adempiere.util.IProcessMonitor; import org.compiere.process.ProcessInfo; /** @@ -35,29 +36,10 @@ import org.compiere.process.ProcessInfo; * * @author Jorg Janke * @version $Id: ASyncProcess.java,v 1.2 2006/07/30 00:51:05 jjanke Exp $ + * @deprecated */ -public interface ASyncProcess +public interface ASyncProcess extends IProcessMonitor { - /** - * Lock User Interface. - * Called from the Worker before processing - * @param pi process info - */ - public void lockUI (ProcessInfo pi); - - /** - * Unlock User Interface. - * Called from the Worker when processing is done - * @param pi result of execute ASync call - */ - public void unlockUI (ProcessInfo pi); - - /** - * Is the UI locked (Internal method) - * @return true, if UI is locked - */ - boolean isUILocked(); - /** * Method to be executed async. * Called from the Worker diff --git a/org.adempiere.base/src/org/compiere/util/Env.java b/org.adempiere.base/src/org/compiere/util/Env.java index a17a113a66..0f23cd44b8 100644 --- a/org.adempiere.base/src/org/compiere/util/Env.java +++ b/org.adempiere.base/src/org/compiere/util/Env.java @@ -47,6 +47,7 @@ import javax.swing.JFrame; import org.adempiere.base.Core; import org.adempiere.base.IResourceFinder; +import org.adempiere.util.IProcessMonitor; import org.adempiere.util.ServerContextProvider; import org.compiere.db.CConnection; import org.compiere.model.GridWindowVO; @@ -55,6 +56,8 @@ import org.compiere.model.MLookupCache; import org.compiere.model.MRole; import org.compiere.model.MSession; import org.compiere.model.PO; +import org.compiere.process.ProcessInfo; +import org.compiere.process.SvrProcess; /** * System Environment and static variables. @@ -1691,6 +1694,17 @@ public final class Env return mWindowVO; } // getWindow + //Current Process + public static IProcessMonitor getProcessMonitor(Properties ctx) + { + return (IProcessMonitor) ctx.get(SvrProcess.PROCESS_MONITOR_CTX_KEY); + } + + public static ProcessInfo getProcessInfo(Properties ctx) + { + return (ProcessInfo) ctx.get(SvrProcess.PROCESS_INFO_CTX_KEY); + } + /************************************************************************** * Static Variables */ diff --git a/org.adempiere.report.jasper/src/org/compiere/report/ReportStarter.java b/org.adempiere.report.jasper/src/org/compiere/report/ReportStarter.java index 4516461709..350faaf993 100644 --- a/org.adempiere.report.jasper/src/org/compiere/report/ReportStarter.java +++ b/org.adempiere.report.jasper/src/org/compiere/report/ReportStarter.java @@ -64,6 +64,7 @@ import net.sf.jasperreports.engine.util.JRSwapFile; import org.adempiere.base.Service; import org.adempiere.exceptions.AdempiereException; import org.adempiere.exceptions.DBException; +import org.adempiere.util.IProcessMonitor; import org.compiere.model.MAttachment; import org.compiere.model.MAttachmentEntry; import org.compiere.model.MProcess; @@ -118,6 +119,7 @@ public class ReportStarter implements ProcessCall, ClientProcess private ProcessInfo processInfo; private MAttachment attachment; + private IProcessMonitor m_processMonitor; /** * @author rlemeill @@ -1195,4 +1197,9 @@ public class ReportStarter implements ProcessCall, ClientProcess } } + @Override + public void setProcessMonitor(IProcessMonitor processMonitor) { + m_processMonitor = processMonitor; + } + } \ No newline at end of file diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/APanel.java b/org.adempiere.ui.swing/src/org/compiere/apps/APanel.java index d95c7b6fb3..33093ca3d4 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/APanel.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/APanel.java @@ -59,6 +59,7 @@ import javax.swing.SwingUtilities; import javax.swing.event.ChangeEvent; import javax.swing.event.ChangeListener; +import org.adempiere.util.IProcessMonitor; import org.compiere.apps.form.FormFrame; import org.compiere.apps.search.Find; import org.compiere.grid.APanelTab; @@ -94,7 +95,6 @@ import org.compiere.process.DocAction; import org.compiere.process.ProcessInfo; import org.compiere.process.ProcessInfoUtil; import org.compiere.swing.CPanel; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogMgt; import org.compiere.util.CLogger; import org.compiere.util.DB; @@ -141,7 +141,7 @@ import org.compiere.util.Util; * @sponsor www.metas.de */ public final class APanel extends CPanel - implements DataStatusListener, ChangeListener, ActionListener, ASyncProcess + implements DataStatusListener, ChangeListener, ActionListener, IProcessMonitor { /** * @@ -2894,4 +2894,13 @@ public final class APanel extends CPanel public JTabbedPane getCurrentTabbedPane() { return m_curWinTab; } + + @Override + public void statusUpdate(String message) { + JFrame frame = AEnv.getFrame(this); + if (frame == null) // during init + return; + if (frame instanceof AWindow) + ((AWindow)frame).setBusyMessage(message); + } } // APanel diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/ClientProcessCtrl.java b/org.adempiere.ui.swing/src/org/compiere/apps/ClientProcessCtrl.java index 8f39202729..a973d17657 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/ClientProcessCtrl.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/ClientProcessCtrl.java @@ -2,9 +2,9 @@ package org.compiere.apps; import java.awt.Container; +import org.adempiere.util.IProcessMonitor; import org.compiere.model.MPInstance; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; import org.compiere.util.Msg; @@ -34,7 +34,7 @@ public class ClientProcessCtrl { * @param trx Transaction * @return worker started ProcessCtl instance or null for workflow */ - public static ProcessCtl process (ASyncProcess parent, int WindowNo, ProcessInfo pi, Trx trx) + public static ProcessCtl process (IProcessMonitor parent, int WindowNo, ProcessInfo pi, Trx trx) { log.fine("WindowNo=" + WindowNo + " - " + pi); diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessCtl.java b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessCtl.java index bf782f3f33..f769545b60 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessCtl.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessCtl.java @@ -21,9 +21,9 @@ import java.awt.Container; import javax.swing.JFrame; import javax.swing.SwingUtilities; +import org.adempiere.util.IProcessMonitor; import org.compiere.model.MPInstance; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; import org.compiere.util.Msg; @@ -64,7 +64,7 @@ public class ProcessCtl extends AbstractProcessCtl * @param trx Transaction * @return worker started ProcessCtl instance or null for workflow */ - public static ProcessCtl process (ASyncProcess parent, int WindowNo, ProcessInfo pi, Trx trx) + public static ProcessCtl process (IProcessMonitor parent, int WindowNo, ProcessInfo pi, Trx trx) { log.fine("WindowNo=" + WindowNo + " - " + pi); @@ -142,7 +142,7 @@ public class ProcessCtl extends AbstractProcessCtl * @param trx Transaction * @return worker started ProcessCtl instance or null for workflow */ - public static ProcessCtl process(ASyncProcess parent, int WindowNo, IProcessParameter parameter, ProcessInfo pi, Trx trx) + public static ProcessCtl process(IProcessMonitor parent, int WindowNo, IProcessParameter parameter, ProcessInfo pi, Trx trx) { log.fine("WindowNo=" + WindowNo + " - " + pi); @@ -206,7 +206,7 @@ public class ProcessCtl extends AbstractProcessCtl * @param trx Transaction * Created in process(), VInvoiceGen.generateInvoices */ - public ProcessCtl (ASyncProcess parent, int WindowNo, ProcessInfo pi, Trx trx) + public ProcessCtl (IProcessMonitor parent, int WindowNo, ProcessInfo pi, Trx trx) { super(parent, WindowNo, pi, trx); } // ProcessCtl @@ -223,12 +223,12 @@ public class ProcessCtl extends AbstractProcessCtl { // log.info("..."); //m_parent is null for synchrous execution - if (getParent() != null) + if (getProcessMonitor() != null) { - if (getParent() instanceof Container) + if (getProcessMonitor() instanceof Container) { //swing client - JFrame frame = AEnv.getFrame((Container)getParent()); + JFrame frame = AEnv.getFrame((Container)getProcessMonitor()); if (frame instanceof AWindow) ((AWindow)frame).setBusyTimer(getProcessInfo().getEstSeconds()); else @@ -247,7 +247,7 @@ public class ProcessCtl extends AbstractProcessCtl parent.lockUI(pi); } }; - runnable.setParent(getParent()); + runnable.setParent(getProcessMonitor()); runnable.setProcessInfo(getProcessInfo()); SwingUtilities.invokeLater(runnable); } @@ -255,7 +255,7 @@ public class ProcessCtl extends AbstractProcessCtl { //other client log.finer("lock"); - getParent().lockUI(getProcessInfo()); + getProcessMonitor().lockUI(getProcessInfo()); } } } // lock @@ -317,14 +317,14 @@ public class ProcessCtl extends AbstractProcessCtl abstract class ProcessUpdateRunnable implements Runnable { protected ProcessInfo pi = null; - protected ASyncProcess parent = null; + protected IProcessMonitor parent = null; public void setProcessInfo(ProcessInfo pi) { this.pi = pi; } - public void setParent(ASyncProcess parent) + public void setParent(IProcessMonitor parent) { this.parent = parent; } diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessDialog.java b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessDialog.java index 946032a84c..db0aec7bd5 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessDialog.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessDialog.java @@ -36,6 +36,7 @@ import javax.swing.JSeparator; import org.adempiere.exceptions.AdempiereException; import org.adempiere.exceptions.DBException; +import org.adempiere.util.IProcessMonitor; import org.compiere.print.ReportCtl; import org.compiere.print.ReportEngine; import org.compiere.process.ProcessInfo; @@ -43,7 +44,6 @@ import org.compiere.process.ProcessInfoUtil; import org.compiere.swing.CButton; import org.compiere.swing.CFrame; import org.compiere.swing.CPanel; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.Env; @@ -67,7 +67,7 @@ import org.compiere.util.Msg; *
  • BF [ 1963128 ] Running a process w/o trl should display an error */ public class ProcessDialog extends CFrame - implements ActionListener, ASyncProcess + implements ActionListener, IProcessMonitor { /** * @@ -516,4 +516,9 @@ public class ProcessDialog extends CFrame PrintScreenPainter.printScreen (this); } // printScreen + @Override + public void statusUpdate(String status) { + message.setText(status); + } + } // ProcessDialog diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessModalDialog.java b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessModalDialog.java index 58099bb87d..cb23ee749e 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/ProcessModalDialog.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/ProcessModalDialog.java @@ -32,11 +32,11 @@ import javax.swing.JScrollPane; import javax.swing.JSeparator; import org.adempiere.exceptions.DBException; +import org.adempiere.util.IProcessMonitor; import org.compiere.process.ProcessInfo; import org.compiere.swing.CButton; import org.compiere.swing.CDialog; import org.compiere.swing.CPanel; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.Env; @@ -76,13 +76,13 @@ public class ProcessModalDialog extends CDialog * @param autoStart */ public ProcessModalDialog (Properties ctx, Frame parent, String title, - ASyncProcess aProcess, int WindowNo, int AD_Process_ID, + IProcessMonitor aProcess, int WindowNo, int AD_Process_ID, int tableId, int recordId, boolean autoStart) { super(parent, title, true); log.info("Process=" + AD_Process_ID ); m_ctx = ctx; - m_ASyncProcess = aProcess; + m_processMonitor = aProcess; m_WindowNo = WindowNo; m_AD_Process_ID = AD_Process_ID; m_tableId = tableId; @@ -99,7 +99,7 @@ public class ProcessModalDialog extends CDialog } } // ProcessDialog - private ASyncProcess m_ASyncProcess; + private IProcessMonitor m_processMonitor; private int m_WindowNo; private Properties m_ctx; private int m_tableId; @@ -332,7 +332,7 @@ public class ProcessModalDialog extends CDialog { if (e.getSource() == bOK) { - ProcessCtl.process(m_ASyncProcess, m_WindowNo, parameterPanel, m_pi, null); + ProcessCtl.process(m_processMonitor, m_WindowNo, parameterPanel, m_pi, null); dispose(); } diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/form/VGenPanel.java b/org.adempiere.ui.swing/src/org/compiere/apps/form/VGenPanel.java index 34df10603d..9ba016a7f7 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/form/VGenPanel.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/form/VGenPanel.java @@ -28,6 +28,7 @@ import javax.swing.event.TableModelEvent; import javax.swing.event.TableModelListener; import org.adempiere.plaf.AdempierePLAF; +import org.adempiere.util.IProcessMonitor; import org.compiere.apps.ADialog; import org.compiere.apps.ADialogDialog; import org.compiere.apps.AEnv; @@ -49,7 +50,6 @@ import org.compiere.process.ProcessInfoUtil; import org.compiere.swing.CPanel; import org.compiere.swing.CTabbedPane; import org.compiere.swing.CTextPane; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; import org.compiere.util.Msg; @@ -58,7 +58,7 @@ import org.compiere.util.Msg; * Generate custom form panel * */ -public class VGenPanel extends CPanel implements ActionListener, ChangeListener, TableModelListener, ASyncProcess +public class VGenPanel extends CPanel implements ActionListener, ChangeListener, TableModelListener, IProcessMonitor { /** * @@ -380,4 +380,9 @@ public class VGenPanel extends CPanel implements ActionListener, ChangeListener, { return statusBar; } + + @Override + public void statusUpdate(String message) { + statusBar.setStatusLine(message); + } } \ No newline at end of file diff --git a/org.adempiere.ui.swing/src/org/compiere/apps/form/VPaySelect.java b/org.adempiere.ui.swing/src/org/compiere/apps/form/VPaySelect.java index cc91f14034..f687b86725 100644 --- a/org.adempiere.ui.swing/src/org/compiere/apps/form/VPaySelect.java +++ b/org.adempiere.ui.swing/src/org/compiere/apps/form/VPaySelect.java @@ -35,6 +35,7 @@ import javax.swing.JScrollPane; import javax.swing.event.TableModelEvent; import javax.swing.event.TableModelListener; +import org.adempiere.util.IProcessMonitor; import org.compiere.apps.ADialog; import org.compiere.apps.AEnv; import org.compiere.apps.ConfirmPanel; @@ -50,7 +51,6 @@ import org.compiere.plaf.CompiereColor; import org.compiere.process.ProcessInfo; import org.compiere.swing.CLabel; import org.compiere.swing.CPanel; -import org.compiere.util.ASyncProcess; import org.compiere.util.Env; import org.compiere.util.KeyNamePair; import org.compiere.util.Msg; @@ -65,7 +65,7 @@ import org.compiere.util.ValueNamePair; * @author Jorg Janke * @version $Id: VPaySelect.java,v 1.2 2008/07/11 08:20:12 cruiz Exp $ */ -public class VPaySelect extends PaySelect implements FormPanel, ActionListener, TableModelListener, ASyncProcess +public class VPaySelect extends PaySelect implements FormPanel, ActionListener, TableModelListener, IProcessMonitor { /** @todo withholding */ private CPanel panel = new CPanel(); @@ -438,4 +438,9 @@ public class VPaySelect extends PaySelect implements FormPanel, ActionListener, { log.config("-"); } // executeASync + + @Override + public void statusUpdate(String message) { + dataStatus.setText(message); + } } // VPaySelect diff --git a/org.adempiere.ui.swing/src/org/compiere/print/AReport.java b/org.adempiere.ui.swing/src/org/compiere/print/AReport.java index e74de89c5b..141774f626 100644 --- a/org.adempiere.ui.swing/src/org/compiere/print/AReport.java +++ b/org.adempiere.ui.swing/src/org/compiere/print/AReport.java @@ -27,6 +27,7 @@ import javax.sql.RowSet; import javax.swing.JComponent; import javax.swing.JPopupMenu; +import org.adempiere.util.IProcessMonitor; import org.compiere.apps.ADialog; import org.compiere.apps.ClientProcessCtrl; import org.compiere.apps.ProcessCtl; @@ -35,7 +36,6 @@ import org.compiere.model.MRole; import org.compiere.model.MTable; import org.compiere.model.PrintInfo; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; import org.compiere.util.KeyNamePair; @@ -73,7 +73,7 @@ public class AReport implements ActionListener * @param parent The invoking parent window * @param WindowNo The invoking parent window number */ - public AReport (int AD_Table_ID, JComponent invoker, MQuery query, ASyncProcess parent, int WindowNo) + public AReport (int AD_Table_ID, JComponent invoker, MQuery query, IProcessMonitor parent, int WindowNo) { log.config("AD_Table_ID=" + AD_Table_ID + " " + query); if (!MRole.getDefault().isCanReport(AD_Table_ID)) @@ -100,7 +100,7 @@ public class AReport implements ActionListener * @param whereExtended The filtering where clause * @param WindowNo The invoking parent window number */ - public AReport (int AD_Table_ID, JComponent invoker, MQuery query, ASyncProcess parent, int WindowNo, String whereExtended) + public AReport (int AD_Table_ID, JComponent invoker, MQuery query, IProcessMonitor parent, int WindowNo, String whereExtended) { log.config("AD_Table_ID=" + AD_Table_ID + " " + query); if (!MRole.getDefault().isCanReport(AD_Table_ID)) @@ -129,7 +129,7 @@ public class AReport implements ActionListener /** Logger */ private static CLogger log = CLogger.getCLogger(AReport.class); /** The parent window for locking/unlocking during process execution */ - ASyncProcess parent; + IProcessMonitor parent; /** The filter to apply to this report */ String m_whereExtended; /** The parent window number */ diff --git a/org.adempiere.ui.swing/src/org/eevolution/form/VInOutInvoiceGen.java b/org.adempiere.ui.swing/src/org/eevolution/form/VInOutInvoiceGen.java index d07c7f0666..2444d4cc0f 100755 --- a/org.adempiere.ui.swing/src/org/eevolution/form/VInOutInvoiceGen.java +++ b/org.adempiere.ui.swing/src/org/eevolution/form/VInOutInvoiceGen.java @@ -38,6 +38,7 @@ import javax.swing.event.TableModelEvent; import javax.swing.event.TableModelListener; import org.adempiere.plaf.AdempierePLAF; +import org.adempiere.util.IProcessMonitor; import org.compiere.apps.ADialog; import org.compiere.apps.ADialogDialog; import org.compiere.apps.AEnv; @@ -66,7 +67,6 @@ import org.compiere.swing.CLabel; import org.compiere.swing.CPanel; import org.compiere.swing.CTabbedPane; import org.compiere.swing.CTextPane; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.DisplayType; @@ -83,7 +83,7 @@ import org.compiere.util.Trx; */ public class VInOutInvoiceGen extends CPanel implements FormPanel, ActionListener, VetoableChangeListener, - ChangeListener, TableModelListener, ASyncProcess + ChangeListener, TableModelListener, IProcessMonitor { /** * @@ -895,4 +895,9 @@ public class VInOutInvoiceGen extends CPanel public void executeASync (ProcessInfo pi) { } // executeASync + + @Override + public void statusUpdate(String message) { + statusBar.setStatusLine(message); + } } // VInOutGen diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/AdempiereWebUI.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/AdempiereWebUI.java index 1e095a7ea3..d133b9624e 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/AdempiereWebUI.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/AdempiereWebUI.java @@ -249,6 +249,7 @@ public class AdempiereWebUI extends Window implements EventListener, IWebClient } currSess.setAttribute(ZK_DESKTOP_SESSION_KEY, this.getPage().getDesktop()); + ctx.put(ZK_DESKTOP_SESSION_KEY, this.getPage().getDesktop()); } catch (Throwable t) { //restore fail appDesktop = null; @@ -267,6 +268,7 @@ public class AdempiereWebUI extends Window implements EventListener, IWebClient ExecutionCarryOver eco = new ExecutionCarryOver(this.getPage().getDesktop()); currSess.setAttribute(EXECUTION_CARRYOVER_SESSION_KEY, eco); currSess.setAttribute(ZK_DESKTOP_SESSION_KEY, this.getPage().getDesktop()); + ctx.put(ZK_DESKTOP_SESSION_KEY, this.getPage().getDesktop()); } if ("Y".equalsIgnoreCase(Env.getContext(ctx, BrowserToken.REMEMBER_ME)) && MSystem.isZKRememberUserAllowed()) diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/AEnv.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/AEnv.java index e5136ed11b..38908a50fe 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/AEnv.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/AEnv.java @@ -36,6 +36,7 @@ import java.util.logging.Level; import javax.servlet.ServletRequest; +import org.adempiere.webui.AdempiereWebUI; import org.adempiere.webui.component.Window; import org.adempiere.webui.session.SessionManager; import org.adempiere.webui.theme.ThemeManager; @@ -55,6 +56,7 @@ import org.compiere.util.Ini; import org.compiere.util.Language; import org.zkoss.web.servlet.Servlets; import org.zkoss.zk.ui.Component; +import org.zkoss.zk.ui.Desktop; import org.zkoss.zk.ui.Execution; import org.zkoss.zk.ui.Executions; @@ -739,4 +741,35 @@ public final class AEnv header = ThemeManager.getBrowserTitle(); return header; } + + /** + * Execute task that required access to the zk desktop + * @param runnable + */ + public static void executeDesktopTask(Runnable runnable) { + boolean inUIThread = Executions.getCurrent() != null; + boolean desktopActivated = false; + + Desktop desktop = null; + try { + if (!inUIThread) { + desktop = (Desktop) Env.getCtx().get(AdempiereWebUI.ZK_DESKTOP_SESSION_KEY); + if (desktop == null) + return; + //1 second timeout + if (Executions.activate(desktop, 1000)) { + desktopActivated = true; + } else { + return; + } + } + runnable.run(); + } catch (Exception e) { + throw new RuntimeException(e.getLocalizedMessage(), e); + } finally { + if (!inUIThread && desktopActivated) { + Executions.deactivate(desktop); + } + } + } } // AEnv diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/BusyDialog.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/BusyDialog.java index 7830657135..ebe5f826cf 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/BusyDialog.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/BusyDialog.java @@ -28,13 +28,15 @@ import org.zkoss.zul.Image; public class BusyDialog extends Window { private static final long serialVersionUID = -779475945298887887L; + private Label label; public BusyDialog() { super(); Hbox box = new Hbox(); box.setStyle("padding: 5px"); appendChild(box); - box.appendChild(new Label(Msg.getMsg(Env.getCtx(), "Processing"))); + label = new Label(Msg.getMsg(Env.getCtx(), "Processing")); + box.appendChild(label); Image image = new Image(); box.appendChild(image); image.setHeight("16px"); @@ -44,4 +46,10 @@ public class BusyDialog extends Window { setShadow(true); } + public void statusUpdate(String message) { + if (label != null) { + label.setText(message); + this.invalidate(); + } + } } diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessDialog.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessDialog.java index 08759f89be..c4239742b7 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessDialog.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessDialog.java @@ -11,6 +11,10 @@ import java.util.List; import java.util.Properties; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; +import org.adempiere.util.ServerContext; +import org.adempiere.webui.AdempiereWebUI; +import org.adempiere.webui.apps.ProcessDialog.ProcessDialogRunnable; import org.adempiere.webui.component.Button; import org.adempiere.webui.component.Panel; import org.adempiere.webui.component.Window; @@ -28,6 +32,9 @@ import org.compiere.util.Env; import org.compiere.util.Msg; import org.zkoss.zk.au.out.AuEcho; import org.zkoss.zk.ui.Component; +import org.zkoss.zk.ui.Desktop; +import org.zkoss.zk.ui.Execution; +import org.zkoss.zk.ui.Executions; import org.zkoss.zk.ui.event.Event; import org.zkoss.zk.ui.event.EventListener; import org.zkoss.zk.ui.event.Events; @@ -73,7 +80,7 @@ import com.lowagie.text.pdf.PdfWriter; * @author arboleda - globalqss * - Implement ShowHelp option on processes and reports */ -public class ProcessDialog extends Window implements EventListener//, ASyncProcess +public class ProcessDialog extends Window implements EventListener, IProcessMonitor { /** * generate serial version ID @@ -192,6 +199,9 @@ public class ProcessDialog extends Window implements EventListener//, ASyncProce private boolean isParameterPage = true; private String initialMessage; private BusyDialog progressWindow; + private Thread thread; + private String statusUpdate; + private ProcessDialogRunnable processDialogRunnable; /** @@ -307,9 +317,48 @@ public class ProcessDialog extends Window implements EventListener//, ASyncProce } public void runProcess() { + //prepare context for background thread + Properties p = new Properties(); + Properties env = Env.getCtx(); + for(Object key : env.keySet()) { + if (key instanceof String) { + String sKey = (String) key; + Object value = env.get(sKey); + if (value instanceof String) { + String sValue = (String) value; + p.put(sKey, sValue); + } + } + } + Desktop desktop = this.getDesktop(); + p.put(AdempiereWebUI.ZK_DESKTOP_SESSION_KEY, desktop); + + processDialogRunnable = new ProcessDialogRunnable(p); + thread = new Thread(processDialogRunnable); + thread.start(); + + Clients.response(new AuEcho(this, "checkProgress", null)); + } + + public void checkProgress() { try { - WProcessCtl.process(null, m_WindowNo, parameterPanel, m_pi, null); - } finally { + Thread.sleep(500); + } catch (InterruptedException e) { + Thread.interrupted(); + } + if (thread.isAlive()) { + synchronized(this) { + if (statusUpdate != null) { + if (progressWindow != null) + progressWindow.statusUpdate(statusUpdate); + statusUpdate = null; + } + } + Clients.response(new AuEcho(this, "checkProgress", null)); + } else { + Env.getCtx().putAll(processDialogRunnable.getProperties()); + thread = null; + processDialogRunnable = null; unlockUI(m_pi); } } @@ -334,7 +383,7 @@ public class ProcessDialog extends Window implements EventListener//, ASyncProce } public void lockUI(ProcessInfo pi) { - if (m_isLocked) return; + if (m_isLocked || Executions.getCurrent() == null) return; m_isLocked = true; @@ -348,7 +397,7 @@ public class ProcessDialog extends Window implements EventListener//, ASyncProce } public void unlockUI(ProcessInfo pi) { - if (!m_isLocked) return; + if (!m_isLocked || Executions.getCurrent() == null) return; m_isLocked = false; hideBusyDialog(); @@ -591,10 +640,34 @@ public class ProcessDialog extends Window implements EventListener//, ASyncProce return valid; } - public void executeASync(ProcessInfo pi) { - } - public boolean isUILocked() { return m_isLocked; } + + class ProcessDialogRunnable implements Runnable { + private Properties properties; + + ProcessDialogRunnable(Properties properties) { + this.properties = properties; + } + + public void run() { + try { + ServerContext.setCurrentInstance(properties); + log.log(Level.INFO, "Process Info="+m_pi+" AD_Client_ID="+Env.getAD_Client_ID(Env.getCtx())); + WProcessCtl.process(ProcessDialog.this, m_WindowNo, parameterPanel, m_pi, null); + } finally { + ServerContext.dispose(); + } + } + + protected Properties getProperties() { + return properties; + } + } + + @Override + public void statusUpdate(String message) { + statusUpdate = message; + } } // ProcessDialog diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessModalDialog.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessModalDialog.java index 3ddabef27b..11c1fe2c3e 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessModalDialog.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/ProcessModalDialog.java @@ -22,19 +22,23 @@ import java.sql.SQLException; import java.util.Properties; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; +import org.adempiere.util.ServerContext; +import org.adempiere.webui.AdempiereWebUI; import org.adempiere.webui.LayoutUtils; import org.adempiere.webui.component.Button; import org.adempiere.webui.component.Panel; import org.adempiere.webui.component.VerticalBox; import org.adempiere.webui.component.Window; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.Env; import org.compiere.util.Msg; import org.zkoss.zk.au.out.AuEcho; import org.zkoss.zk.ui.Component; +import org.zkoss.zk.ui.Desktop; +import org.zkoss.zk.ui.Executions; import org.zkoss.zk.ui.event.Event; import org.zkoss.zk.ui.event.EventListener; import org.zkoss.zk.ui.event.Events; @@ -54,7 +58,7 @@ import org.zkoss.zul.Html; * @author arboleda - globalqss * - Implement ShowHelp option on processes and reports */ -public class ProcessModalDialog extends Window implements EventListener +public class ProcessModalDialog extends Window implements EventListener, IProcessMonitor { /** * generated serial version ID @@ -69,10 +73,10 @@ public class ProcessModalDialog extends Window implements EventListener * @param pi * @param autoStart */ - public ProcessModalDialog(ASyncProcess aProcess, int WindowNo, ProcessInfo pi, boolean autoStart) + public ProcessModalDialog(IProcessMonitor aProcess, int WindowNo, ProcessInfo pi, boolean autoStart) { m_ctx = Env.getCtx(); - m_ASyncProcess = aProcess; + m_processMonitor = aProcess; m_WindowNo = WindowNo; m_pi = pi; m_autoStart = autoStart; @@ -99,7 +103,7 @@ public class ProcessModalDialog extends Window implements EventListener * @param recordId * @param autoStart */ - public ProcessModalDialog ( ASyncProcess aProcess, int WindowNo, int AD_Process_ID, int tableId, int recordId, boolean autoStart) + public ProcessModalDialog ( IProcessMonitor aProcess, int WindowNo, int AD_Process_ID, int tableId, int recordId, boolean autoStart) { this(aProcess, WindowNo, new ProcessInfo("", AD_Process_ID, tableId, recordId), autoStart); } @@ -118,7 +122,7 @@ public class ProcessModalDialog extends Window implements EventListener * @deprecated */ public ProcessModalDialog (Window parent, String title, - ASyncProcess aProcess, int WindowNo, int AD_Process_ID, + IProcessMonitor aProcess, int WindowNo, int AD_Process_ID, int tableId, int recordId, boolean autoStart) { this(aProcess, WindowNo, AD_Process_ID, tableId, recordId, autoStart); @@ -155,7 +159,7 @@ public class ProcessModalDialog extends Window implements EventListener } - private ASyncProcess m_ASyncProcess; + private IProcessMonitor m_processMonitor; private int m_WindowNo; private Properties m_ctx; private String m_Name = null; @@ -173,6 +177,10 @@ public class ProcessModalDialog extends Window implements EventListener private ProcessInfo m_pi = null; private BusyDialog progressWindow; + private boolean isLocked = false; + private org.adempiere.webui.apps.ProcessModalDialog.ProcessDialogRunnable processDialogRunnable; + private Thread thread; + private String statusUpdate; /** * Set Visible @@ -299,12 +307,12 @@ public class ProcessModalDialog extends Window implements EventListener { m_pi.setPrintPreview(true); - if (m_ASyncProcess != null) { - m_ASyncProcess.lockUI(m_pi); + if (m_processMonitor != null) { + m_processMonitor.lockUI(m_pi); Clients.showBusy(null, false); } - showBusyDialog(); + lockUI(m_pi); //use echo, otherwise lock ui wouldn't work Clients.response(new AuEcho(this, "runProcess", null)); @@ -322,15 +330,54 @@ public class ProcessModalDialog extends Window implements EventListener /** * internal use, don't call this directly */ - public void runProcess() { - try { - WProcessCtl.process(null, m_WindowNo, parameterPanel, m_pi, null); - } finally { - dispose(); - if (m_ASyncProcess != null) { - m_ASyncProcess.unlockUI(m_pi); + public void runProcess() { + //prepare context for background thread + Properties p = new Properties(); + Properties env = Env.getCtx(); + for(Object key : env.keySet()) { + if (key instanceof String) { + String sKey = (String) key; + Object value = env.get(sKey); + if (value instanceof String) { + String sValue = (String) value; + p.put(sKey, sValue); + } } - hideBusyDialog(); + } + Desktop desktop = this.getDesktop(); + p.put(AdempiereWebUI.ZK_DESKTOP_SESSION_KEY, desktop); + + processDialogRunnable = new ProcessDialogRunnable(p); + thread = new Thread(processDialogRunnable); + thread.start(); + + Clients.response(new AuEcho(this, "checkProgress", null)); + } + + public void checkProgress() { + try { + Thread.sleep(500); + } catch (InterruptedException e) { + Thread.interrupted(); + } + if (thread.isAlive()) { + synchronized(this) { + if (statusUpdate != null) { + if (progressWindow != null) + progressWindow.statusUpdate(statusUpdate); + statusUpdate = null; + } + } + Clients.response(new AuEcho(this, "checkProgress", null)); + } else { + Env.getCtx().putAll(processDialogRunnable.getProperties()); + thread = null; + processDialogRunnable = null; + dispose(); + if (m_processMonitor != null) { + m_processMonitor.unlockUI(m_pi); + } + unlockUI(m_pi); } } @@ -356,4 +403,53 @@ public class ProcessModalDialog extends Window implements EventListener } } + @Override + public void lockUI(ProcessInfo pi) { + if (isLocked || Executions.getCurrent() == null) + return; + + showBusyDialog(); + isLocked = true; + } + + @Override + public void unlockUI(ProcessInfo pi) { + if (!isLocked || Executions.getCurrent() == null) + return; + + hideBusyDialog(); + isLocked = false; + } + + @Override + public boolean isUILocked() { + return isLocked; + } + + @Override + public void statusUpdate(String message) { + statusUpdate = message; + } + + class ProcessDialogRunnable implements Runnable { + private Properties properties; + + ProcessDialogRunnable(Properties properties) { + this.properties = properties; + } + + public void run() { + try { + ServerContext.setCurrentInstance(properties); + log.log(Level.INFO, "Process Info="+m_pi+" AD_Client_ID="+Env.getAD_Client_ID(Env.getCtx())); + WProcessCtl.process(ProcessModalDialog.this, m_WindowNo, parameterPanel, m_pi, null); + } finally { + ServerContext.dispose(); + } + } + + protected Properties getProperties() { + return properties; + } + } } // ProcessDialog diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/WProcessCtl.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/WProcessCtl.java index f0ac76dedc..2e68c539f8 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/WProcessCtl.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/WProcessCtl.java @@ -16,12 +16,12 @@ *****************************************************************************/ package org.adempiere.webui.apps; +import org.adempiere.util.IProcessMonitor; import org.adempiere.webui.component.Window; import org.compiere.apps.AbstractProcessCtl; import org.compiere.apps.IProcessParameter; import org.compiere.model.MPInstance; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; import org.compiere.util.Msg; @@ -48,12 +48,12 @@ public class WProcessCtl extends AbstractProcessCtl { * lockUI and unlockUI if parent is a ASyncProcess *
    * - * @param aProcess ASyncProcess & Container + * @param aProcessMonitor ASyncProcess & Container * @param WindowNo window no * @param pi ProcessInfo process info * @param trx Transaction */ - public static void process (ASyncProcess aProcess, int WindowNo, ProcessInfo pi, Trx trx) + public static void process (IProcessMonitor aProcessMonitor, int WindowNo, ProcessInfo pi, Trx trx) { log.fine("WindowNo=" + WindowNo + " - " + pi); @@ -82,7 +82,7 @@ public class WProcessCtl extends AbstractProcessCtl { pi.setAD_PInstance_ID (instance.getAD_PInstance_ID()); // Get Parameters (Dialog) - ProcessModalDialog para = new ProcessModalDialog(aProcess, WindowNo, pi, false); + ProcessModalDialog para = new ProcessModalDialog(aProcessMonitor, WindowNo, pi, false); if (para.isValid()) { para.setWidth("500px"); @@ -105,13 +105,13 @@ public class WProcessCtl extends AbstractProcessCtl { *
    * Called from ProcessDialog.actionPerformed * - * @param parent ASyncProcess & Container + * @param aProcessMonitor ASyncProcess & Container * @param WindowNo window no * @param paraPanel Process Parameter Panel * @param pi ProcessInfo process info * @param trx Transaction */ - public static void process(ASyncProcess parent, int WindowNo, IProcessParameter parameter, ProcessInfo pi, Trx trx) + public static void process(IProcessMonitor aProcessMonitor, int WindowNo, IProcessParameter parameter, ProcessInfo pi, Trx trx) { log.fine("WindowNo=" + WindowNo + " - " + pi); @@ -153,7 +153,7 @@ public class WProcessCtl extends AbstractProcessCtl { } // execute - WProcessCtl worker = new WProcessCtl(parent, WindowNo, pi, trx); + WProcessCtl worker = new WProcessCtl(aProcessMonitor, WindowNo, pi, trx); worker.run(); } @@ -163,9 +163,9 @@ public class WProcessCtl extends AbstractProcessCtl { * @param pi * @param trx */ - public WProcessCtl(ASyncProcess parent, int WindowNo, ProcessInfo pi, + public WProcessCtl(IProcessMonitor aProcessMonitor, int WindowNo, ProcessInfo pi, Trx trx) { - super(parent, WindowNo, pi, trx); + super(aProcessMonitor, WindowNo, pi, trx); } @Override @@ -178,15 +178,15 @@ public class WProcessCtl extends AbstractProcessCtl { @Override protected void lock() { - if (getParent() != null) { - getParent().lockUI(getProcessInfo()); + if (getProcessMonitor() != null) { + getProcessMonitor().lockUI(getProcessInfo()); } } @Override protected void unlock() { - if (getParent() != null) { - getParent().unlockUI(getProcessInfo()); + if (getProcessMonitor() != null) { + getProcessMonitor().unlockUI(getProcessInfo()); } } } diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/form/WPaySelect.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/form/WPaySelect.java index 9b95537b9a..f421058825 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/form/WPaySelect.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/apps/form/WPaySelect.java @@ -22,6 +22,7 @@ import java.sql.Timestamp; import java.util.ArrayList; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; import org.adempiere.webui.apps.ProcessModalDialog; import org.adempiere.webui.component.Button; import org.adempiere.webui.component.Checkbox; @@ -72,7 +73,7 @@ import org.zkoss.zul.Space; * @version $Id: VPaySelect.java,v 1.3 2006/07/30 00:51:28 jjanke Exp $ */ public class WPaySelect extends PaySelect - implements IFormController, EventListener, WTableModelListener, ASyncProcess + implements IFormController, EventListener, WTableModelListener, IProcessMonitor { /** @todo withholding */ @@ -444,4 +445,8 @@ public class WPaySelect extends PaySelect public ADForm getForm() { return form; } + + @Override + public void statusUpdate(String message) { + } } // VPaySelect diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/AbstractADWindowPanel.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/AbstractADWindowPanel.java index 3600e88eec..58f741f31f 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/AbstractADWindowPanel.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/AbstractADWindowPanel.java @@ -29,6 +29,7 @@ import java.util.TreeMap; import java.util.Vector; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; import org.adempiere.webui.WArchive; import org.adempiere.webui.WRequest; import org.adempiere.webui.WZoomAcross; @@ -70,7 +71,6 @@ import org.compiere.model.MRole; import org.compiere.process.DocAction; import org.compiere.process.ProcessInfo; import org.compiere.process.ProcessInfoUtil; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.DisplayType; @@ -117,7 +117,7 @@ import org.zkoss.zul.Menupopup; * https://sourceforge.net/tracker/?func=detail&aid=2985892&group_id=176962&atid=955896 */ public abstract class AbstractADWindowPanel extends AbstractUIPart implements ToolbarListener, - EventListener, DataStatusListener, ActionListener, ASyncProcess + EventListener, DataStatusListener, ActionListener, IProcessMonitor { private static final CLogger logger; @@ -2331,6 +2331,11 @@ public abstract class AbstractADWindowPanel extends AbstractUIPart implements To } } + @Override + public void statusUpdate(String message) { + statusBar.setStatusLine(message); + } + private void updateUI(ProcessInfo pi) { // Refresh data curTab.dataRefresh(false); diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/session/SessionContextListener.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/session/SessionContextListener.java index 85da198e7c..665c6f37c4 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/session/SessionContextListener.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/session/SessionContextListener.java @@ -34,6 +34,8 @@ import org.zkoss.zk.ui.event.EventThreadCleanup; import org.zkoss.zk.ui.event.EventThreadInit; import org.zkoss.zk.ui.event.EventThreadResume; import org.zkoss.zk.ui.event.EventThreadSuspend; +import org.zkoss.zk.ui.sys.DesktopCtrl; +import org.zkoss.zk.ui.sys.ServerPush; import org.zkoss.zk.ui.util.ExecutionCleanup; import org.zkoss.zk.ui.util.ExecutionInit; @@ -96,13 +98,17 @@ public class SessionContextListener implements ExecutionInit, */ public void init(Execution exec, Execution parent) { + //in servlet thread if (parent == null) { - //in servlet thread - setupExecutionContextFromSession(Executions.getCurrent()); - //set locale - Locales.setThreadLocal(Env.getLanguage(ServerContext.getCurrentInstance()).getLocale()); - } + ServerPush serverPush = ((DesktopCtrl)exec.getDesktop()).getServerPush(); + if (serverPush == null || !serverPush.isActive()) + { + setupExecutionContextFromSession(Executions.getCurrent()); + //set locale + Locales.setThreadLocal(Env.getLanguage(ServerContext.getCurrentInstance()).getLocale()); + } + } } /** @@ -116,8 +122,12 @@ public class SessionContextListener implements ExecutionInit, //in servlet thread if (parent == null) { - ServerContext.dispose(); - } + ServerPush serverPush = ((DesktopCtrl)exec.getDesktop()).getServerPush(); + if (serverPush == null || !serverPush.isActive()) + { + ServerContext.dispose(); + } + } } /** diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkJRViewerProvider.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkJRViewerProvider.java index 5309b8b8b3..be7556ab62 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkJRViewerProvider.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkJRViewerProvider.java @@ -3,19 +3,27 @@ package org.adempiere.webui.window; import net.sf.jasperreports.engine.JRException; import net.sf.jasperreports.engine.JasperPrint; +import org.adempiere.webui.apps.AEnv; import org.adempiere.webui.component.Window; import org.adempiere.webui.session.SessionManager; import org.compiere.report.JRViewerProvider; public class ZkJRViewerProvider implements JRViewerProvider { - public void openViewer(JasperPrint jasperPrint, String title) + public void openViewer(final JasperPrint jasperPrint, final String title) throws JRException { - Window viewer = new ZkJRViewer(jasperPrint, title); - - viewer.setAttribute(Window.MODE_KEY, Window.MODE_EMBEDDED); - viewer.setAttribute(Window.INSERT_POSITION_KEY, Window.INSERT_NEXT); - SessionManager.getAppDesktop().showWindow(viewer); + Runnable runnable = new Runnable() { + + @Override + public void run() { + Window viewer = new ZkJRViewer(jasperPrint, title); + + viewer.setAttribute(Window.MODE_KEY, Window.MODE_EMBEDDED); + viewer.setAttribute(Window.INSERT_POSITION_KEY, Window.INSERT_NEXT); + SessionManager.getAppDesktop().showWindow(viewer); + } + }; + AEnv.executeDesktopTask(runnable); } } diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkReportViewerProvider.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkReportViewerProvider.java index 8c95da1073..716494fd66 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkReportViewerProvider.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/ZkReportViewerProvider.java @@ -16,6 +16,7 @@ *****************************************************************************/ package org.adempiere.webui.window; +import org.adempiere.webui.apps.AEnv; import org.adempiere.webui.component.Window; import org.adempiere.webui.session.SessionManager; import org.compiere.print.ReportEngine; @@ -28,11 +29,17 @@ import org.compiere.print.ReportViewerProvider; */ public class ZkReportViewerProvider implements ReportViewerProvider { - public void openViewer(ReportEngine report) { - Window viewer = new ZkReportViewer(report, report.getName()); - - viewer.setAttribute(Window.MODE_KEY, Window.MODE_EMBEDDED); - viewer.setAttribute(Window.INSERT_POSITION_KEY, Window.INSERT_NEXT); - SessionManager.getAppDesktop().showWindow(viewer); + public void openViewer(final ReportEngine report) { + Runnable runnable = new Runnable() { + @Override + public void run() { + Window viewer = new ZkReportViewer(report, report.getName()); + + viewer.setAttribute(Window.MODE_KEY, Window.MODE_EMBEDDED); + viewer.setAttribute(Window.INSERT_POSITION_KEY, Window.INSERT_NEXT); + SessionManager.getAppDesktop().showWindow(viewer); + } + }; + AEnv.executeDesktopTask(runnable); } } \ No newline at end of file diff --git a/org.adempiere.ui/src/org/compiere/apps/AbstractProcessCtl.java b/org.adempiere.ui/src/org/compiere/apps/AbstractProcessCtl.java index f9ec2a9d98..5e47aeffa3 100644 --- a/org.adempiere.ui/src/org/compiere/apps/AbstractProcessCtl.java +++ b/org.adempiere.ui/src/org/compiere/apps/AbstractProcessCtl.java @@ -22,6 +22,7 @@ import java.sql.PreparedStatement; import java.sql.ResultSet; import java.util.logging.Level; +import org.adempiere.util.IProcessMonitor; import org.adempiere.util.ProcessUtil; import org.compiere.db.CConnection; import org.compiere.interfaces.Server; @@ -30,7 +31,6 @@ import org.compiere.print.ReportCtl; import org.compiere.process.ClientProcess; import org.compiere.process.ProcessInfo; import org.compiere.process.ProcessInfoUtil; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.DB; import org.compiere.util.Env; @@ -62,10 +62,10 @@ public abstract class AbstractProcessCtl implements Runnable * @param trx Transaction * Created in process(), VInvoiceGen.generateInvoices */ - public AbstractProcessCtl (ASyncProcess parent, int WindowNo, ProcessInfo pi, Trx trx) + public AbstractProcessCtl (IProcessMonitor aProcessMonitor, int WindowNo, ProcessInfo pi, Trx trx) { windowno = WindowNo; - m_parent = parent; + m_processMonitor = aProcessMonitor; m_pi = pi; m_trx = trx; // handeled correctly } // ProcessCtl @@ -73,7 +73,7 @@ public abstract class AbstractProcessCtl implements Runnable /** Windowno */ private int windowno; /** Parenr */ - private ASyncProcess m_parent; + private IProcessMonitor m_processMonitor; /** Process Info */ private ProcessInfo m_pi; private Trx m_trx; @@ -276,7 +276,7 @@ public abstract class AbstractProcessCtl implements Runnable { m_pi.setReportingProcess(true); // Start Report ----------------------------------------------- - boolean ok = ReportCtl.start(m_parent, windowno, m_pi, IsDirectPrint); + boolean ok = ReportCtl.start(m_processMonitor, windowno, m_pi, IsDirectPrint); m_pi.setSummary("Report", !ok); unlock (); } @@ -322,9 +322,14 @@ public abstract class AbstractProcessCtl implements Runnable return m_pi; } - protected ASyncProcess getParent() + protected IProcessMonitor getProcessMonitor() { - return m_parent; + return m_processMonitor; + } + + protected IProcessMonitor getParent() + { + return getProcessMonitor(); } protected boolean isServerProcess() @@ -440,7 +445,7 @@ public abstract class AbstractProcessCtl implements Runnable if (m_pi.getClassName().toLowerCase().startsWith(MRule.SCRIPT_PREFIX)) { return ProcessUtil.startScriptProcess(Env.getCtx(), m_pi, m_trx); } else { - return ProcessUtil.startJavaProcess(Env.getCtx(), m_pi, m_trx); + return ProcessUtil.startJavaProcess(Env.getCtx(), m_pi, m_trx, true, m_processMonitor); } } return !m_pi.isError(); diff --git a/org.adempiere.ui/src/org/compiere/print/ReportCtl.java b/org.adempiere.ui/src/org/compiere/print/ReportCtl.java index 42ec3e958f..b402ce40bc 100644 --- a/org.adempiere.ui/src/org/compiere/print/ReportCtl.java +++ b/org.adempiere.ui/src/org/compiere/print/ReportCtl.java @@ -21,13 +21,13 @@ import java.util.logging.Level; import org.adempiere.base.Service; import org.adempiere.exceptions.AdempiereException; +import org.adempiere.util.IProcessMonitor; import org.compiere.model.MPaySelectionCheck; import org.compiere.model.MProcess; import org.compiere.model.MQuery; import org.compiere.model.MTable; import org.compiere.model.PrintInfo; import org.compiere.process.ProcessInfo; -import org.compiere.util.ASyncProcess; import org.compiere.util.CLogger; import org.compiere.util.Env; @@ -91,7 +91,7 @@ public class ReportCtl * @param IsDirectPrint if true, prints directly - otherwise View * @return true if created */ - static public boolean start (ASyncProcess parent, int WindowNo, ProcessInfo pi, boolean IsDirectPrint) + static public boolean start (IProcessMonitor parent, int WindowNo, ProcessInfo pi, boolean IsDirectPrint) { pi.setPrintPreview(!IsDirectPrint); return start(parent, WindowNo, pi); @@ -108,7 +108,7 @@ public class ReportCtl * @param IsDirectPrint if true, prints directly - otherwise View * @return true if created */ - static public boolean start (ASyncProcess parent, int WindowNo, ProcessInfo pi) + static public boolean start (IProcessMonitor parent, int WindowNo, ProcessInfo pi) { s_log.info("start - " + pi); @@ -260,7 +260,7 @@ public class ReportCtl * @param printerName Specified printer name * @return true if success */ - public static boolean startDocumentPrint(int type, MPrintFormat customPrintFormat, int Record_ID, ASyncProcess parent, int WindowNo, String printerName) + public static boolean startDocumentPrint(int type, MPrintFormat customPrintFormat, int Record_ID, IProcessMonitor parent, int WindowNo, String printerName) { return(startDocumentPrint(type, customPrintFormat, Record_ID, parent, WindowNo, true, printerName)); } @@ -275,7 +275,7 @@ public class ReportCtl * @param IsDirectPrint if true, prints directly - otherwise View * @return true if success */ - public static boolean startDocumentPrint(int type, int Record_ID, ASyncProcess parent, int WindowNo, + public static boolean startDocumentPrint(int type, int Record_ID, IProcessMonitor parent, int WindowNo, boolean IsDirectPrint) { return(startDocumentPrint(type, null, Record_ID, parent, WindowNo, IsDirectPrint, null )); @@ -290,7 +290,7 @@ public class ReportCtl * @param printerName Specified printer name * @return true if success */ - public static boolean startDocumentPrint (int type, MPrintFormat customPrintFormat, int Record_ID, ASyncProcess parent, int WindowNo, + public static boolean startDocumentPrint (int type, MPrintFormat customPrintFormat, int Record_ID, IProcessMonitor parent, int WindowNo, boolean IsDirectPrint, String printerName) { ReportEngine re = ReportEngine.get (Env.getCtx(), type, Record_ID);