使用操作插件把附件反写到上游单据原创
12人赞赏了该文章
2,462次浏览
编辑于2021年08月24日 10:36:11
1、说明
单据A携带“单据A附件”下推生成单据B,单据B新增附件“单据B附件”,并下推生成单据C,单据C新增附件“单据C附件”之后,点击保存或审核,把“单据B附件”和"单据C附件”反写到单据A。
2. 编写操作插件,并在保存操作上注册插件,如下图:
3. 运行效果
4. 操作插件代码
using System; using System.Collections.Generic; using System.ComponentModel; using System.Linq; using System.Text; using System.Data; using Kingdee.BOS.Contracts; using Kingdee.BOS.Core; using Kingdee.BOS.Core.DynamicForm.PlugIn; using Kingdee.BOS.Core.Interaction; using Kingdee.BOS.Core.DynamicForm; using Kingdee.BOS.Core.DynamicForm.PlugIn.Args; using Kingdee.BOS.Util; using Kingdee.BOS.Orm.DataEntity; using Kingdee.BOS.Core.Metadata.EntityElement; using Kingdee.BOS.App.Data; using Kingdee.BOS.Core.BusinessFlow.ServiceArgs; using Kingdee.BOS.App.Core.BusinessFlow; using Kingdee.BOS.BusinessEntity.BusinessFlow; using Kingdee.BOS.Core.Metadata; using Kingdee.BOS.App.Core; using Kingdee.BOS.Core.SqlBuilder; using Kingdee.BOS.App.Core.Query; using Kingdee.BOS.Core.Metadata.FieldElement; namespace Kingdee.BOS.TestPlugIn.FormOperationPlugIn { [HotUpdate] [Description("单据操作插件")] public class BillAOperationPlugIn : AbstractOperationServicePlugIn { /// <summary> /// 在操作事务后处理 /// </summary> /// <param name="e"></param> public override void AfterExecuteOperationTransaction(AfterExecuteOperationTransaction e) { base.AfterExecuteOperationTransaction(e); //得到所有保存操作成功的数据 var succIndexs = this.OperationResult.OperateResult.Where(x => x.SuccessStatus).Select(x => x.DataEntityIndex); if (succIndexs.Count() == 0) return; List<DynamicObject> succObjs = new List<DynamicObject>(); foreach (var index in succIndexs) { succObjs.Add(e.DataEntitys[index]); } //得到所有关联数据 var entity = this.BusinessInfo.GetEntity("FEntity1"); var formId = this.BusinessInfo.GetForm().Id; var dicPkIdAndEntityId = this.GetEntityPkIds(succObjs, entity); List<long> relateEntityPkIds = new List<long>(); dicPkIdAndEntityId.Values.ToList().ForEach(x => relateEntityPkIds.AddRange(x)); StringBuilder sql = new StringBuilder(); var bfMetaService = new BusinessFlowMetadataService(); List<BusinessFlowTracker> allTrack = new List<BusinessFlowTracker>(); using (SessionScope scope = new SessionScope()) { BusinessFlowDataService bfService = new BusinessFlowDataService(); var instArgs = new ReadInstDatasWithHisArgs("KKK_BillC", "FEntity1", relateEntityPkIds.ToArray()); instArgs.IsGetInst = false; instArgs.IsGetAmount = false; var bfResult = bfService.LoadInstDatasWithHis(this.Context, instArgs); var trackType = new BusinessFlowTrackerType(BOSTableConst.BF_Instance, BOSTableConst.BF_InstanceEntry, BOSTableConst.BF_InstanceAmount); ; sql.AppendFormat("SELECT FRouteId,FInstanceId,FSTableName,FSID,FTTableName,FTID,FFirstNode FROM {0} ", bfResult.TmpTableEntry); using (IDataReader reader = DBUtils.ExecuteReader(this.Context, sql.ToString())) { while (reader.Read()) { var instanceId = reader["FInstanceId"] as String; var route = new BusinessFlowTracker(new DynamicObject(trackType)); route.InstanceId = instanceId; route.Id = reader["FRouteId"] as String; route.SourceTableName = reader["FSTableName"] as String;//.ToString(); route.SourceId = Convert.ToInt64(reader["FSID"]); route.TargetTableName = reader["FTTableName"] as String; route.TargetId = Convert.ToInt64(reader["FTID"]); route.FirstNode = (reader["FFirstNode"] as String) == "1"; allTrack.Add(route); } } DBUtils.DropSessionTemplateTable(this.Context, bfResult.TmpTableMasterIds); DBUtils.DropSessionTemplateTable(this.Context, bfResult.TmpTableEntry); } if (allTrack.Count > 0) //存在关联数据 { //取到所有单据头附件 var pkIds = succObjs.Select(x => Convert.ToInt64(x["Id"])); Dictionary<long, List<long>> dicBillIDAndAttId = new Dictionary<long, List<long>>(); //单据内码和附件内码的集合 List<SqlParam> lstParam = new List<SqlParam>(); long[] disPkIds = pkIds.Distinct().ToArray(); String sqlWithCard = StringUtils.GetSqlWithCardinality(disPkIds.Length, "@PkId", 1); lstParam.Add(new SqlParam("@PkId", KDDbType.udt_inttable, disPkIds)); lstParam.Add(new SqlParam("@FormId", KDDbType.AnsiString, formId)); var sql1 = string.Format("select t0.FID,t0.FINTERID from T_BAS_ATTACHMENT t0 INNER JOIN {0} t1 ON t0.FInterId=t1.FID " + "Where t0.FBillType =@FormId and t0.FEntryInterId = '-1' ", sqlWithCard); using (IDataReader reader1 = DBUtils.ExecuteReader(this.Context, sql1, lstParam)) { while (reader1.Read()) { var billId = Convert.ToInt64(reader1["FINTERID"]); var attachId = Convert.ToInt64(reader1["FID"]); if (dicBillIDAndAttId.ContainsKey(billId)) { dicBillIDAndAttId[billId].Add(attachId); } else { dicBillIDAndAttId[billId] = new List<long>() { attachId }; } } } //得到所有单据C对应的单据A TableDefine billATableDefine = bfMetaService.LoadTableDefine(this.Context, "KKK_BillA", "FEntity"); TableDefine billCTableDefine = bfMetaService.LoadTableDefine(this.Context, "KKK_BillC", "FEntity1"); Dictionary<long, List<long>> dicBillCPKIdAndBillAEntityId = new Dictionary<long, List<long>>(); foreach (var item in dicPkIdAndEntityId) { List<string> cId = new List<string>(); item.Value.ForEach(x => cId.Add(billCTableDefine.TableNumber + "," + x.ToString())); var filterInstanceIds = allTrack.Where(x => cId.Contains(x.TargetCId)).Select(x=>x.InstanceId); dicBillCPKIdAndBillAEntityId[item.Key]= allTrack.Where(x => filterInstanceIds.Contains(x.InstanceId) && x.SourceTableName == billATableDefine.TableNumber).Select(x => x.SourceId).ToList(); } //得到单据A的所有内码 Dictionary<long, List<long>> dicBillCPKIdAndBillAPkId = new Dictionary<long, List<long>>(); var billABInfo = this.LoadBusinessInfo("KKK_BillA"); var pkName = billABInfo.GetForm().PkFieldName; var billAEntity = billABInfo.GetEntity("FEntity"); List<long> billAPKIdId = new List<long>(); if (billAEntity is HeadEntity) //如果是单据头直接等于 { dicBillCPKIdAndBillAPkId = dicBillCPKIdAndBillAEntityId; dicBillCPKIdAndBillAEntityId.Values.ToList().ForEach(x => billAPKIdId.AddRange(x)); } else { List<long> billAEntityId = new List<long>(); dicBillCPKIdAndBillAEntityId.Values.ToList().ForEach(x => billAEntityId.AddRange(x)); var entityPkName = string.Concat(billAEntity.Key, "_", billAEntity.EntryPkFieldName); QueryBuilderParemeter qbParemeter = new QueryBuilderParemeter(); qbParemeter.FormId = billABInfo.GetForm().Id; qbParemeter.SelectItems.Add(new SelectorItemInfo(pkName)); qbParemeter.SelectItems.Add(new SelectorItemInfo(entityPkName)); qbParemeter.FilterClauseWihtKey = string.Format(entityPkName+" in ({0}) ", string.Join(",",billAEntityId.ToArray())); QueryService dataReader = new QueryService(); DynamicObjectCollection rows = dataReader.GetDynamicObjectCollection(this.Context, qbParemeter); foreach (var item in dicBillCPKIdAndBillAEntityId) { var billPkIds= rows.Where(x => item.Value.Contains(Convert.ToInt64(x[entityPkName]))).Select(x =>Convert.ToInt64(x[pkName])).Distinct().ToList(); billAPKIdId.AddRange(billPkIds); dicBillCPKIdAndBillAPkId[item.Key] = billPkIds; } } //把到单据C复制一份到单据A var attBInfo = this.LoadBusinessInfo("BOS_Attachment"); var dynamicType = attBInfo.GetDynamicObjectType(); //附件实体类型 var createTime = (new TimeService()).GetSystemDateTime(this.Context); foreach (var item in dicBillCPKIdAndBillAPkId) { if (dicBillIDAndAttId.ContainsKey(item.Key)) //单据C存在附件 { var attachIds = dicBillIDAndAttId[item.Key]; QueryBuilderParemeter qbParemeter = new QueryBuilderParemeter(); qbParemeter.FormId = attBInfo.GetForm().Id; qbParemeter.FilterClauseWihtKey = string.Format("FINTERID ={0} and FFileId not in( select FFileId from T_BAS_ATTACHMENT where FBILLTYPE='{1}' and FINTERID in ({2}) )", item.Key, billABInfo.GetForm().Id, string.Join(",", item.Value.ToArray())); IViewService viewService = ServiceFactory.GetViewService(this.Context); DynamicObject[] srcDynObjs = viewService.LoadFromCache(this.Context, dynamicType, qbParemeter); if(srcDynObjs.Length ==0) return; //把单据C附件复制到单据A List<DynamicObject> lstTargetObjs = new List<DynamicObject>(); int index = 0; var multiLangField = attBInfo.GetField("FAttachmentDes"); foreach (var billAPkid in item.Value) { foreach (var srcObj in srcDynObjs) { var pkId = ObjectUtils.Object2Int(srcObj["Id"]); var targetObj = new DynamicObject(dynamicType); targetObj["BillType"] = billABInfo.GetForm().Id; targetObj["InterID"] = billAPkid; targetObj["EntryInterID"] = -1; targetObj["EntryKey"] = ""; targetObj["CreateTime"] = createTime; targetObj["AttachmentSize"] = srcObj["AttachmentSize"]; targetObj["AttachmentName"] = srcObj["AttachmentName"]; targetObj["AttachmentDes"] = srcObj["AttachmentDes"]; targetObj["FBillStatus"] = "A"; targetObj["Attachment"] = srcObj["Attachment"]; targetObj["CreateMen_Id"] = ObjectUtils.Object2Int(this.Context.UserId); targetObj["FileId"] = srcObj["FileId"]; targetObj["AliasFileName"] = srcObj["AliasFileName"]; targetObj["ExtName"] = srcObj["ExtName"]; targetObj["FileStorage"] = srcObj["FileStorage"]; targetObj["IsAllowDownLoad"] = ObjectUtils.Object2Bool(srcObj["IsAllowDownLoad"]); var srcMultiLangObjs = srcObj["MultiLanguageText"] as LocalDynamicObjectCollection; var targetMultiLangObjs = targetObj["MultiLanguageText"] as LocalDynamicObjectCollection; if (!srcMultiLangObjs.IsEmpty() && targetMultiLangObjs != null) { targetMultiLangObjs.Clear(); // var lstMultiSeq = seqReader.GetSequence<Int32>("T_BAS_ATTACHMENT_L", srcMultiLangObjs.Count).ToList(); int subIndex = 0; foreach (var multiObj in srcMultiLangObjs) { var targetMutilLangObj = new DynamicObject(multiObj.DynamicObjectType); // targetMutilLangObj["PkId"] = lstMultiSeq[subIndex]; targetMutilLangObj["LocaleId"] = ObjectUtils.Object2Int(multiObj["LocaleId"]); targetMutilLangObj[multiLangField.PropertyName] = ObjectUtils.Object2String(multiObj[multiLangField.PropertyName]); targetMultiLangObjs.Add(targetMutilLangObj); subIndex++; } } lstTargetObjs.Add(targetObj); index++; } } SaveService saveService = new SaveService(); saveService.Save(this.Context, attBInfo, lstTargetObjs.ToArray(), null); } } } } /// <summary> /// 加载单据的元数据包 /// </summary> /// <param name="formId"></param> /// <returns></returns> private BusinessInfo LoadBusinessInfo(string formId) { IMetaDataService service = new MetaDataService(); var metadata = service.Load(this.Context, formId) as FormMetadata; return metadata.BusinessInfo; } /// <summary> /// 得到关联实体内码 /// </summary> /// <param name="dataObjects"></param> /// <param name="entity"></param> /// <returns></returns> private Dictionary<long, List<long>> GetEntityPkIds(List<DynamicObject> dataObjects, Entity entity) { Dictionary<long, List<long>> dicPKId = new Dictionary<long, List<long>>(); foreach (var dataObj in dataObjects) { var pkId =Convert.ToInt64( dataObj[0]); if (entity is HeadEntity)//实体为单据头 { dicPKId[pkId] = new List<long>() { pkId }; } else//实体为单据体或子单据头 { var dynObjs = (DynamicObjectCollection)entity.DynamicProperty.GetValue(dataObj); dicPKId[pkId] = dynObjs.Select(x => Convert.ToInt64(x[0])).ToList(); } } return dicPKId; } } }
赞 12
12人点赞
还没有人点赞,快来当第一个点赞的人吧!
打赏
0人打赏
还没有人打赏,快来当第一个打赏的人吧!
推荐阅读