package com.steering.pss.sale.order.bomGeneration;

import java.sql.Connection;
import java.util.List;

import com.steering.pss.sale.order.bomGeneration.dao.CraftDao;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomBLDaoImp;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomCheckDaoImp;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomQueryDaoImp;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomFactoryDao;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomJGDaoImp;
import com.steering.pss.sale.order.bomGeneration.daoImp.BomSaveDaoImp;
import com.steering.pss.sale.order.bomGeneration.model.BomEntity;
import com.steering.pss.sale.order.bomGeneration.model.DesignBomEntity;
import com.steering.pss.sale.order.bomGeneration.model.DesignBomKEntity;
import com.steering.pss.sale.order.bomGeneration.model.MscBlEntity;
import com.steering.pss.sale.order.bomGeneration.model.MscJgEntity;
import com.steering.pss.sale.order.bomGeneration.model.SlmOrdDesignBlEntity;
import com.steering.pss.sale.order.bomGeneration.model.SlmOrdDesignBomHEntity;
import com.steering.pss.sale.order.bomGeneration.model.SlmOrdDesignMscBlEntity;
import com.steering.pss.sale.order.bomGeneration.model.SlmOrdDesignMscJgLineEntity;
import com.steering.pss.sale.order.bomGeneration.server.BomFromKey;
import com.steering.pss.sale.order.bomGeneration.server.BomMaterial;
import com.steering.pss.sale.order.bomGeneration.server.BomProduc;
import com.steering.pss.sale.order.bomGeneration.server.GeneraBomEntity;
import com.steering.pss.sale.order.bomGeneration.serverImp.BomFactoryServer;
import com.steering.pss.sale.order.bomGeneration.serverImp.BomProducImp;
import com.steering.pss.sale.order.model.BaseProductEntity;
import com.steering.pss.sale.order.model.DesignMscEntity;
import com.steering.pss.sale.order.model.DesignMscPlGxPrlEntity;
import com.steering.pss.sale.order.qualityDesign.Dao.factory.FactoryDao;
import com.steering.pss.sale.order.qualityDesign.Dao.imp.QualityPrePDaoImp;

public class BOMGeneration {
	// 物料码生成流程：
	// 1、取基础数据形成物料通用数据类
	// 2、形成产品的物料(备料码当产品用)
	// 3、接箍码(如果是冶金规范码类型是成品接箍，开成接箍加工的物料　其它则形成接箍加工/加工的物料)
	// 4、备料码(肯定要有加工工序，形成加工的物料)

	/**
	 * 物料码生成
	 * 
	 * @param con
	 *            连接字符串
	 * @param designKey
	 *            质量或者工艺主键
	 * @param flag
	 *            基础数据来源(合同行 0，备料 1，工艺 2)
	 * @param craftFlag
	 *            评审类型(0 质量设计 1工艺评审)
	 * @throws Exception
	 */
	public static void generationBomMain(Connection con, String designKey,
			String flag, String craftFlag) throws Exception {
		con.setAutoCommit(false);
		try {
			BomQueryDaoImp bomQueryDaoImp = BomFactoryDao.getBomQueryDaoImp();
			QualityPrePDaoImp qualityPrePDaoImp = FactoryDao
					.getQualityPrePDaoImp();
			BomSaveDaoImp bomSaveDaoImp = BomFactoryDao.getBomSaveDaoImp();
			BomJGDaoImp bomJGDaoImp = BomFactoryDao.getBomJGDaoImp();
			BomProducImp bomProducImp = BomFactoryServer.getBomProducImp();
			BomCheckDaoImp bomCheckDaoImp = BomFactoryDao.getBomCheckDaoImp();
			BomBLDaoImp bomBLDaoImp = BomFactoryDao.getBomBLDaoImp();
			// 生成BOM类(用于存储整个物料常用的变量)
			BomEntity bomEntity = null;
			if (flag.equals("0")) {
				// 质量设计
				String[] ordLnPk = bomQueryDaoImp.getOrdLnPk(con, designKey);
				DesignMscEntity mscEntity = qualityPrePDaoImp.getOrderLine(con,
						ordLnPk[1], ordLnPk[0]);
				bomEntity = GeneraBomEntity.generaBomEntity(mscEntity);
			} else if (flag.equals("1")) {
				// 备料
				SlmOrdDesignBlEntity blEntity = bomQueryDaoImp.getBLEntity(con,
						designKey);
				bomEntity = GeneraBomEntity.generaBomEntity(con, blEntity);

			} else {
				// 工艺评审
				CraftDao craftDao = new CraftDao();
				DesignMscEntity mscEntity = craftDao
						.getCraftMsc(con, designKey);
				bomEntity = GeneraBomEntity.generaBomEntity(mscEntity);
			}

			// 获取产品类型(2016/06/22)
			BaseProductEntity producEntity = bomQueryDaoImp.getProductCode(con,
					bomEntity.getProduccode());
			// 获取数据正常情况不会为null
			if (producEntity != null) {
				bomEntity.setProducType(producEntity.getProducType());
			}

			/**
			 * 一、选根据合同行、制程、规格、钢种等生成多套物料编码
			 */
			List<DesignBomEntity> boms = BomFromKey.generationKey(con,
					designKey, bomEntity, craftFlag);
			for (DesignBomEntity bom : boms) {
				// 查询整个制程下产线
				List<DesignMscPlGxPrlEntity> lines = null;
				if (craftFlag.equals("0")) {
					// 质量设计(或者备料码)
					lines = bomQueryDaoImp.getProline(con, designKey,
							bom.getMscPline());
				} else {
					// 工艺评审
					CraftDao craftDao = new CraftDao();
					lines = craftDao.getProline(con, designKey,
							bom.getMscPline());
				}

				// 根据物料编码生成BOM,及形成基础物料数据
				String bomNo = bomProducImp.fromAndSaveBom(con, bom, bomEntity,
						lines, designKey, craftFlag);
				// 如果是工艺评审,则保存工艺评审对应表,否则保存质量评审表
				if (craftFlag.equals("0")) {
					// 保存合同行与物料编码的对应关系(designKey,bom关联)
					if (bomCheckDaoImp
							.checkSlmOrdLineBom(con, designKey, bomNo) == 0) {
						bomSaveDaoImp.saveLineBom(con, designKey, bomNo);
					}
				} else {
					CraftDao craftDao = new CraftDao();
					if (!craftDao.checkCraftOrdLineBom(con, designKey, bomNo)) {
						craftDao.saveCraftOrdLineBom(con, designKey, bomNo);
					}
				}
				/**
				 * 二、接箍物料BOM,如果产品对接箍有要求,分析接箍物料编码 (钢管加接箍B,附件短节C,成品接箍D
				 * 这三种类型的合同是有接箍码的,但成品接箍是没有加工工序)
				 */

				// 1.查询接箍码
				List<String> codeJGs = bomJGDaoImp.getJGCode(con, designKey,
						craftFlag);
				// 如果合同冶金规范码类型是成品接箍,则形成接箍加工的物料(有两条:备料码－＞接箍码;接箍码->成品接箍)
				// 否则肯定有加工工序，形成接箍加工工序/加工工序的物料/BOM(各一条：备料码－＞接箍码；接箍码－＞管体)
				if (codeJGs != null && codeJGs.size() != 0) {
					for (String codeJG : codeJGs) {
						MscJgEntity mscJg = bomJGDaoImp.getJGInfo(con, codeJG);// 肯定不为null
						if (mscJg == null) {
							continue;
						}
						/**
						 * 1.中间物料编码即接箍码/中间物料描述(品种、规格、标准类别
						 */
						// 钢级、扣型)　以Ｊ开头(和成品接箍的成品物料不一致)
						String jgMaterialNo = codeJG;
						String jgMaterialDesc = "J"
								+ BomMaterial.generationPrefix(con,
										mscJg.getProduccode())
								+ mscJg.getProduccodeJgDesc() + ","
								+ mscJg.getSpecJgDesc().trim() + ","
								+ mscJg.getStdStyleDesc().trim() + ","
								+ mscJg.getSteelcodeJgDesc().trim() + ","
								+ mscJg.getModelDesc().trim();
						/**
						 * 2.形成接箍码->成品接箍/接箍码->管体
						 */
						// 如果是成品接箍码，则再形成一条接箍码－＞成品接箍的接箍加工物料
						if (bomEntity.getMscStyle().equals("D")) {
							SlmOrdDesignBomHEntity bomHA = new SlmOrdDesignBomHEntity();
							bomHA.setBom(bomNo);
							bomHA.setInMaterialNo(jgMaterialNo);
							bomHA.setInMaterialDesc(jgMaterialDesc);
							bomHA.setOutMaterialNo(bom.getMaterialNo());
							bomHA.setOutMaterialDesc(bom.getMaterialDesc());
							// 保存数据
							// 保存接箍加工BOM
							if (bomCheckDaoImp.checkBomH(con, bomHA.getBom(),
									bomHA.getInMaterialNo(),
									bomHA.getOutMaterialNo())) {
								bomSaveDaoImp.saveBomH(con, bomHA);
							}
							// 基础物料-接箍加工
							if (bomCheckDaoImp.checkBaseMaterialH(con,
									bomHA.getInMaterialNo(),
									bomHA.getOutMaterialNo()) == 0) {
								bomSaveDaoImp.saveBaseMaterialH(con, bomHA);
							}
							// 成品的接箍加工产线
							List<DesignMscPlGxPrlEntity> fitPlines = BomProduc
									.fiterLine(lines, "H");
							// 备料码到接箍码的产线能力
							if (fitPlines != null) {
								for (DesignMscPlGxPrlEntity line : fitPlines) {
									if (bomCheckDaoImp.checkBaseMaterialHPl(
											con, bomHA.getInMaterialNo(),
											bomHA.getOutMaterialNo(),
											line.getPlineCode()) == 0) {
										// 保存接箍加工产线能力
										bomSaveDaoImp.saveBaseMaterialHPl(con,
												bomHA.getInMaterialNo(),
												bomHA.getOutMaterialNo(),
												line.getPlineCode(),
												line.getPlineName(),
												bomHA.getInMaterialDesc(),
												bomHA.getOutMaterialDesc());
									}
								}
							}

						} else {
							// 不是成品接箍，并且有接箍码，则形成一条加工的物料
							// 形成加工工序的物料(接箍码的标识是2,管体是1,备料码是3)
							DesignBomKEntity bomK = new DesignBomKEntity();
							bomK.setBom(bomNo);
							bomK.setMark("2");
							bomK.setGroupNum("0");
							bomK.setInMaterialNo(jgMaterialNo);
							bomK.setInMaterialDesc(jgMaterialDesc);
							bomK.setOutMaterialNo(bom.getMaterialNo());
							bomK.setOutMaterialDesc(bom.getMaterialDesc());
							// 验证则保存数据
							if (bomCheckDaoImp
									.checkBomK(con, bomK.getBom(),
											bomK.getInMaterialNo(),
											bomK.getOutMaterialNo(),
											bomK.getGroupNum())) {
								bomSaveDaoImp.saveBomK(con, bomK);
							}
							// 基础物料-加工
							if (bomCheckDaoImp.checkBaseMaterialK(con,
									bomK.getInMaterialNo(),
									bomK.getOutMaterialNo()) == 0) {
								bomSaveDaoImp.saveBaseMaterialK(con, bomK);
							}
							// 基础数据- 加工投入产出-产线能力
							List<DesignMscPlGxPrlEntity> fitPlines = BomProduc
									.fiterLine(lines, "G");
							for (DesignMscPlGxPrlEntity pline : fitPlines) {
								if (bomCheckDaoImp.checkBaseMaterialKPl(con,
										bomK.getInMaterialNo(),
										bomK.getOutMaterialNo(),
										pline.getPlineCode()) == 0) {
									bomSaveDaoImp.saveBaseMaterialKPl(con,
											bomK.getInMaterialNo(),
											bomK.getOutMaterialNo(),
											pline.getPlineCode(),
											pline.getPlineName(),
											bomK.getInMaterialDesc(),
											bomK.getOutMaterialDesc());
								}
							}
						}
						/**
						 * 3. 查询备料码形成投入物料(正常数据：备料码只有一条)只要有接箍码，都能形成接箍加工数据
						 */

						List<String> codeBLs = bomJGDaoImp.getJGBLCode(con,
								designKey, craftFlag);
						if (codeBLs != null) {
							for (String codeBL : codeBLs) {
								// 查询备料码信息
								MscBlEntity blEntity = bomBLDaoImp.getBLInfo(
										con, codeBL);

								BomEntity blbomentity = GeneraBomEntity
										.generaBomEntityB(con, blEntity);
								// 形成投入物料编码与描述
								String[] materialArr = BomMaterial
										.formEndMaterial(blbomentity, con);
								// 形成接箍加工物料
								SlmOrdDesignBomHEntity bomH = new SlmOrdDesignBomHEntity();
								bomH.setBom(bomNo);
								bomH.setInMaterialNo(materialArr[0]);
								bomH.setInMaterialDesc(materialArr[1]);
								bomH.setOutMaterialNo(jgMaterialNo);
								bomH.setOutMaterialDesc(jgMaterialDesc);
								// 保存接箍加工BOM
								if (bomCheckDaoImp.checkBomH(con,
										bomH.getBom(), bomH.getInMaterialNo(),
										bomH.getOutMaterialNo())) {
									bomSaveDaoImp.saveBomH(con, bomH);
								}
								// 基础物料-接箍加工
								if (bomCheckDaoImp.checkBaseMaterialH(con,
										bomH.getInMaterialNo(),
										bomH.getOutMaterialNo()) == 0) {
									bomSaveDaoImp.saveBaseMaterialH(con, bomH);
								}
								// 接箍码的接箍加工产线
								List<SlmOrdDesignMscJgLineEntity> jgLines = bomQueryDaoImp
										.getJGLine(con, designKey, craftFlag);
								// 备料码到接箍码的产线能力
								if (jgLines != null) {
									for (SlmOrdDesignMscJgLineEntity jgLine : jgLines) {
										if (bomCheckDaoImp
												.checkBaseMaterialHPl(
														con,
														bomH.getInMaterialNo(),
														bomH.getOutMaterialNo(),
														jgLine.getPlineCode()) == 0) {
											// 保存接箍加工产线能力
											bomSaveDaoImp.saveBaseMaterialHPl(
													con,
													bomH.getInMaterialNo(),
													bomH.getOutMaterialNo(),
													jgLine.getPlineCode(),
													jgLine.getPlineName(),
													bomH.getInMaterialDesc(),
													bomH.getOutMaterialDesc());
										}
									}
								}
							}
						}
					}
				}
				/**
				 * 四、如果产品对备料码有要求,建立产品与备料码关联(只要建立备料物料码与产品码的关系)
				 */

				List<SlmOrdDesignMscBlEntity> blentityList = bomBLDaoImp
						.getBLCode(con, designKey, craftFlag);
				if (blentityList != null && blentityList.size() > 0) {
					for (SlmOrdDesignMscBlEntity entity : blentityList) {
						MscBlEntity blEntity = bomBLDaoImp.getBLInfo(con,
								entity.getPscBl());
						BomEntity bomentity = GeneraBomEntity.generaBomEntityB(
								con, blEntity);
						String[] materialArr = BomMaterial.formEndMaterial(
								bomentity, con);
						// 此方法作废
						// bomBLImp.generationBL(con, entity.getPscBl(), bomNo);
						// 重新生成(2016/6/22)
						DesignBomKEntity bomK = new DesignBomKEntity();
						bomK.setBom(bomNo);
						bomK.setMark("3");
						bomK.setGroupNum(entity.getGroupNum());
						bomK.setInMaterialNo(materialArr[0]);
						bomK.setInMaterialDesc(materialArr[1]);
						bomK.setOutMaterialNo(bom.getMaterialNo());
						bomK.setOutMaterialDesc(bom.getMaterialDesc());
						// 验证则保存数据
						if (bomCheckDaoImp.checkBomK(con, bomK.getBom(),
								bomK.getInMaterialNo(),
								bomK.getOutMaterialNo(), bomK.getGroupNum())) {
							bomSaveDaoImp.saveBomK(con, bomK);
						}
						// 基础物料-加工
						if (bomCheckDaoImp
								.checkBaseMaterialK(con,
										bomK.getInMaterialNo(),
										bomK.getOutMaterialNo()) == 0) {
							bomSaveDaoImp.saveBaseMaterialK(con, bomK);
						}
						// 基础数据- 加工投入产出-产线能力
						List<DesignMscPlGxPrlEntity> fitPlines = BomProduc
								.fiterLine(lines, "G");
						for (DesignMscPlGxPrlEntity pline : fitPlines) {
							if (bomCheckDaoImp.checkBaseMaterialKPl(con,
									bomK.getInMaterialNo(),
									bomK.getOutMaterialNo(),
									pline.getPlineCode()) == 0) {
								bomSaveDaoImp.saveBaseMaterialKPl(con,
										bomK.getInMaterialNo(),
										bomK.getOutMaterialNo(),
										pline.getPlineCode(),
										pline.getPlineName(),
										bomK.getInMaterialDesc(),
										bomK.getOutMaterialDesc());
							}
						}
					}
				}
			}
			con.commit();
		} catch (Exception e) {
			e.printStackTrace();
			throw e;
		} finally {
			con.setAutoCommit(true);
		}
	}
}
