⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 processctl.java

📁 Java写的ERP系统
💻 JAVA
字号:
/******************************************************************************
 * The contents of this file are subject to the   Compiere License  Version 1.1
 * ("License"); You may not use this file except in compliance with the License
 * You may obtain a copy of the License at http://www.compiere.org/license.html
 * Software distributed under the License is distributed on an  "AS IS"  basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License for
 * the specific language governing rights and limitations under the License.
 * The Original Code is                  Compiere  ERP & CRM  Business Solution
 * The Initial Developer of the Original Code is Jorg Janke  and ComPiere, Inc.
 * Portions created by Jorg Janke are Copyright (C) 1999-2001 Jorg Janke, parts
 * created by ComPiere are Copyright (C) ComPiere, Inc.;   All Rights Reserved.
 * Contributor(s): ______________________________________.
 *****************************************************************************/
package org.compiere.apps;

import java.awt.*;
import java.sql.*;
import java.util.*;
import javax.swing.*;

import org.compiere.util.*;
import org.compiere.process.*;
import org.compiere.print.*;

/**
 *	Process Interface Controller
 *
 *  @author 	Jorg Janke
 *  @version 	$Id: ProcessCtl.java,v 1.28 2003/03/15 07:03:18 jjanke Exp $
 */
public class ProcessCtl extends Thread
{
	/**
	 *	Async Process - Do it all.
	 *  <br>
	 *	- Get Instance
	 *	- Get Parameters
	 *	- execute
	 *  <br>
	 *  Creates a ProcessCtl instance, which calls
	 *  lockUI and unlockUI if parent is a ASyncProcess
	 *  <br>
	 *	Called from ProcessStart.startProcess, ProcessDialog.actionPerformed,
	 *  APanel.cmd_print, APanel.actionButton, VPaySelect.cmd_generate
	 *
	 *  @param parent ASyncProcess & Container
	 *  @param WindowNo window no
	 *  @param pi ProcessInfo process info
	 *  @return worker started ProcessCtl instance
	 */
	public static ProcessCtl process (ASyncProcess parent, int WindowNo, ProcessInfo pi)
	{
		Log.trace(Log.l2_Sub, "ProcessCtl.process - WindowNo=" + WindowNo, pi);

		//	Get Instance
		pi.AD_PInstance_ID = getInstanceID(WindowNo, pi.AD_Process_ID, pi.Record_ID);
		if (pi.AD_PInstance_ID == 0)
		{
			pi.Summary = Msg.getMsg(Env.getCtx(), "ProcessNoInstance");
			pi.Error = true;
			return null;
		}

		//	Get Parameters
		ProcessParameter para = new ProcessParameter (Env.getFrame((Container)parent), WindowNo, pi);
		if (para.initDialog())
		{
			para.show();
			if (!para.isOK())
			{
				pi.Summary = Msg.getMsg(Env.getCtx(), "ProcessCancelled");
				pi.Error = true;
				return null;
			}
		}

		//	execute
		ProcessCtl worker = new ProcessCtl(parent, pi);
		worker.start();
		return worker;
	}	//	execute


	/*************************************************************************/

	/**
	 *	Create Process Instance
	 *	Returns AD_PInstance_ID
	 *
	 *  @param WindowNo window no
	 *  @param AD_Process_ID process
	 *  @param Record_ID record
	 *  @return AD_PInstance_ID instance
	 */
	public static int getInstanceID(int WindowNo, int AD_Process_ID, int Record_ID)
	{
	//	Log.trace(Log.l3_Util, "ProcessCtl.createInstanceID for " + AD_Process_ID + " with " + Record_ID);

		//	Get AD_PInstance_ID
		int AD_PInstance_ID = DB.getKeyNextNo(Env.getCtx(), WindowNo, "AD_PInstance");
		if (AD_PInstance_ID == 0)
			return 0;
		//  Get User
		int AD_User_ID = Env.getContextAsInt(Env.getCtx(), "#AD_User_ID");

		//	Create Instance Record
		StringBuffer sql = new StringBuffer ();
		sql.append("INSERT INTO AD_PInstance (AD_PInstance_ID, AD_Process_ID, Record_ID, AD_User_ID) ")
			.append("VALUES (").append(AD_PInstance_ID)
			.append(",").append(AD_Process_ID)
			.append(",").append(Record_ID)
			.append(",").append(AD_User_ID).append(")");
		try
		{
			Statement stmt = DB.createStatement();
			int n = stmt.executeUpdate(sql.toString());
			stmt.close();
		}
		catch (SQLException e)
		{
			Log.error("ProcessCtl.createInstanceID", e);
			return 0;
		}
		//
		Log.trace(Log.l4_Data, "Process Instance = " + AD_PInstance_ID);
		return AD_PInstance_ID;
	}	//	createInstance

	/*************************************************************************/

	/**
	 *	Query PInstance for result.
	 *  Fill Summary and success in ProcessInfo
	 *  @param pi Process Info
	 */
	public static void setInstanceInfo (ProcessInfo pi)
	{
		Log.trace(Log.l4_Data, "ProcessCtl.setInstanceInfo - Instance: " + pi.AD_PInstance_ID);
		int sleepTime = 2000;	//	2 secomds
		int noRetry = 5;        //  10 seconds total
		//
		String SQL = "SELECT Result, ErrorMsg FROM AD_PInstance "
			+ "WHERE AD_PInstance_ID=?"
			+ " AND Result IS NOT NULL";

		try
		{
			PreparedStatement pstmt = DB.prepareStatement (SQL, ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
			for (int noTry = 0; noTry < noRetry; noTry++)
			{
				pstmt.setInt(1, pi.AD_PInstance_ID);
				ResultSet rs = pstmt.executeQuery();
				if (rs.next())
				{
					//	we have a result
					int i = rs.getInt(1);
					if (i == 1)
					{
						pi.Summary = Msg.getMsg(Env.getCtx(), "Success");
					}
					else
					{
						pi.Summary = Msg.getMsg(Env.getCtx(), "Failure");
						pi.Error = true;
					}
					String Message = rs.getString(2);
					rs.close();
					pstmt.close();
					if (Message != null)
						pi.Summary += "  (" +  Msg.parseTranslation(Env.getCtx(), Message)  + ")";
				//	Log.trace(Log.l4_Data, "ProcessCtl.setInstanceInfo - done");
					return;
				}

				rs.close();
				//	sleep
				try
				{
					Log.trace(Log.l4_Data, "ProcessCtl.setInstanceInfo - sleeping");
					Thread.currentThread().sleep(sleepTime);
				}
				catch (InterruptedException ie)
				{
					Log.error("ProcessCtl.setInstanceInfo Sleep Thread", ie);
				}
			}
			pstmt.close();
		}
		catch (SQLException e)
		{
			Log.error("ProcessCtl.setInstanceInfo", e);
			pi.Summary = e.getLocalizedMessage();
			pi.Error = true;
			return;
		}
		pi.Error = true;
		pi.Summary = Msg.getMsg(Env.getCtx(), "Timeout");
	}	//	setInstanceInfo

	/*************************************************************************/

	/**
	 *  Start Java Class.
	 *      instanciate the class implementing the interface ProcessCall.
	 *  The class can be a Server/Client class (when in Package
	 *  org compiere.process or org.compiere.model) or a client only class
	 *  (e.g. in org.compiere.report)
	 *
	 *  @param ctx  Context
	 *  @param ClassName    name of the class to call
	 *  @param pi	process info
	 *  @return     true if success
	 *  @see org.compiere.model.ProcessCall
	 */
	private static boolean startClass (Properties ctx, String ClassName, ProcessInfo pi)
	{
		Log.trace(Log.l4_Data, "ProcessCtl.startClass - " + ClassName, pi);
		boolean retValue = false;
		ProcessCall myObject = null;
		try
		{
			Class myClass = Class.forName(ClassName);
			myObject = (ProcessCall)myClass.newInstance();
			if (myObject == null)
				retValue = false;
			else
				retValue = myObject.startProcess(ctx, pi);
		}
		catch (Exception e)
		{
			Log.error("ProcessCtl.startClass - " + ClassName, e);
			retValue = false;
		}

		return retValue;
	}   //  startClass


	/*************************************************************************/

	/**
	 *  Start Database Process
	 *  @param ProcedureName PL/SQL procedure name
	 *  @param pi orocess info
	 *  @return true if success
	 */
	private static boolean startProcess (String ProcedureName, ProcessInfo pi)
	{
		//  execute on this thread/connection
		Log.trace(Log.l4_Data, "ProcessCtl.startProcess", ProcedureName + "(" + pi.AD_PInstance_ID + ")");
		try
		{
			String sql = "{CALL " + ProcedureName + "(?)}";
			CallableStatement cstmt = DB.prepareCall(sql);	//	ro??
			cstmt.setInt(1, pi.AD_PInstance_ID);
			cstmt.executeUpdate();
			cstmt.close();
		}
		catch (Exception e)
		{
			Log.error("ProcessCtl.startProcess", e);
			pi.Summary = Msg.getMsg(Env.getCtx(), "ProcessRunError") + " " + e.getLocalizedMessage();
			pi.Error = true;
			return false;
		}
	//	Log.trace(Log.l4_Data, "ProcessCtl.startProcess - done");
		return true;
	}   //  startProcess

	/*************************************************************************/

	/**
	 *  Constructor
	 *  @param parent Container & ASyncProcess
	 *  @param pi
	 *  Created in process(), VInvoiceGen.generateInvoices
	 */
	public ProcessCtl (ASyncProcess parent, ProcessInfo pi)
	{
		m_parent = parent;
		m_pi = pi;
	}   //  ProcessCtl

	private ASyncProcess    m_parent;
	private ProcessInfo     m_pi;
	private Waiting         m_waiting;

	/**
	 *	Execute Process Instance and Lock UI.
	 *  Calls lockUI and unlockUI if parent is a ASyncProcess
	 *  <pre>
	 *		- Get Process Information
	 *      - Call Class
	 *		- Submit SQL Procedure
	 *		- Run SQL Procedure
	 *	</pre>
	 */
	public void run ()
	{
		Log.trace(Log.l3_Util, "ProcessCtl.run", "AD_PInstance_ID=" + m_pi.AD_PInstance_ID
			+ ", Record_ID=" + m_pi.Record_ID);

		//  Lock
		lock();
	//	try {System.out.println(">> sleeping ..");sleep(20000);System.out.println(".. sleeping <<");} catch (Exception e) {}

		//	Get Process Information: Name, Procedure Name, ClassName, IsReport, IsDirectPrint
		String 	ProcedureName = "";
		String  ClassName = "";
		int     AD_ReportView_ID = 0;
		boolean IsReport = false;
		boolean	IsDirectPrint = false;
		//
		String SQL = "SELECT p.Name, p.ProcedureName,p.ClassName, p.AD_Process_ID,"
			+ " p.isReport,p.IsDirectPrint,p.AD_ReportView_ID,"
			+ " DECODE(p.Statistic_Count,0,0, p.Statistic_Seconds/p.Statistic_Count) "
			+ "FROM AD_Process p, AD_PInstance i "
			+ "WHERE p.AD_Process_ID=i.AD_Process_ID AND p.IsActive='Y'"
			+ " AND i.AD_PInstance_ID=?";
		if (!Env.isBaseLanguage(Env.getCtx(), "AD_Process"))
			SQL = "SELECT t.Name, p.ProcedureName,p.ClassName, p.AD_Process_ID,"
				+ " p.isReport, p.IsDirectPrint,AD_ReportView_ID,"
				+ " DECODE(p.Statistic_Count,0,0, p.Statistic_Seconds/p.Statistic_Count) "
				+ "FROM AD_Process p, AD_Process_Trl t, AD_PInstance i "
				+ "WHERE p.AD_Process_ID=i.AD_Process_ID"
				+ " AND p.AD_Process_ID=t.AD_Process_ID AND p.IsActive='Y'"
				+ " AND i.AD_PInstance_ID=?"
				+ " AND t.AD_Language='" + Env.getAD_Language(Env.getCtx()) + "'";
		//
		try
		{
			PreparedStatement pstmt = DB.prepareStatement(SQL, ResultSet.TYPE_FORWARD_ONLY, ResultSet.CONCUR_READ_ONLY);
			pstmt.setInt(1, m_pi.AD_PInstance_ID);
			ResultSet rs = pstmt.executeQuery();
			if (rs.next())
			{
				m_pi.Title = rs.getString(1);
				if (m_waiting != null)
					m_waiting.setTitle(m_pi.Title);
				ProcedureName = rs.getString(2);
				ClassName = rs.getString(3);
				m_pi.AD_Process_ID = rs.getInt(4);
				//	Report
				if ("Y".equals(rs.getString(5)))
				{
					IsReport = true;
					if ("Y".equals(rs.getString(6)) && !Ini.getPropertyBool(Ini.P_PRINTPREVIEW))
						IsDirectPrint = true;
				}
				AD_ReportView_ID = rs.getInt(7);
				//
				int estimate = rs.getInt(8);
				if (estimate != 0)
				{
					m_pi.EstSeconds = estimate + 1;     //  admin overhead
					if (m_waiting != null)
						m_waiting.setTimerEstimate(m_pi.EstSeconds);
				}
			}
			else
				Log.error("ProcessCtrl.run - no AD_PInstance_ID=" + m_pi.AD_PInstance_ID);
			rs.close();
			pstmt.close();
		}
		catch (SQLException e)
		{
			m_pi.Summary = Msg.getMsg(Env.getCtx(), "ProcessNoProcedure") + " " + e.getLocalizedMessage();
			unlock (false, "SQL Error");
			Log.error("ProcessCtrl.run", e);
			return;
		}

		//  No Procedure
		if (ProcedureName == null)
			ProcedureName = "";

		//  Start Optional Class
		if (ClassName != null && ClassName.length() > 0)
		{
			if (!startClass (Env.getCtx(), ClassName, m_pi))
			{
				setInstanceInfo (m_pi);
				unlock (false, "Start Class failed");
				return;
			}

			//  No Optional SQL procedure ... done
			if (!IsReport  && ProcedureName.length() == 0)
			{
				setInstanceInfo (m_pi);
				unlock (true, null);
				return;
			}
			//  No Optional Report ... done
			if (IsReport && AD_ReportView_ID == 0)
			{
				setInstanceInfo (m_pi);
				unlock (true, null);
				return;
			}
		}

		//  If not a report, we need a prodedure name
		if (!IsReport && ProcedureName.length() == 0)
		{
			m_pi.Summary = Msg.getMsg(Env.getCtx(), "ProcessNoProcedure");
			unlock (false, "Not a Report or ProcedureName");
			return;
		}

		/**********************************************************************
		 *	Report submission
		 */
		if (IsReport)
		{
			//	Optional Pre-Report Process
			if (ProcedureName.length() > 0)
			{
				if (!startProcess(ProcedureName, m_pi))
				{
					unlock (false, "Start Procedure failed (1)");
					return;
				}
			}	//	Pre-Report

			//	Start Report	-----------------------------------------------
			unlock (ReportCtl.start(m_pi, IsDirectPrint), "ReportDispatcher");
		}
		/**********************************************************************
		 * 	Process submission
		 */
		else
		{
			if (!startProcess(ProcedureName, m_pi))
			{
				unlock (false, "Start Procedure failed (2)");
				return;
			}
			//	getResult
			setInstanceInfo (m_pi);
			unlock (true, null);
		}			//	*** Process submission ***
	//	Log.trace(Log.l3_Util, "ProcessCtl.run - done");
	}   //  run

	/**
	 *  Lock & show Waiting
	 */
	private void lock ()
	{
	//	Log.trace(Log.l5_DData, "ProcessCtl.locking ...");
		JFrame frame = Env.getFrame((Container)m_parent);
		if (frame instanceof AWindow)
			((AWindow)frame).setBusyTimer(m_pi.EstSeconds);
		else
			m_waiting = new Waiting (frame, Msg.getMsg(Env.getCtx(), "Processing"), false, m_pi.EstSeconds);
		SwingUtilities.invokeLater(new Runnable()
		{
			public void run()
			{
				Log.trace(Log.l5_DData, "ProcessCtl.lock");
				m_parent.lockUI(m_pi);
			}
		});
		if (m_waiting != null)
			m_waiting.toFront();
	}   //  lock

	/**
	 *  Unlock & dispose Waiting
	 *  @param ok success
	 *  @param info optional
	 */
	private void unlock (final boolean ok, String info)
	{
		if (info != null && info.length() > 0)
			Log.trace(Log.l5_DData, "ProcessCtl.unlocking ...", info);
		SwingUtilities.invokeLater(new Runnable()
		{
			public void run()
			{
				Log.trace(Log.l5_DData, "ProcessCtl.unlock - " + ok);
				m_pi.Error = !ok;
				m_parent.unlockUI(m_pi);
			}
		});
		if (m_waiting != null)
			m_waiting.dispose();
		m_waiting = null;
	}   //  unlock

}	//	ProcessCtl

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -