contract_register.go 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408
  1. package fms
  2. import (
  3. "errors"
  4. "fmt"
  5. "github.com/shopspring/decimal"
  6. "hongze/fms_api/models/base"
  7. "hongze/fms_api/models/crm"
  8. "hongze/fms_api/models/fms"
  9. "hongze/fms_api/services/alarm_msg"
  10. crmService "hongze/fms_api/services/crm"
  11. "hongze/fms_api/services/resource"
  12. "hongze/fms_api/utils"
  13. "os"
  14. "regexp"
  15. "sort"
  16. "strings"
  17. "time"
  18. )
  19. // CheckContractRegisterAmount 校验合同登记金额-判断是否需要更新合同登记状态
  20. func CheckContractRegisterAmount(registerId int) {
  21. var err error
  22. defer func() {
  23. if err != nil {
  24. alarm_msg.SendAlarmMsg("校验合同登记金额失败, ErrMsg: "+err.Error(), 3)
  25. }
  26. }()
  27. // 获取合同登记信息
  28. cr := new(fms.ContractRegister)
  29. item, e := cr.Fetch(registerId)
  30. if e != nil {
  31. err = errors.New("获取合同登记信息失败, Err: " + e.Error())
  32. return
  33. }
  34. amount := decimal.NewFromFloat(item.ContractAmount).Round(2)
  35. // 获取开票/到款信息
  36. invoiceCond := `contract_register_id = ?`
  37. invoicePars := make([]interface{}, 0)
  38. invoicePars = append(invoicePars, registerId)
  39. ci := new(fms.ContractInvoice)
  40. invoiceList, e := ci.List(invoiceCond, invoicePars, "")
  41. if e != nil {
  42. err = errors.New("获取开票到款信息失败, Err: " + e.Error())
  43. return
  44. }
  45. invoiceAmount := decimal.NewFromFloat(0).Round(2)
  46. paymentAmount := decimal.NewFromFloat(0).Round(2)
  47. for i := range invoiceList {
  48. a := decimal.NewFromFloat(invoiceList[i].OriginAmount).Round(2)
  49. if invoiceList[i].InvoiceType == fms.ContractInvoiceTypeMake {
  50. invoiceAmount = invoiceAmount.Add(a)
  51. }
  52. if invoiceList[i].InvoiceType == fms.ContractInvoiceTypePay {
  53. paymentAmount = paymentAmount.Add(a)
  54. }
  55. }
  56. status := fms.ContractRegisterStatusIng
  57. // 以下情况更新合同登记状态为已完成
  58. // 1.合同存在代付; 2.合同状态为已签回且合同金额=开票金额=到款金额; 3合同状态为已终止
  59. if item.HasInvoice == 0 || (amount.Equal(invoiceAmount) && invoiceAmount.Equal(paymentAmount) && item.ContractStatus == fms.ContractStatusCheckedBack) || item.ContractStatus == fms.ContractStatusEnd {
  60. status = fms.ContractRegisterStatusComplete
  61. }
  62. updateCols := []string{"InvoicedAmount", "PaymentAmount", "RegisterStatus", "ModifyTime"}
  63. ia, _ := invoiceAmount.Round(2).Float64()
  64. pa, _ := paymentAmount.Round(2).Float64()
  65. item.InvoicedAmount = ia
  66. item.PaymentAmount = pa
  67. item.RegisterStatus = status
  68. item.ModifyTime = time.Now().Local()
  69. if e = item.Update(updateCols); e != nil {
  70. err = errors.New("更新合同登记金额及状态失败, Err: " + e.Error())
  71. return
  72. }
  73. return
  74. }
  75. // HandleContractServiceAndDetail 根据请求数据获取套餐服务详情信息
  76. func HandleContractServiceAndDetail(serviceList []fms.ContractServiceAddReq, base642Image bool, serviceAmountMap map[int]float64) (serviceDetailList []*fms.ContractServiceAndDetail, err error) {
  77. serviceDetailList = make([]*fms.ContractServiceAndDetail, 0)
  78. if len(serviceList) < 0 {
  79. err = errors.New("请至少选择一种套餐")
  80. return
  81. }
  82. for i := 0; i < len(serviceList); i++ {
  83. item := serviceList[i]
  84. hasDetail := "否"
  85. // 合同模板
  86. serviceTemp, e := fms.GetContractServiceTemplateById(item.ServiceTemplateId)
  87. if e != nil {
  88. err = errors.New("找不到该模板")
  89. return
  90. }
  91. serviceDetail := &fms.ContractServiceAndDetail{
  92. ServiceTemplateId: item.ServiceTemplateId,
  93. Title: item.Title,
  94. Value: item.Value,
  95. ProductId: serviceTemp.ProductId,
  96. HasDetail: hasDetail,
  97. TableValue: serviceTemp.TableValue,
  98. ChartPermissionId: serviceTemp.ChartPermissionId,
  99. ChartPermissionIds: item.ChartPermissionIds,
  100. //Detail: detailList,
  101. }
  102. serviceDetailList = append(serviceDetailList, serviceDetail)
  103. }
  104. return
  105. }
  106. // HandleContractServiceAmount 根据请求数据获取套餐金额详情信息
  107. func HandleContractServiceAmount(serviceAmountList []fms.ContractServiceAmountAddReq, serviceAmountMap map[int]float64, currencyUnit string) (list []*fms.ContractServiceAmount, err error) {
  108. if len(serviceAmountList) < 0 {
  109. err = errors.New("请至少输入一种套餐金额信息")
  110. return
  111. }
  112. for i := 0; i < len(serviceAmountList); i++ {
  113. item := serviceAmountList[i]
  114. serviceAmountMap[item.ProductId] = item.ServiceAmount
  115. if item.ProductId !=crm.CompanyProductRai && item.ProductId != crm.CompanyProductFicc {
  116. err = errors.New("请选择正确和套餐类型")
  117. return
  118. }
  119. serviceDetail := &fms.ContractServiceAmount{
  120. ProductId: item.ProductId,
  121. ServiceAmount: item.ServiceAmount,
  122. CurrencyUnit: currencyUnit,
  123. TimeBase: base.TimeBase{},
  124. }
  125. list = append(list, serviceDetail)
  126. }
  127. return
  128. }
  129. // GetContractServiceAndDetail 根据合同登记ID获取服务详情
  130. func GetContractServiceAndDetail(contractRegisterId int) (serviceList []*fms.ContractServiceAndDetail, err error) {
  131. list, e := fms.GetContractServiceAndDetailList(contractRegisterId)
  132. if e != nil {
  133. err = errors.New(fmt.Sprint("查找合同服务异常", e))
  134. return
  135. }
  136. serviceList = list
  137. //newLen := len(serviceList)
  138. //for i := 0; newLen > i; i++ {
  139. // if serviceList[i].HasDetail == "是" {
  140. // detail, e := fms.GetContractServiceDetailByServiceId(serviceList[i].ContractServiceId)
  141. // if e != nil {
  142. // err = errors.New(fmt.Sprint("查找合同服务详情异常", e))
  143. // return
  144. // }
  145. // serviceList[i].Detail = detail
  146. // }
  147. //}
  148. return
  149. }
  150. // UploadImageBase64 将base64的图片上传至oss
  151. func UploadImageBase64(base64Str string) (resourceUrl string, err error) {
  152. ext := ".png"
  153. uploadDir := "./static"
  154. randStr := utils.GetRandStringNoSpecialChar(28)
  155. fileName := randStr + ext
  156. fpath := uploadDir + "/" + fileName
  157. b, _ := regexp.MatchString(`^data:\s*image\/(\w+);base64,`, base64Str)
  158. if !b {
  159. err = errors.New("图片格式不正确")
  160. return
  161. }
  162. re, _ := regexp.Compile(`^data:\s*image\/(\w+);base64,`)
  163. base64Str = re.ReplaceAllString(base64Str, "")
  164. base64Str = strings.Replace(base64Str, " ", "", -1)
  165. base64Str = strings.Replace(base64Str, " ", "", -1)
  166. err = utils.SaveBase64ToFile(base64Str, fpath)
  167. if err != nil {
  168. return
  169. }
  170. defer os.Remove(fpath)
  171. savePath := utils.OssUploadImgDir + time.Now().Format("200601/20060102/")
  172. savePath += fileName
  173. // 上传到阿里云
  174. err = resource.UploadVideoAliyun(fileName, fpath, savePath)
  175. if err != nil {
  176. return
  177. }
  178. resourceUrl = utils.OssHost + savePath
  179. return
  180. }
  181. // FixContractInvoiceSellerInfo 修复开票登记销售相关信息(一次性)
  182. func FixContractInvoiceSellerInfo() {
  183. sellerList, e := crmService.GetSellerDepartmentListWithGroupAndTeam()
  184. if e != nil {
  185. fmt.Println("获取销售列表失败, Err: " + e.Error())
  186. return
  187. }
  188. sellerMap := make(map[int]*crm.SellerAdminWithGroupTeam)
  189. for i := range sellerList {
  190. sellerMap[sellerList[i].SellerId] = sellerList[i]
  191. }
  192. registerCond := ``
  193. registerPars := make([]interface{}, 0)
  194. registerOB := new(fms.ContractRegister)
  195. registerList, e := registerOB.List(registerCond, registerPars)
  196. if e != nil {
  197. fmt.Println("获取合同登记列表失败, Err: " + e.Error())
  198. return
  199. }
  200. invUpCols := []string{"SellerId", "SellerName", "SellerGroupId", "SellerGroupName", "SellerTeamId", "SellerTeamName"}
  201. fmt.Println("start 修复")
  202. for i := range registerList {
  203. registerId := registerList[i].ContractRegisterId
  204. sellerId := registerList[i].SellerId
  205. sellerItem := sellerMap[sellerId]
  206. if sellerItem == nil {
  207. fmt.Printf("ID-%d 无销售信息\n", registerId)
  208. continue
  209. }
  210. invOB := new(fms.ContractInvoice)
  211. invCond := `invoice_type = 1 AND contract_register_id = ?`
  212. invPars := make([]interface{}, 0)
  213. invPars = append(invPars, registerId)
  214. invList, e := invOB.List(invCond, invPars, "")
  215. if e != nil {
  216. fmt.Println("获取开票登记列表失败, Err: " + e.Error())
  217. return
  218. }
  219. for _, v := range invList {
  220. v.SellerId = sellerItem.SellerId
  221. v.SellerName = sellerItem.SellerName
  222. v.SellerGroupId = sellerItem.GroupId
  223. v.SellerGroupName = sellerItem.GroupName
  224. v.SellerTeamId = sellerItem.TeamId
  225. v.SellerTeamName = sellerItem.TeamName
  226. if e = v.Update(invUpCols); e != nil {
  227. fmt.Println("更新开票登记失败, Err: " + e.Error())
  228. return
  229. }
  230. fmt.Printf("ID-%d 修复成功\n", v.ContractInvoiceId)
  231. }
  232. }
  233. fmt.Println("end 修复")
  234. return
  235. }
  236. // FixContractInvoicePaymentType 修复历史到款登记付款方式(一次性)
  237. func FixContractInvoicePaymentType() {
  238. registerCond := ``
  239. registerPars := make([]interface{}, 0)
  240. registerOB := new(fms.ContractRegister)
  241. registerList, e := registerOB.List(registerCond, registerPars)
  242. if e != nil {
  243. fmt.Println("获取合同登记列表失败, Err: " + e.Error())
  244. return
  245. }
  246. invUpCols := []string{"PayType"}
  247. fmt.Println("start 修复")
  248. for i := range registerList {
  249. registerId := registerList[i].ContractRegisterId
  250. invOB := new(fms.ContractInvoice)
  251. invCond := `invoice_type = 2 AND contract_register_id = ?`
  252. invPars := make([]interface{}, 0)
  253. invPars = append(invPars, registerId)
  254. invList, e := invOB.List(invCond, invPars, "")
  255. if e != nil {
  256. fmt.Println("获取到款登记列表失败, Err: " + e.Error())
  257. return
  258. }
  259. dayDiff := registerList[i].EndDate.Sub(registerList[i].StartDate).Hours() / 24
  260. for _, v := range invList {
  261. v.PayType = CalculateContractPaymentType(v.Amount, registerList[i].ContractAmount, dayDiff)
  262. if e = v.Update(invUpCols); e != nil {
  263. fmt.Println("更新到款登记付款方式失败, Err: " + e.Error())
  264. return
  265. }
  266. fmt.Printf("ID-%d 修复成功\n", v.ContractInvoiceId)
  267. }
  268. }
  269. fmt.Println("end 修复")
  270. return
  271. }
  272. // FixContractSummaryData 修复开票到款汇总数据(一次性)
  273. func FixContractSummaryData() {
  274. registerCond := ``
  275. registerPars := make([]interface{}, 0)
  276. registerOB := new(fms.ContractRegister)
  277. registerList, e := registerOB.List(registerCond, registerPars)
  278. if e != nil {
  279. fmt.Println("获取合同登记列表失败, Err: " + e.Error())
  280. return
  281. }
  282. fmt.Println("start 修复")
  283. for i := range registerList {
  284. fmt.Printf("正在修复-%d", registerList[i].ContractRegisterId)
  285. SummaryInvoicePaymentByContractRegisterId(registerList[i].ContractRegisterId)
  286. }
  287. fmt.Println("end 修复")
  288. return
  289. }
  290. func GetContractServiceNameFormat(registerIds []int) (serviceNameMap map[int]string, serviceFormatMap map[int][]fms.ContractServiceTemplateFormat, err error) {
  291. serviceNameMap = make(map[int]string)
  292. serviceMap := make(map[int][]string, 0)
  293. serviceFormatMap = make(map[int][]fms.ContractServiceTemplateFormat, 0)
  294. serviceIndustryStr := "医药,消费,科技,智造"
  295. serviceIdMap := make(map[int]*fms.ContractServiceTemplateFullName, 0)
  296. serviceIndustryMap := make(map[int]map[string][]*fms.ContractServiceTemplateFullName, 0)
  297. allServiceList, e := fms.GetContractServiceTemplateFullName()
  298. if e != nil {
  299. err = fmt.Errorf("获取所有套餐失败, Err: "+e.Error())
  300. return
  301. }
  302. for _, v := range allServiceList {
  303. serviceIdMap[v.ServiceTemplateId] = v
  304. }
  305. // 获取服务套餐
  306. servicesList, e := fms.GetContractRegisterServicesByRegisterIds(registerIds)
  307. if e != nil {
  308. err = fmt.Errorf("获取套餐字符串失败, Err: "+e.Error())
  309. return
  310. }
  311. for i := range servicesList {
  312. item := servicesList[i]
  313. if item.Title == "行业套餐" || item.Title == "权益大套餐" {
  314. continue
  315. }
  316. if fullItem, ok := serviceIdMap[item.ServiceTemplateId]; ok {
  317. if fullItem.ParentTitle == "行业套餐" {
  318. continue
  319. }
  320. if fullItem.ParentTitle != "" {
  321. if strings.Contains(serviceIndustryStr, fullItem.ParentTitle) {
  322. if _, ok1 := serviceIndustryMap[item.ContractRegisterId]; !ok1 {
  323. serviceIndustryMap[item.ContractRegisterId] = make(map[string][]*fms.ContractServiceTemplateFullName)
  324. }
  325. serviceIndustryMap[item.ContractRegisterId][fullItem.ParentTitle] = append(serviceIndustryMap[item.ContractRegisterId][fullItem.ParentTitle], fullItem)
  326. } else {
  327. formatTitle := ""
  328. if fullItem.ParentTitle == "策略" {
  329. formatTitle = fullItem.Title
  330. }else{
  331. formatTitle = fullItem.ParentTitle+"("+fullItem.Title+")"
  332. }
  333. serviceMap[item.ContractRegisterId] = append(serviceMap[item.ContractRegisterId], formatTitle)
  334. tmp := fms.ContractServiceTemplateFormat{
  335. FormatTitle: formatTitle,
  336. ServiceTemplateId: fullItem.ServiceTemplateId,
  337. ServiceTemplatePid: fullItem.Pid,
  338. ServiceProductId: fullItem.ProductId,
  339. }
  340. serviceFormatMap[item.ContractRegisterId] = append(serviceFormatMap[item.ContractRegisterId], tmp)
  341. }
  342. }else{
  343. serviceMap[item.ContractRegisterId] = append(serviceMap[item.ContractRegisterId], fullItem.Title)
  344. tmp := fms.ContractServiceTemplateFormat{
  345. FormatTitle: fullItem.Title,
  346. ServiceTemplateId: fullItem.ServiceTemplateId,
  347. ServiceTemplatePid: fullItem.Pid,
  348. ServiceProductId: fullItem.ProductId,
  349. }
  350. serviceFormatMap[item.ContractRegisterId] = append(serviceFormatMap[item.ContractRegisterId], tmp)
  351. }
  352. }
  353. }
  354. for k, v := range serviceIndustryMap {
  355. for sk, sv := range v {
  356. formatTitle := ""
  357. templateId := 0
  358. pid := 0
  359. if len(sv) >= 2 {
  360. formatTitle = sk
  361. templateId = sv[0].Pid
  362. }else{
  363. formatTitle = sk+"("+sv[0].Title+")"
  364. templateId = sv[0].ServiceTemplateId
  365. pid = sv[0].Pid
  366. }
  367. serviceMap[k] = append(serviceMap[k], formatTitle)
  368. tmp := fms.ContractServiceTemplateFormat{
  369. FormatTitle: formatTitle,
  370. ServiceTemplateId: templateId,
  371. ServiceTemplatePid: pid,
  372. ServiceProductId: sv[0].ProductId,
  373. }
  374. serviceFormatMap[k] = append(serviceFormatMap[k], tmp)
  375. }
  376. }
  377. // 给套餐内容排序
  378. for k, v := range serviceFormatMap {
  379. sort.Sort(fms.ContractServiceTemplateFormatList(v))
  380. for _, sv := range v {
  381. serviceNameMap[k] += sv.FormatTitle+","
  382. }
  383. serviceNameMap[k] = strings.Trim(serviceNameMap[k], ",")
  384. }
  385. return
  386. }