package proj import ( "context" contractDao "dashoo.cn/micro/app/dao/contract" custDao "dashoo.cn/micro/app/dao/cust" projDao "dashoo.cn/micro/app/dao/proj" model "dashoo.cn/micro/app/model/proj" workflowModel "dashoo.cn/micro/app/model/workflow" "dashoo.cn/micro/app/service" workflowService "dashoo.cn/micro/app/service/workflow" "dashoo.cn/opms_libary/myerrors" "dashoo.cn/opms_libary/plugin/dingtalk/message" "dashoo.cn/opms_libary/plugin/dingtalk/workflow" "dashoo.cn/opms_libary/utils" "fmt" "github.com/gogf/gf/database/gdb" "github.com/gogf/gf/frame/g" "github.com/gogf/gf/os/gtime" "github.com/gogf/gf/util/gconv" "github.com/shopspring/decimal" "strconv" "strings" ) type businessService struct { *service.ContextService Dao *projDao.ProjBusinessDao } func NewBusinessService(ctx context.Context) (svc *businessService, err error) { svc = new(businessService) if svc.ContextService, err = svc.Init(ctx); err != nil { return nil, err } svc.Dao = projDao.NewProjBusinessDao(svc.Tenant) return svc, nil } func (p *businessService) GetList(req *model.ProjBusinessSearchReq) (total int, businessList []*model.ProjBusinessRes, err error) { db := p.Dao.As("proj").DataScope(p.Ctx, "sale_id") if req.NboName != "" { db = db.WhereLike("proj."+p.Dao.C.NboName, "%"+req.NboName+"%") } if req.CustName != "" { db = db.WhereLike("proj."+p.Dao.C.CustName, "%"+req.CustName+"%") } if req.SaleName != "" { db = db.WhereLike("proj."+p.Dao.C.SaleName, "%"+req.SaleName+"%") } if req.NboType != "" { db = db.Where("proj."+p.Dao.C.NboType, req.NboType) } if req.BeginTime != "" { db = db.WhereGTE("proj."+p.Dao.C.CreatedTime, req.BeginTime) } if req.EndTime != "" { db = db.WhereLTE("proj."+p.Dao.C.CreatedTime, req.EndTime) } total, err = db.Count() if err != nil { err = myerrors.DbError("获取总行数失败。") return } if req.NboType == StatusDeal { db = db.Unscoped().WhereNull(`proj.deleted_time`). LeftJoin(contractDao.CtrContract.Table, "contract", "`proj`.id=`contract`.nbo_id AND `contract`.`deleted_time` IS NULL "). Fields("`proj`.cust_city_id as cust_city_id,`contract`.contract_amount, `contract`.created_time as proj_closing_time") } db = db.Fields("`proj`.*") err = db.Page(req.PageNum, req.PageSize).OrderDesc("id").Scan(&businessList) return } func (p *businessService) GetEntityById(id int64) (business *model.ProjBusiness, err error) { err = p.Dao.Where(projDao.ProjBusiness.C.Id, id).Scan(&business) return } func (p *businessService) GetBusinessProduct(id int64) (productList []*model.ProjBusinessProduct, err error) { productDao := projDao.NewProjBusinessProductDao(p.Tenant) err = productDao.Where(productDao.ProjBusinessProductDao.C.BusId, id).Scan(&productList) return } func (p *businessService) GetBusinessDynamics(req *model.BusinessReq) (total int, result g.MapStrAny, err error) { result = make(g.MapStrAny, 0) dynamicsDao := projDao.NewProjBusinessDynamicsDao(p.Tenant).ProjBusinessDynamicsDao.Where(projDao.ProjBusinessDynamics.C.BusId, req.BusId) total, err = dynamicsDao.Count() if err != nil { g.Log().Error(err) return } dynamicsList, err := dynamicsDao.Page(req.GetPage()).Order("created_time desc").All() if err != nil || dynamicsList == nil { return } // 数据树格式转换 opnDateFlag := gtime.New(dynamicsList[0].OpnDate).Format("Y-m-d") for k, v := range dynamicsList { opnDate := gtime.New(v.OpnDate).Format("Y-m-d") if opnDateFlag == opnDate && k != 0 { result[opnDate] = append(result[opnDate].(g.ListStrAny), g.Map{ "opnPeople": v.OpnPeople, "opnDate": v.OpnDate, "opnType": v.OpnType, "remark": v.Remark, "opnContent": gconv.Map(v.OpnContent), }) } else { temp := make(g.ListStrAny, 0) temp = append(temp, g.Map{ "opnPeople": v.OpnPeople, "opnDate": v.OpnDate, "opnType": v.OpnType, "remark": v.Remark, "opnContent": gconv.Map(v.OpnContent), }) result[opnDate] = temp } } return } func (p *businessService) GetBusinessDynamicsList(req *model.BusinessDynamicsReq) (total int, list []map[string]interface{}, err error) { dynamicsDao := projDao.NewProjBusinessDynamicsDao(p.Tenant).Where(projDao.ProjBusinessDynamics.C.BusId, req.BusId) if req.OpnType != "" { dynamicsDao = dynamicsDao.Where(projDao.ProjBusinessDynamics.C.OpnType+" = ?", req.OpnType) } total, err = dynamicsDao.Count() if err != nil { g.Log().Error(err) return } dynamicsList, err := dynamicsDao.Page(req.GetPage()).Order("created_time desc").All() for _, v := range dynamicsList { val := gconv.Map(v) val["opnContent"] = gconv.Map(v.OpnContent) list = append(list, val) } return } // 获取项目编号 func (s *businessService) getNboCode(customerCode string) (string, error) { sequence, err := service.Sequence(s.Dao.DB, "nbo_code") if err != nil { return "", err } return customerCode + sequence, nil } func (p *businessService) Create(req *model.AddProjBusinessReq) (err error) { // 获取客户信息 customer, err := custDao.NewCustCustomerDao(p.Tenant).WherePri(req.CustId).One() if err != nil { return err } if customer == nil { return myerrors.TipsError("客户不存在") } // 设置默认联系人 contact := g.Map{ projDao.ProjBusinessContact.C.ContactId: req.ContactId, } service.SetCreatedInfo(contact, p.GetCxtUserId(), p.GetCxtUserName()) // 设置产品信息 totalPrice, products, err := p.setProductInfo(0, req.Products) if err != nil { return err } // 获取项目编号 nboCode, err := p.getNboCode(customer.CustCode) if err != nil { return err } // 初始化项目信息 businessData := new(model.ProjBusiness) if err = gconv.Struct(req, businessData); err != nil { return } businessData.NboCode = nboCode //businessData.NboStatus = StatusOK businessData.NboType = StatusC businessData.ApproStatus = ApprovalNotSubmit businessData.EstTransPrice = totalPrice businessData.CustProvinceId = customer.CustProvinceId businessData.CustProvince = customer.CustProvince businessData.CustCityId = customer.CustCityId businessData.CustCity = customer.CustCity businessData.CustRegionId = customer.CustRegionId businessData.CustRegion = customer.CustRegion businessData.DeptId = p.GetCxtUserDeptId() service.SetCreatedInfo(businessData, p.GetCxtUserId(), p.GetCxtUserName()) // 事务 err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 添加项目 lastId, err := p.Dao.TX(tx).InsertAndGetId(businessData) if err != nil { return err } // 创建了联系人 contact[projDao.ProjBusinessContact.C.BusId] = lastId _, err = projDao.NewProjBusinessContactDao(p.Tenant).TX(tx).Insert(contact) if err != nil { return err } // 处理项目产品信息 for _, v := range products { v.BusId = int(lastId) } // 添加项目产品 _, err = projDao.NewProjBusinessProductDao(p.Tenant).TX(tx).Insert(products) if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: int(lastId), OpnType: OpnCreate, Remark: businessData.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, businessData) return err }) return } // setProductInfo 设置产品信息 func (p *businessService) setProductInfo(busId int, productInfo []model.BusinessProduct) (total float64, products []*model.ProjBusinessProduct, err error) { products = make([]*model.ProjBusinessProduct, len(productInfo)) if err = gconv.Structs(productInfo, &products); err != nil { return 0, nil, err } var totalPrice decimal.Decimal for _, v := range products { v.Id = 0 v.BusId = busId v.TotalPrice = decimal.NewFromFloat(v.ProdPrice).Mul(decimal.NewFromInt(int64(v.ProdNum))).InexactFloat64() totalPrice = totalPrice.Add(decimal.NewFromFloat(v.TotalPrice)) service.SetCreatedInfo(v, p.GetCxtUserId(), p.GetCxtUserName()) } return totalPrice.InexactFloat64(), products, nil } func (p *businessService) UpdateById(req *model.UpdateProjBusinessReq) error { record, err := p.Dao.WherePri(req.Id).Count() if err != nil { return err } if record == 0 { return myerrors.TipsError("项目不存在。") } // 设置产品信息 totalPrice, products, err := p.setProductInfo(req.Id, req.Products) if err != nil { return err } // 设置默认联系人 contact := g.Map{ projDao.ProjBusinessContact.C.BusId: req.Id, projDao.ProjBusinessContact.C.ContactId: req.ContactId, } contactFlag, err := projDao.NewProjBusinessContactDao(p.Tenant).Where(contact).Count() if err != nil { return err } if contactFlag == 0 { service.SetCreatedInfo(contact, p.GetCxtUserId(), p.GetCxtUserName()) } // 设置项目信息 req.EstTransPrice = totalPrice businessData := gconv.Map(req) service.SetUpdatedInfo(businessData, p.GetCxtUserId(), p.GetCxtUserName()) err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目 _, err = p.Dao.TX(tx).FieldsEx(service.UpdateFieldEx...).WherePri(projDao.ProjBusiness.C.Id, req.Id).Update(businessData) if err != nil { return err } // 删除项目产品 _, err = projDao.NewProjBusinessProductDao(p.Tenant).TX(tx).Where(projDao.ProjBusinessProduct.C.BusId, req.Id).Delete() if err != nil { return err } // 添加项目产品 _, err = projDao.NewProjBusinessProductDao(p.Tenant).TX(tx).Insert(products) if err != nil { return err } // 关联联系人 if contactFlag == 0 { _, err = projDao.NewProjBusinessContactDao(p.Tenant).TX(tx).Insert(contact) if err != nil { return err } } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: req.Id, OpnType: OpnUpdate, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, req) return err }) return err } func (p *businessService) DeleteByIds(ids []int64) (err error) { _, err = p.Dao.WhereIn(projDao.ProjBusiness.C.Id, ids).Delete() return } // BusinessTransfer 项目转移 func (p *businessService) BusinessTransfer(req *model.BusinessTransferReq) error { business, err := p.Dao.WherePri(req.Id).WhereNot(p.Dao.C.ApproStatus, ApprovalWaiting).One() if err != nil { return err } if business == nil { return myerrors.TipsError("项目已提交审批任务,无法重复提交。") } businessMap := g.Map{ p.Dao.C.ApproStatus: ApprovalWaiting, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) opnContent := businessMap opnContent["origSaleId"] = business.SaleId opnContent["origSaleName"] = business.SaleName opnContent["saleId"] = req.UserId opnContent["saleName"] = req.UserName opnContent["remark"] = req.Remark // 审批流 workflowSrv, _ := workflowService.NewFlowService(p.Ctx) err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目 _, err = p.Dao.TX(tx).WherePri(projDao.ProjBusiness.C.Id, req.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: req.Id, OpnType: OpnTransfer, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, opnContent) if err != nil { g.Log().Error(err) return err } // OMS项目转移 审批 bizCode := business.NboCode + ":" + strconv.Itoa(business.Id) _, err = workflowSrv.StartProcessInstance(bizCode, workflowModel.ProjectTransfer, "", &workflow.StartProcessInstanceRequest{ ProcessCode: &BusinessTransferRequestProcessCode, FormComponentValues: []*workflow.StartProcessInstanceRequestFormComponentValues{ { Id: utils.String("TextField-K2AD4O5B"), Name: utils.String("项目编码"), Value: utils.String(business.NboCode), }, { Id: utils.String("TextField_7EFHRQ9DDF80"), Name: utils.String("项目名称"), Value: utils.String(business.NboName), }, { Id: utils.String("TextField_1T3DEY5FWV7K0"), Name: utils.String("客户名称"), Value: utils.String(business.CustName), }, { Id: utils.String("TextField_QDU06LXYKK00"), Name: utils.String("所在省"), Value: utils.String(business.CustProvince), }, { Id: utils.String("TextField_MVSOO6EG6YO0"), Name: utils.String("所在市"), Value: utils.String(business.CustCity), }, { Id: utils.String("TextField_1E1WOYGKRTDS0"), Name: utils.String("项目级别"), Value: utils.String(nboType[business.NboType]), }, { Id: utils.String("TextField_NRQXWLJ17HC0"), Name: utils.String("申请人"), Value: utils.String(p.GetCxtUserName()), }, { Id: utils.String("TextField_GHSQYDGD13K0"), Name: utils.String("转移原因"), Value: utils.String(req.Remark), }, { Id: utils.String("TextField_76P8FPHH0UC0"), Name: utils.String("接收人"), Value: utils.String(req.UserName), }, }, }) if err != nil { g.Log().Error(err) return err } return nil }) return err } // BusinessTransferNotify 项目转移 审批结果通知 func (p *businessService) BusinessTransferNotify(flow *workflowModel.PlatWorkflow, msg *message.MixMessage) error { business, err := p.checkDingTalkNotify(flow, msg) if err != nil { return err } var data = g.Map{} if msg.ProcessType == "terminate" { data[p.Dao.C.ApproStatus] = ApprovalReturn } if msg.ProcessType == "finish" && msg.Result != "refuse" { data[p.Dao.C.ApproStatus] = ApprovalRejection } if msg.ProcessType == "finish" && msg.Result == "agree" { // 从项目动态内获取变更信息 var transferDynamics model.ProjBusinessDynamics dynamicsDao := projDao.NewProjBusinessDynamicsDao(p.Tenant).Where(projDao.ProjBusinessDynamics.C.BusId, business.Id) err = dynamicsDao.Where(projDao.ProjBusinessDynamics.C.OpnType, OpnTransfer).OrderDesc("created_time").Scan(&transferDynamics) if err != nil { return err } changeData := gconv.Map(transferDynamics.OpnContent) data[p.Dao.C.SaleId] = changeData["saleId"] data[p.Dao.C.SaleName] = changeData["saleName"] data[p.Dao.C.Remark] = changeData["remark"] data[p.Dao.C.ApproStatus] = ApprovalOK } // 项目修改 _, err = p.Dao.WherePri(business.Id).FieldsEx(service.UpdateFieldEx...).Data(data).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnTransferApproval, } err = p.CreateProjBusinessDynamics(nil, dynamics, data) if err != nil { return err } return err } // BusinessGradation 项目调级 func (p *businessService) BusinessGradation(busId int, nboType, busType string) (*model.ProjBusiness, error) { business, err := p.Dao.WherePri(busId).WhereNot(p.Dao.C.ApproStatus, ApprovalWaiting).One() if err != nil { return nil, err } if business == nil { return nil, myerrors.TipsError("项目已提交审批任务,无法重复提交。") } if business.NboType == nboType { return nil, myerrors.TipsError("同级别无法进行调级。") } if business.NboType == StatusDeal { return nil, myerrors.TipsError("成交项目无法进行调级。") } if business.NboType == StatusReserve && nboType == StatusDeal { return nil, myerrors.TipsError("储备项目无法直接转为成交项目。") } if busType == "up" && gconv.Int(business.NboType) < gconv.Int(nboType) { return nil, myerrors.TipsError("项目级别错误。") } if busType == "down" && gconv.Int(business.NboType) > gconv.Int(nboType) { return nil, myerrors.TipsError("项目级别错误。") } return business, err } // BusinessUpgrade 项目升级 func (p *businessService) BusinessUpgrade(req *model.BusinessUpgradeReq) error { business, err := p.BusinessGradation(req.Id, req.NboType, "up") if err != nil { return err } var upgradeType string switch true { case business.NboType == StatusC && req.NboType == StatusB: upgradeType = "option_0" case business.NboType == StatusB && req.NboType == StatusA: upgradeType = "option_1" case business.NboType == StatusC && req.NboType == StatusA: upgradeType = "option_2" default: return myerrors.TipsError("错误的升级类型") } fmt.Println(upgradeType) businessMap := g.Map{ p.Dao.C.ApproStatus: ApprovalWaiting, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) opnContent := gconv.Map(req) opnContent["origNboType"] = business.NboType opnContent["approStatus"] = ApprovalWaiting service.SetUpdatedInfo(opnContent, p.GetCxtUserId(), p.GetCxtUserName()) // 审批流 workflowSrv, _ := workflowService.NewFlowService(p.Ctx) err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目调级 _, err = p.Dao.TX(tx).WherePri(req.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnUpgrade, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, opnContent) if err != nil { return err } // OMS项目降级 审批 bizCode := business.NboCode + ":" + strconv.Itoa(business.Id) _, err = workflowSrv.StartProcessInstance(bizCode, workflowModel.ProjectUpGrade, "", &workflow.StartProcessInstanceRequest{ ProcessCode: &BusinessUpgradeRequestProcessCode, FormComponentValues: []*workflow.StartProcessInstanceRequestFormComponentValues{ { Id: utils.String("TextField-K2AD4O5B"), Name: utils.String("项目编码"), Value: utils.String(business.NboCode), }, { Id: utils.String("TextField_BDLSECETVSG0"), Name: utils.String("项目名称"), Value: utils.String(business.NboName), }, { Id: utils.String("DDSelectField_VSA3U380ZK00"), Name: utils.String("升级类型"), Value: utils.String(upgradeType), }, { Id: utils.String("TextField_1J9BJMOZ18F40"), Name: utils.String("客户名称"), Value: utils.String(business.CustName), }, { Id: utils.String("NumberField_1F88MCD0W8KG0"), Name: utils.String("项目预算"), Value: utils.String(gconv.String(req.NboBudget)), }, { Id: utils.String("TextField_1PWK6WHMGITC0"), Name: utils.String("经销商/代理商"), Value: utils.String(req.DistributorName), }, { Id: utils.String("TextField_X4D3QGARU7K0"), Name: utils.String("支持内容"), Value: utils.String(req.TechnicalSupportContent), }, { Id: utils.String("TextField_AEUWH63LJ0O0"), Name: utils.String("销售工程师"), Value: utils.String(business.SaleName), }, { Id: utils.String("DDDateField_1FW1QZQYBZVK0"), Name: utils.String("采购时间"), Value: utils.String(gconv.String(req.PurchasingTime.Format("Y-m-d"))), }, { Id: utils.String("DDSelectField_21ASEWDIB3MO0"), Name: utils.String("采购方式"), Value: utils.String(gconv.String(purchasingWayType[req.PurchasingWay])), }, { Id: utils.String("DDSelectField_5R11VVM6GI00"), Name: utils.String("是否我司参数"), Value: utils.String(gconv.String(yesOrNoType[req.IsAdoptDashoo])), }, }, }) if err != nil { g.Log().Error(err) return err } return err }) return err } // BusinessUpgradeNotify 项目降级 审批结果通知 func (p *businessService) BusinessUpgradeNotify(flow *workflowModel.PlatWorkflow, msg *message.MixMessage) error { business, err := p.checkDingTalkNotify(flow, msg) if err != nil { return err } var data = g.Map{} if msg.ProcessType == "terminate" { data[p.Dao.C.ApproStatus] = ApprovalReturn } if msg.ProcessType == "finish" && msg.Result != "refuse" { data[p.Dao.C.ApproStatus] = ApprovalRejection } if msg.ProcessType == "finish" && msg.Result == "agree" { // 从项目动态内获取变更信息 dynamics := new(model.ProjBusinessDynamics) dynamicsDao := projDao.NewProjBusinessDynamicsDao(p.Tenant).Where(projDao.ProjBusinessDynamics.C.BusId, business.Id) err = dynamicsDao.Where(projDao.ProjBusinessDynamics.C.OpnType, OpnUpgrade).OrderDesc("created_time").Scan(dynamics) if err != nil { return err } updateData := new(model.BusinessUpgradeReq) gconv.Struct(dynamics.OpnContent, updateData) data = gconv.Map(updateData) data[p.Dao.C.ApproStatus] = ApprovalOK } // 项目修改 _, err = p.Dao.WherePri(business.Id).FieldsEx(service.UpdateFieldEx...).Data(data).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnUpgradeApproval, } err = p.CreateProjBusinessDynamics(nil, dynamics, data) if err != nil { return err } return nil } // BusinessDowngrade 项目降级 func (p *businessService) BusinessDowngrade(req *model.BusinessDowngradeReq) error { business, err := p.BusinessGradation(req.Id, req.NboType, "down") if err != nil { return err } var downgradeType string switch true { case business.NboType == StatusB && req.NboType == StatusC: downgradeType = "option_0" case business.NboType == StatusA && req.NboType == StatusB: downgradeType = "option_1" case business.NboType == StatusA && req.NboType == StatusC: downgradeType = "option_2" case business.NboType == StatusA && req.NboType == StatusReserve: downgradeType = "option_YZMFJYQQK6O0" default: return myerrors.TipsError("错误的降级类型") } businessMap := g.Map{ p.Dao.C.ApproStatus: ApprovalWaiting, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) opnContent := gconv.Map(req) opnContent["origNboType"] = business.NboType opnContent["approStatus"] = ApprovalWaiting service.SetUpdatedInfo(opnContent, p.GetCxtUserId(), p.GetCxtUserName()) // 审批流 workflowSrv, _ := workflowService.NewFlowService(p.Ctx) err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目调级 _, err = p.Dao.TX(tx).WherePri(req.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnDowngrade, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, opnContent) if err != nil { return err } // OMS项目降级 审批 bizCode := business.NboCode + ":" + strconv.Itoa(business.Id) _, err = workflowSrv.StartProcessInstance(bizCode, workflowModel.ProjectDownGrade, "", &workflow.StartProcessInstanceRequest{ ProcessCode: &BusinessDowngradeRequestProcessCode, FormComponentValues: []*workflow.StartProcessInstanceRequestFormComponentValues{ { Id: utils.String("TextField-K2AD4O5B"), Name: utils.String("项目编码"), Value: utils.String(business.NboCode), }, { Id: utils.String("TextField_BDLSECETVSG0"), Name: utils.String("项目名称"), Value: utils.String(business.NboName), }, { Id: utils.String("TextField_1J9BJMOZ18F40"), Name: utils.String("客户名称"), Value: utils.String(business.CustName), }, { Id: utils.String("TextField_GL7MQUB723K0"), Name: utils.String("所在省"), Value: utils.String(business.CustProvince), }, { Id: utils.String("TextField_CFA88QQQUUO0"), Name: utils.String("所在市"), Value: utils.String(business.CustCity), }, { Id: utils.String("DDSelectField_VSA3U380ZK00"), Name: utils.String("降级类型"), Value: utils.String(downgradeType), }, { Id: utils.String("TextField_X4D3QGARU7K0"), Name: utils.String("支持内容"), Value: utils.String(req.TechnicalSupportContent), }, { Id: utils.String("TextField_AEUWH63LJ0O0"), Name: utils.String("销售工程师"), Value: utils.String(business.SaleName), }, { Id: utils.String("TextareaField_PTGJOKD3J7K0"), Name: utils.String("降级原因"), Value: utils.String(req.Remark), }, }, }) if err != nil { g.Log().Error(err) return err } return nil }) return err } // BusinessDowngradeNotify 项目降级 审批结果通知 func (p *businessService) BusinessDowngradeNotify(flow *workflowModel.PlatWorkflow, msg *message.MixMessage) error { business, err := p.checkDingTalkNotify(flow, msg) if err != nil { return err } var data = g.Map{} if msg.ProcessType == "terminate" { data[p.Dao.C.ApproStatus] = ApprovalReturn } if msg.ProcessType == "finish" && msg.Result != "refuse" { data[p.Dao.C.ApproStatus] = ApprovalRejection } if msg.ProcessType == "finish" && msg.Result == "agree" { // 从项目动态内获取变更信息 dynamics := new(model.ProjBusinessDynamics) dynamicsDao := projDao.NewProjBusinessDynamicsDao(p.Tenant).Where(projDao.ProjBusinessDynamics.C.BusId, business.Id) err = dynamicsDao.Where(projDao.ProjBusinessDynamics.C.OpnType, OpnDowngrade).OrderDesc("created_time").Scan(dynamics) if err != nil { return err } updateData := new(model.BusinessDowngradeReq) gconv.Struct(dynamics.OpnContent, updateData) data = gconv.Map(updateData) data[p.Dao.C.ApproStatus] = ApprovalOK } // 项目修改 _, err = p.Dao.WherePri(business.Id).FieldsEx(service.UpdateFieldEx...).Data(data).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnDowngradeApproval, } err = p.CreateProjBusinessDynamics(nil, dynamics, data) if err != nil { return err } return nil } // SetPrimacyContact 项目设置首要联系人 func (p *businessService) SetPrimacyContact(req *model.BusinessPrimacyContactReq) (err error) { business, err := p.Dao.Where(projDao.ProjBusiness.C.Id, req.Id).One() if err != nil { return err } if business == nil { return myerrors.TipsError("项目不存在。") } businessMap := g.Map{ p.Dao.C.ContactId: req.ContactId, p.Dao.C.ContactName: req.ContactName, p.Dao.C.ContactPostion: req.ContactPostion, p.Dao.C.ContactTelephone: req.ContactTelephone, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) opnContent := businessMap opnContent["origContactId"] = business.ContactId opnContent["origContactName"] = business.ContactName opnContent["origContactPostion"] = business.ContactPostion opnContent["origContactTelephone"] = business.ContactTelephone err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目 _, err = p.Dao.TX(tx).WherePri(projDao.ProjBusiness.C.Id, req.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: req.Id, OpnType: OpnPrimacyContact, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, opnContent) return err }) return err } // UpdateBusinessStatus 更新项目状态 func (p *businessService) UpdateBusinessStatus(req *model.UpdateBusinessStatusReq) error { business, err := p.Dao.WherePri(req.Id).One() if err != nil { return err } if business == nil { return myerrors.TipsError("项目不存在。") } businessMap := g.Map{ p.Dao.C.NboStatus: req.NboStatus, p.Dao.C.Remark: req.Remark, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) opnContent := businessMap opnContent["origNboStatus"] = business.NboStatus err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目 _, err = p.Dao.TX(tx).WherePri(projDao.ProjBusiness.C.Id, req.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: req.Id, OpnType: OpnStatus, Remark: req.Remark, } err = p.CreateProjBusinessDynamics(tx, dynamics, opnContent) return err }) return err } // CreateProjBusinessDynamics 创建项目动态 func (p *businessService) CreateProjBusinessDynamics(tx *gdb.TX, dynamics model.ProjBusinessDynamics, opnContent interface{}) error { if v, ok := opnContent.(g.Map); ok { opnContent = utils.MapKeySnakeCamelCase(v) } // 添加项目动态 dynamics.OpnPeopleId = p.GetCxtUserId() dynamics.OpnPeople = p.GetCxtUserName() dynamics.OpnDate = gtime.Now() dynamics.OpnContent = gconv.String(opnContent) service.SetCreatedInfo(&dynamics, p.GetCxtUserId(), p.GetCxtUserName()) dao := projDao.NewProjBusinessDynamicsDao(p.Tenant).M if tx != nil { dao = dao.TX(tx) } _, err := dao.Insert(&dynamics) return err } // ConvertToReserve 转为储备项目 func (p *businessService) ConvertToReserve(req *model.BusinessToReserveReq) error { business, err := p.Dao.WherePri(req.Id).WhereNot(p.Dao.C.ApproStatus, ApprovalWaiting).One() if err != nil { return err } if business == nil { return myerrors.TipsError("项目已提交审批任务,无法重复提交。") } // 审批流 workflowSrv, _ := workflowService.NewFlowService(p.Ctx) err = p.Dao.Transaction(context.TODO(), func(ctx context.Context, tx *gdb.TX) error { // 更新项目 businessMap := g.Map{ p.Dao.C.ApproStatus: ApprovalWaiting, p.Dao.C.ProjConversionTime: gtime.Now(), p.Dao.C.ProjConversionReason: req.ProjConversionReason, } service.SetUpdatedInfo(businessMap, p.GetCxtUserId(), p.GetCxtUserName()) _, err = p.Dao.TX(tx).WherePri(business.Id).Data(businessMap).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnToReserve, Remark: req.ProjConversionReason, } err = p.CreateProjBusinessDynamics(tx, dynamics, businessMap) if err != nil { return err } // OMS项目转储备 审批 bizCode := business.NboCode + ":" + strconv.Itoa(business.Id) _, err = workflowSrv.StartProcessInstance(bizCode, workflowModel.ProjectToReserve, "", &workflow.StartProcessInstanceRequest{ ProcessCode: &ConvertToReserveRequestProcessCode, FormComponentValues: []*workflow.StartProcessInstanceRequestFormComponentValues{ { Id: utils.String("TextField-K2AD4O5B"), Name: utils.String("项目编码"), Value: utils.String(business.NboCode), }, { Id: utils.String("TextField_CMH6TBXYR5S0"), Name: utils.String("项目名称"), Value: utils.String(business.NboName), }, { Id: utils.String("TextField_YQBGGYHQPS00"), Name: utils.String("客户名称"), Value: utils.String(business.CustName), }, { Id: utils.String("TextField_57000M1HBVO0"), Name: utils.String("项目级别"), Value: utils.String(nboType[business.NboType]), }, { Id: utils.String("TextField_1NDD3TY8KJB40"), Name: utils.String("销售工程师"), Value: utils.String(business.SaleName), }, { Id: utils.String("TextareaField_15KZFM4YHQ8W0"), Name: utils.String("转化原因"), Value: utils.String(req.ProjConversionReason), }, }, }) if err != nil { g.Log().Error(err) return err } return nil }) return err } // ConvertToReserveNotify 转为储备项目 审批结果通知 func (p *businessService) ConvertToReserveNotify(flow *workflowModel.PlatWorkflow, msg *message.MixMessage) error { business, err := p.checkDingTalkNotify(flow, msg) if err != nil { return err } var data = g.Map{} if msg.ProcessType == "terminate" { data[p.Dao.C.ApproStatus] = ApprovalReturn } if msg.ProcessType == "finish" && msg.Result != "refuse" { data[p.Dao.C.ApproStatus] = ApprovalRejection } if msg.ProcessType == "finish" && msg.Result == "agree" { data[p.Dao.C.NboType] = StatusReserve data[p.Dao.C.ApproStatus] = ApprovalOK } // 项目修改 _, err = p.Dao.WherePri(business.Id).FieldsEx(service.UpdateFieldEx...).Data(data).Update() if err != nil { return err } // 添加项目动态 dynamics := model.ProjBusinessDynamics{ BusId: business.Id, OpnType: OpnToReserveApproval, } err = p.CreateProjBusinessDynamics(nil, dynamics, data) if err != nil { return err } return err } // 钉钉审批通知检查 func (p *businessService) checkDingTalkNotify(flow *workflowModel.PlatWorkflow, msg *message.MixMessage) (*model.ProjBusiness, error) { bizCode := strings.Split(flow.BizCode, ":") if len(bizCode) != 2 { return nil, fmt.Errorf("项目转储备审批 bizCode 不合法:%s Id: %d", flow.BizCode, flow.Id) } nboCode := bizCode[0] busId, err := strconv.Atoi(bizCode[1]) if err != nil { return nil, fmt.Errorf("项目转储备审批 bizCode 不合法:%s Id: %d", flow.BizCode, flow.Id) } if msg.ProcessType != "finish" && msg.ProcessType != "terminate" { return nil, fmt.Errorf("无法识别的 ProcessType :%s", msg.ProcessType) } if msg.Result != "agree" && msg.Result != "refuse" && msg.Result != "" { return nil, fmt.Errorf("无法识别的 Result :%s", msg.Result) } fmt.Println(msg) business, err := p.Dao.WherePri(busId).Where(p.Dao.C.NboCode, nboCode).One() if err != nil { return nil, err } if business == nil { return nil, fmt.Errorf("项目不存在:%s Id: %d", flow.BizCode, flow.Id) } return business, nil }