using MesServerWork;
using MisDataFunDll;
using MisDataSaveDate;
using System;

namespace MesServerFunctions
{
    partial class FunctionMES
    {
        // 防止 PLC 传递机型信号重复触发时并发进站。
        object lockBarcodeEngineTypeGetOver = new object();

        /// <summary>
        /// OP431 PLC 回传机型后，校验 PAD 确认信息并调用工厂 MES 进站。
        /// </summary>
        private void EngineTypeGetOver_PLC(object e)
        {
            lock (lockBarcodeEngineTypeGetOver)
            {
                try
                {
                    var msgEvent = (DeviceDriver_BasicData.CustomeEvetnArgs)e;
                    string opName = Convert.ToString(msgEvent.OpName);
                    int tagValue = Convert.ToInt32(msgEvent.TagValue);

                    if (tagValue != 1)
                    {
                        MisDataFun.LogRecording_OP(opName, "INFO", "MIS", "PLC传递机型取消！");
                        MIS_BASE.Write_FixAllow(opName, false);
                        return;
                    }

                    MisDataFun.LogRecording_OP(opName, "INFO", "MIS", "PLC传递机型！");
                    MIS_BASE.Write_TagValueByTagTypeID(34, opName, false);

                    // 同时读取 PLC 回传信息和 PAD 确认时写入的 MES 产品区信息。
                    MIS_BASE.GetEngineTypeFromPLC(opName, out int engineTypeID, out string engineType, out string engineID, out int palletCode, out string orderForm);
                    MIS_BASE.GetEngineTypeFromPLC_MES(opName, out int engineTypeIDMes, out string engineTypeMes, out string engineIDMes, out string orderFormMes);

                    if (string.IsNullOrWhiteSpace(engineID) || engineTypeID <= 0)
                    {
                        WriteManualStaticEngineError(opName, "PLC产品码或机型为空，产品码：" + engineID + "，机型代码：" + engineTypeID);
                        return;
                    }

                    if (string.IsNullOrWhiteSpace(engineIDMes) || engineTypeIDMes <= 0)
                    {
                        WriteManualStaticEngineError(opName, "未查询到PAD确认上线信息，请先在PAD确认上线");
                        return;
                    }

                    // PLC 回传产品必须与 PAD 确认上线产品一致，避免错件进站。
                    if (!string.Equals(engineID.Trim(), engineIDMes.Trim(), StringComparison.OrdinalIgnoreCase))
                    {
                        WriteManualStaticEngineError(opName, "PLC产品码与PAD确认产品码不一致，PLC：" + engineID + "，PAD：" + engineIDMes);
                        return;
                    }

                    if (engineTypeID != engineTypeIDMes)
                    {
                        WriteManualStaticEngineError(opName, "PLC机型与PAD确认机型不一致，PLC：" + engineTypeID + "，PAD：" + engineTypeIDMes);
                        return;
                    }

                    // 进站前再次取产品执行信息，后续写 MOBY 使用数据库中的订单和型号。
                    if (!TryGetManualStaticOutProduct(engineID, out ManualStaticOutProduct product, out string productMessage))
                    {
                        WriteManualStaticEngineError(opName, productMessage);
                        return;
                    }

                    // 调用工厂 MES 进站，成功后才允许 PLC 工作。
                    CallWebService.Call_miFindCustomAndSfcData(opName, engineID, out string code, out string message);
                    if (code != "0")
                    {
                        WriteManualStaticEngineError(opName, "进站失败：" + engineID + "，code：" + code + "，message：" + message);
                        return;
                    }

                    MisDataFun.LogRecording_OP(opName, "INFO", "MOM", "进站成功：" + engineID);

                    // 写普通 MOBY 当前工位状态，供后续正常过站过程取数。
                    MisDataFun.OpName_MIS_MOBY_Insert(opName, product.EngineTypeID, product.EngineType, product.EngineID, palletCode, product.OrderForm, 0, 0, "");

                    MIS_BASE.Write_FixAllow(opName, true);
                    SendMessage.AsyncSendMessage_Notice(opName, "【" + opName + "】进站成功，允许PLC工作：" + engineID);
                }
                catch (Exception err)
                {
                    MyLog4Net.MyLogHelper.Error("Function1062.EngineTypeGetOver", err.Message);
                    MisDataFun.LogRecording_OP(ManualStaticOutOpName, "ERROR", "EngineTypeGetOver", err.Message);
                }
            }
        }

        /// <summary>
        /// OP431 进站失败时禁止 PLC 工作、置 MES 报警并通知页面。
        /// </summary>
        private void WriteManualStaticEngineError(string opName, string message)
        {
            MIS_BASE.Write_FixAllow(opName, false);
            MIS_BASE.Write_TagValueByTagTypeID(34, opName, true);
            SendMessage.AsyncSendMessage_Notice(opName, "【" + opName + "】" + message);
            MisDataFun.LogRecording_OP(opName, "ERROR", "EngineTypeGetOver", message);
        }
    }
}
