project.go 54 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511
  1. package front
  2. import (
  3. "encoding/json"
  4. "fmt"
  5. "github.com/shopspring/decimal"
  6. "github.com/tealeg/xlsx"
  7. "go.mongodb.org/mongo-driver/bson"
  8. "go.mongodb.org/mongo-driver/bson/primitive"
  9. "io"
  10. "mime/multipart"
  11. "mongodb"
  12. qu "qfw/util"
  13. "sort"
  14. "strconv"
  15. "strings"
  16. "sync"
  17. "sync/atomic"
  18. "time"
  19. "util"
  20. )
  21. // ProjectIsExists 获取所有项目名称
  22. func (f *Front) ProjectIsExists() {
  23. defer qu.Catch()
  24. name := f.GetString("s_name")
  25. exists := false
  26. project, _ := util.Mgo.FindOne(util.PROJECTCOLLNAME, map[string]interface{}{"s_name": name})
  27. if project != nil && len(*project) > 0 {
  28. exists = true
  29. }
  30. f.ServeJson(map[string]interface{}{"exists": exists})
  31. }
  32. // ProjectList 项目列表
  33. func (f *Front) ProjectList() {
  34. defer qu.Catch()
  35. if f.Method() == "POST" {
  36. start, _ := f.GetInteger("start")
  37. limit, _ := f.GetInteger("length")
  38. draw, _ := f.GetInteger("draw")
  39. status := f.GetString("s_status")
  40. searchStr := f.GetString("search[value]")
  41. search := strings.TrimSpace(searchStr)
  42. //data := util.GetPostForm(f.Request)
  43. query := map[string]interface{}{}
  44. if status != "-1" {
  45. query["s_status"] = status
  46. } else {
  47. query["s_status"] = map[string]interface{}{
  48. "$in": []string{"未开始", "进行中", "已完成"},
  49. }
  50. }
  51. if search != "" {
  52. query["$or"] = []interface{}{
  53. map[string]interface{}{"s_name": map[string]interface{}{"$regex": search}},
  54. map[string]interface{}{"s_entname": map[string]interface{}{"$regex": search}},
  55. map[string]interface{}{"s_rule": map[string]interface{}{"$regex": search}},
  56. map[string]interface{}{"s_departname": map[string]interface{}{"$regex": search}},
  57. }
  58. }
  59. list, _ := util.Mgo.Find(util.PROJECTCOLLNAME, query, map[string]interface{}{"_id": -1}, nil, false, start, limit)
  60. count := util.Mgo.Count(util.PROJECTCOLLNAME, query)
  61. f.ServeJson(map[string]interface{}{"draw": draw, "data": *list, "recordsFiltered": count, "recordsTotal": count})
  62. } else {
  63. _ = f.Render("project/project_list.html", &f.T)
  64. }
  65. }
  66. // ProjectSave 项目保存
  67. func (f *Front) ProjectSave() {
  68. defer qu.Catch()
  69. s_name := f.GetString("s_name") //项目名称
  70. if s_name == "" {
  71. f.ServeJson(map[string]interface{}{"success": false, "msg": "缺少项目名称字段"})
  72. return
  73. }
  74. success := false //导入数据是否成功
  75. msg := "" //异常信息
  76. successNum := int64(0) //导入成功条数
  77. importDataNum := 0 //查询数量
  78. appid := "" // 客户标识(客户管理平台)
  79. var s_rulename []string //规则
  80. user := f.GetSession("user").(map[string]interface{})
  81. username := qu.ObjToString(user["s_login"]) //当前登录用户
  82. stype := f.GetString("s_type") //新建项目类型:数据库导入、excel导入
  83. s_departname, s_entname := "", ""
  84. query := map[string]interface{}{
  85. "s_name": s_name,
  86. }
  87. set := map[string]interface{}{}
  88. //导入数据
  89. if stype == "excel" { //excel导入
  90. s_entname = f.GetString("s_entname") //公司名称
  91. if s_entname == "" {
  92. f.ServeJson(map[string]interface{}{"success": false, "msg": "缺少公司名称字段"})
  93. return
  94. }
  95. s_departname = f.GetString("s_departname") //部门名称
  96. rulename := f.GetString("s_rulename") //规则名称
  97. s_rulename = strings.Split(rulename, ",")
  98. mf, _, err := f.GetFile("xlsx")
  99. qu.Debug(s_entname, s_departname, s_rulename)
  100. if err == nil {
  101. importDataNum, appid = ImportDataByExcel(mf, &success, &msg, &successNum, true)
  102. }
  103. if importDataNum == 0 {
  104. f.ServeJson(map[string]interface{}{"success": false, "msg": "文档缺少企业客户id字段"})
  105. return
  106. }
  107. //保存项目信息
  108. set = map[string]interface{}{
  109. "s_name": s_name, //项目名称
  110. "s_entname": s_entname, //公司名称
  111. "s_departname": s_departname, //部门名称
  112. "s_rulename": strings.Join(s_rulename, ","), //规则名称
  113. "i_importnum": importDataNum, //导入数量
  114. "appid": appid,
  115. "s_createname": username, //创建人
  116. "s_status": "未开始", //项目状态
  117. "i_createtime": time.Now().Unix(), //创建时间
  118. "s_importtype": "excel", //导入类型
  119. "b_isassessment": false, //是否进行了质量评估
  120. }
  121. } else if stype == "coll" { //数据库导入
  122. historyid := f.GetString("s_historyid")
  123. collName := f.GetString("coll")
  124. q := f.GetString("s_query")
  125. if historyid == "" || collName == "" {
  126. f.ServeJson(map[string]interface{}{"success": false, "msg": "数据导出ID字段"})
  127. return
  128. }
  129. query1 := make(map[string]interface{})
  130. if q != "" {
  131. if err := json.Unmarshal([]byte(q), &query1); err != nil {
  132. qu.Debug("GroupInfo Unmarshal Failed:", err)
  133. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询条件有误"})
  134. return
  135. }
  136. }
  137. query1["historyId"] = historyid
  138. if c := util.MgoJy.Count(collName, query1); c == 0 {
  139. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询数据量为0!"})
  140. return
  141. }
  142. s_departname, s_entname, appid, s_rulename, importDataNum = ImportDataByColl(collName, query1, &success, &msg, &successNum, true)
  143. appidNum := ""
  144. if util.Appid[appid] != 0 {
  145. i := util.Appid[appid]
  146. i++
  147. appidNum = fmt.Sprintf("%s-%03d", appid, i)
  148. util.Appid[appid] = i
  149. } else {
  150. appidNum = fmt.Sprintf("%s-%03d", appid, 1)
  151. util.Appid[appid] = 1
  152. }
  153. qu.Debug(s_departname, s_entname, appidNum, s_rulename, importDataNum)
  154. //保存项目信息
  155. set = map[string]interface{}{
  156. "s_name": s_name, //项目名称
  157. "s_entname": s_entname, //公司名称
  158. "s_departname": s_departname, //部门名称
  159. "s_rulename": strings.Join(s_rulename, ","), //规则名称
  160. "i_importnum": importDataNum, //导入数量
  161. "appid": appid,
  162. "s_createname": username, //创建人
  163. "s_status": "未开始", //项目状态
  164. "i_createtime": time.Now().Unix(), //创建时间
  165. "s_importtype": "coll", //导入类型
  166. "s_historyid": historyid, //源数据集标识
  167. "b_isassessment": false, //是否进行了质量评估
  168. }
  169. } else if stype == "edit" { //编辑保存
  170. success = true
  171. //s_entname = f.GetString("s_entname") //公司名称
  172. s_departname = f.GetString("s_departname") //部门名称
  173. rulename := f.GetString("s_rulename") //规则名称
  174. s_rulename = strings.Split(rulename, ",")
  175. s_personname := f.GetString("s_personname")
  176. set = map[string]interface{}{
  177. //"s_name": s_name, //项目名称
  178. //"s_entname": s_entname, //公司名称
  179. "s_departname": s_departname, //部门名称
  180. "s_rulename": strings.Join(s_rulename, ","), //规则名称
  181. "s_updateperson": username, //更新人
  182. "i_createtime": time.Now().Unix(), //更新时间
  183. "s_personname": s_personname, //售后人员
  184. //"i_starttime":,//开始时间
  185. //"i_completetime",//结束时间
  186. }
  187. }
  188. if success {
  189. success = util.Mgo.Update(util.PROJECTCOLLNAME, query, map[string]interface{}{"$set": set}, true, false)
  190. if !success { //保存项目失败
  191. msg = "新建项目失败\n" + msg
  192. } else {
  193. msg = "保存项目成功"
  194. }
  195. }
  196. //qu.Debug("Msg:", msg)
  197. //返回信息
  198. if stype == "edit" {
  199. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  200. } else {
  201. qu.Debug("Create Project:", success, "importnum:", importDataNum, "successnum:", successNum, "failnum:", int64(importDataNum)-successNum)
  202. f.ServeJson(map[string]interface{}{"success": success, "msg": msg, "importnum": importDataNum, "successnum": successNum, "failnum": int64(importDataNum) - successNum})
  203. }
  204. }
  205. func (f *Front) ProjectAddData() {
  206. defer qu.Catch()
  207. if f.Method() == "POST" {
  208. user := f.GetSession("user").(map[string]interface{})
  209. username := qu.ObjToString(user["s_login"])
  210. projectid := f.GetString("projectid")
  211. stype := f.GetString("s_type")
  212. info, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, projectid, nil)
  213. if len(*info) > 0 {
  214. success := false //导入数据是否成功
  215. msg := "" //异常信息
  216. importDataNum, successNum := 0, int64(0) //导入成功条数
  217. if stype == "excel" {
  218. mf, _, err := f.GetFile("xlsx")
  219. if err == nil {
  220. importDataNum, _ = ImportDataByExcel(mf, &success, &msg, &successNum, false)
  221. var addDataTag []map[string]interface{}
  222. if (*info)["v_add_tag"] != nil {
  223. arr := qu.ObjArrToMapArr((*info)["v_add_data"].([]interface{}))
  224. addDataTag = append(addDataTag, arr...)
  225. } else {
  226. addDataTag = append(addDataTag, map[string]interface{}{
  227. "s_importtype": stype,
  228. "i_importnum": importDataNum,
  229. "s_updateperson": username,
  230. "i_updatetime": time.Now().Unix(),
  231. })
  232. }
  233. s_status := ""
  234. if status := qu.ObjToString((*info)["s_status"]); status == "未开始" || status == "进行中" {
  235. s_status = status
  236. } else if status == "已完成" {
  237. s_status = "进行中"
  238. }
  239. set := map[string]interface{}{
  240. "i_importnum": importDataNum + qu.IntAll((*info)["i_importnum"]), //导入数量
  241. "s_status": s_status, //项目状态
  242. "i_updatetime": time.Now().Unix(),
  243. "v_add_data": addDataTag,
  244. }
  245. util.Mgo.UpdateById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{"$set": set})
  246. }
  247. } else if stype == "coll" {
  248. historyid := f.GetString("s_historyid")
  249. collName := f.GetString("coll")
  250. q := f.GetString("s_query")
  251. if historyid == "" || collName == "" {
  252. f.ServeJson(map[string]interface{}{"success": false, "msg": "数据导出ID字段"})
  253. return
  254. }
  255. query1 := make(map[string]interface{})
  256. if q != "" {
  257. if err := json.Unmarshal([]byte(q), &query1); err != nil {
  258. qu.Debug("GroupInfo Unmarshal Failed:", err)
  259. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询条件有误"})
  260. return
  261. }
  262. }
  263. query1["historyId"] = historyid
  264. qu.Debug(query1)
  265. if c := util.MgoJy.Count(collName, query1); c == 0 {
  266. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询数据量为0!"})
  267. return
  268. }
  269. _, _, _, _, importDataNum = ImportDataByColl(collName, query1, &success, &msg, &successNum, false)
  270. if !success {
  271. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  272. return
  273. }
  274. var addDataTag []map[string]interface{}
  275. if (*info)["v_add_tag"] != nil {
  276. arr := qu.ObjArrToMapArr((*info)["v_add_data"].([]interface{}))
  277. addDataTag = append(addDataTag, arr...)
  278. } else {
  279. addDataTag = append(addDataTag, map[string]interface{}{
  280. "s_importtype": stype,
  281. "i_importnum": importDataNum,
  282. "s_updateperson": username,
  283. "i_updatetime": time.Now().Unix(),
  284. })
  285. }
  286. s_status := ""
  287. if status := qu.ObjToString((*info)["s_status"]); status == "未开始" || status == "进行中" {
  288. s_status = status
  289. } else if status == "已完成" {
  290. s_status = "进行中"
  291. }
  292. //保存项目信息
  293. set := map[string]interface{}{
  294. "i_importnum": importDataNum + qu.IntAll((*info)["i_importnum"]), //导入数量
  295. "s_status": s_status, //项目状态
  296. "i_updatetime": time.Now().Unix(),
  297. "v_add_data": addDataTag,
  298. }
  299. util.Mgo.UpdateById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{"$set": set})
  300. }
  301. f.ServeJson(map[string]interface{}{"success": success, "msg": msg, "importnum": importDataNum, "successnum": successNum, "failnum": int64(importDataNum) - successNum})
  302. } else {
  303. f.ServeJson(map[string]interface{}{"success": false, "msg": "项目查询失败"})
  304. }
  305. }
  306. }
  307. // ProjectComplete 项目提交完成
  308. func (f *Front) ProjectComplete() {
  309. defer qu.Catch()
  310. user := f.GetSession("user").(map[string]interface{})
  311. username := qu.ObjToString(user["s_login"]) //当前登录用户
  312. success := false
  313. msg := ""
  314. projectId := f.GetString("s_projectid")
  315. //status := f.GetString("s_status")
  316. info, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, projectId, `{"s_status": 1, "appid": 1}`)
  317. if len(*info) <= 0 {
  318. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询项目失败"})
  319. return
  320. }
  321. status := (*info)["s_status"]
  322. if status == "进行中" {
  323. //查询该项目下未完成的用户组和用户任务
  324. query := map[string]interface{}{
  325. "s_projectid": projectId,
  326. "s_status": map[string]interface{}{
  327. "$in": []string{"未开始", "进行中"},
  328. },
  329. }
  330. taskCount := util.Mgo.Count(util.TASKCOLLNAME, query)
  331. dataCount := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istag": false, "appid": qu.ObjToString((*info)["appid"])}) //未标注数据个数
  332. qu.Debug("No Tag Count:", dataCount)
  333. if dataCount == 0 && taskCount == 0 { //全部完成
  334. success = util.Mgo.UpdateById(util.PROJECTCOLLNAME, projectId, map[string]interface{}{
  335. "$set": map[string]interface{}{
  336. "s_status": "已完成",
  337. "i_completetime": time.Now().Unix(),
  338. "s_updateperson": username,
  339. "i_updatetime": time.Now().Unix(),
  340. },
  341. })
  342. if !success {
  343. msg = "更新项目失败"
  344. }
  345. }
  346. if taskCount != 0 {
  347. msg += "任务未全部完成,"
  348. }
  349. if dataCount != 0 {
  350. msg += "数据未全部标注"
  351. }
  352. } else {
  353. msg = "项目未开始"
  354. }
  355. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  356. }
  357. // ProjectQualityAssessment 数据质量评估
  358. func (f *Front) ProjectQualityAssessment() {
  359. defer qu.Catch()
  360. msg := ""
  361. success := false
  362. //质量评估
  363. projectid := f.GetString("pid") //项目id
  364. project, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{"b_isassessment": 1, "appid": 1, "v_fields": 1})
  365. if project != nil && len(*project) > 0 {
  366. if isAssessment, ok := (*project)["b_isassessment"].(bool); ok && !isAssessment {
  367. appid := qu.ObjToString((*project)["appid"])
  368. // todo
  369. util.Mgo.Update(util.DATACOLLNAME, bson.M{"appid": appid}, bson.M{"$set": bson.M{"b_istagging": true}}, false, true)
  370. util.Mgo.UpdateById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{"$set": map[string]interface{}{"b_isassessment": true, "s_status": "进行中", "i_starttime": time.Now().Unix()}})
  371. success = true
  372. } else if ok && isAssessment {
  373. success = true
  374. msg = "成功"
  375. } else {
  376. msg = "查询项目失败"
  377. }
  378. } else {
  379. msg = "查询项目失败"
  380. }
  381. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  382. }
  383. // ProjectGroupTaskList 用户组任务分发列表
  384. func (f *Front) ProjectGroupTaskList() {
  385. defer qu.Catch()
  386. projectid := f.GetString("pid") //项目id
  387. if f.Method() == "POST" {
  388. status := f.GetString("s_status") //任务状态
  389. searchStr := f.GetString("search[value]")
  390. search := strings.TrimSpace(searchStr)
  391. start, _ := f.GetInteger("start")
  392. limit, _ := f.GetInteger("length")
  393. draw, _ := f.GetInteger("draw")
  394. query := map[string]interface{}{ //查找用户组任务
  395. "s_projectid": projectid,
  396. "s_stype": "group",
  397. }
  398. if status != "-1" {
  399. query["s_status"] = status
  400. }
  401. if search != "" {
  402. query["$or"] = []interface{}{
  403. map[string]interface{}{"s_groupname": map[string]interface{}{"$regex": search}},
  404. }
  405. }
  406. qu.Debug("Query:", query)
  407. list, _ := util.Mgo.Find(util.TASKCOLLNAME, query, map[string]interface{}{"_id": -1}, nil, false, start, limit)
  408. count := util.Mgo.Count(util.TASKCOLLNAME, query)
  409. for _, l := range *list {
  410. if status := qu.ObjToString(l["s_status"]); status == "进行中" { //更新任务进度
  411. //groupId := qu.ObjToString(l["s_groupid"])
  412. groupTaskId := mongodb.BsonIdToSId(l["_id"])
  413. giveNum := qu.IntAll(l["i_givenum"])
  414. tagNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"s_grouptaskid": groupTaskId, "b_istag": true})
  415. progressFloat := float64(tagNum) / float64(giveNum)
  416. value, _ := strconv.ParseFloat(fmt.Sprintf("%.4f", progressFloat), 64)
  417. decimalValue := decimal.NewFromFloat(value)
  418. decimalValue = decimalValue.Mul(decimal.NewFromInt(100))
  419. value, _ = decimalValue.Float64()
  420. progress := fmt.Sprint(value) + "%"
  421. l["s_progress"] = progress
  422. //同步数据库
  423. util.Mgo.UpdateById(util.TASKCOLLNAME, l["_id"], map[string]interface{}{"$set": map[string]interface{}{"s_progress": progress}})
  424. }
  425. }
  426. f.ServeJson(map[string]interface{}{"draw": draw, "data": *list, "recordsFiltered": count, "recordsTotal": count})
  427. } else {
  428. project, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{"appid": 1})
  429. appid := qu.ObjToString((*project)["appid"])
  430. if project != nil && len(*project) > 0 { //数据源表
  431. okAllDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": false, "appid": appid}) //达标数据总量
  432. okIsGiveDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": false, "b_isgivegroup": true, "appid": appid}) //达标数据已分发量
  433. okNotGiveDataNum := okAllDataNum - okIsGiveDataNum //达标待分发量
  434. okIsTagDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": false, "b_istag": true, "appid": appid}) //达标已标注量
  435. IsNoOkAllDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": true, "appid": appid}) //未达标数据总量
  436. IsNoOkIsGiveDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": true, "b_isgivegroup": true, "appid": appid}) //未达标数据已分发量
  437. IsNotOkNotGiveDataNum := IsNoOkAllDataNum - IsNoOkIsGiveDataNum //未达标待分发量
  438. IsNotOkIsTagDataNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_istagging": true, "b_istag": true, "appid": appid}) //未达标已标注量
  439. acceptNum := util.Mgo.Count("jy_check", map[string]interface{}{"projectid": projectid}) // 验收数据量
  440. allGiveDataNum := okIsGiveDataNum + IsNoOkIsGiveDataNum //总分发量
  441. allNoGiveDataNum := okNotGiveDataNum + IsNotOkNotGiveDataNum //总待分发量
  442. allIsTagDataNum := okIsTagDataNum + IsNotOkIsTagDataNum //已标注总量
  443. allDataNum := allGiveDataNum + allNoGiveDataNum
  444. // 查询全部实际可分发数据量(未分发、未标注)
  445. okRealGiveNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_isgivegroup": false, "b_istag": false})
  446. //qu.Debug("数据总量:", allDataNum, "已分发总量:", allGiveDataNum, "待分发总量:", allNoGiveDataNum, "已标注总量:", allIsTagDataNum)
  447. //qu.Debug("达标量:", okAllDataNum, "达标已分发量:", okIsGiveDataNum, "达标待分发量:", okNotGiveDataNum, "达标已标注量:", okIsTagDataNum)
  448. //qu.Debug(" 未达标量:", IsNoOkAllDataNum, " 未达标已分发量:", IsNoOkIsGiveDataNum, " 未达标待分发量:", IsNotOkNotGiveDataNum, " 未达标已标注量:", IsNotOkIsTagDataNum)
  449. f.T["s_projectid"] = projectid
  450. f.T["appid"] = appid
  451. f.T["allDataNum"] = allDataNum
  452. f.T["okAllDataNum"] = okAllDataNum
  453. f.T["okIsGiveDataNum"] = okIsGiveDataNum
  454. f.T["okNotGiveDataNum"] = okNotGiveDataNum
  455. f.T["IsNoOkAllDataNum"] = IsNoOkAllDataNum
  456. f.T["IsNoOkIsGiveDataNum"] = IsNoOkIsGiveDataNum
  457. f.T["IsNotOkNotGiveDataNum"] = IsNotOkNotGiveDataNum
  458. f.T["allGiveDataNum"] = allGiveDataNum
  459. f.T["allNoGiveDataNum"] = allNoGiveDataNum
  460. f.T["allIsTagDataNum"] = allIsTagDataNum
  461. f.T["okIsTagDataNum"] = okIsTagDataNum
  462. f.T["IsNotOkIsTagDataNum"] = IsNotOkIsTagDataNum
  463. f.T["okRealGiveNum"] = okRealGiveNum
  464. f.T["acceptNum"] = acceptNum
  465. _ = f.Render("project/project_clear.html", &f.T)
  466. } else {
  467. qu.Debug("Project Find Error")
  468. f.ServeJson("查询项目失败")
  469. }
  470. }
  471. }
  472. // ProjectGroupTaskSave 用户组任务分发
  473. func (f *Front) ProjectGroupTaskSave() {
  474. defer qu.Catch()
  475. var groupArr []map[string]interface{}
  476. var taskArr []map[string]interface{}
  477. var groupIdArr []string
  478. var groupTaskIdArr []string
  479. groupIdTask := map[string]util.Task{}
  480. success := false
  481. msg := ""
  482. user := f.GetSession("user").(map[string]interface{})
  483. username := qu.ObjToString(user["s_login"]) //当前登录用户
  484. projectid := f.GetString("s_projectid") //项目标识
  485. project, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, projectid, nil)
  486. projectname := qu.ObjToString((*project)["s_name"]) //项目名称
  487. appid := qu.ObjToString((*project)["appid"])
  488. group := f.GetString("s_group")
  489. stype := f.GetString("s_type")
  490. qu.Debug("项目id:", projectid, " 项目名称:", projectname)
  491. if err := json.Unmarshal([]byte(group), &groupArr); err != nil {
  492. qu.Debug("GroupInfo Unmarshal Failed:", err)
  493. msg = "用户组信息解析失败"
  494. } else {
  495. qu.Debug("用户组信息:", groupArr, stype)
  496. //if stype != "tag" { //如果分发的是达标数据或者全部数据且进行了初步质检,将没有质检记录的字段从v_taginfo标注记录中删除
  497. // DeleleDataTagInfo(sourceinfo)
  498. //}
  499. // 查询实际可分发数据量(未分发、未标注)
  500. realNum := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"b_isgivegroup": false, "b_istag": false, "appid": appid})
  501. for _, groupInfo := range groupArr {
  502. groupId := qu.ObjToString(groupInfo["s_groupid"])
  503. groupIdArr = append(groupIdArr, groupId)
  504. givenum := qu.IntAll(groupInfo["i_givenum"])
  505. if givenum <= 0 {
  506. continue
  507. }
  508. if realNum <= 0 {
  509. break
  510. }
  511. if realNum < givenum {
  512. givenum = realNum
  513. }
  514. groupTaskId := primitive.NewObjectID()
  515. groupTaskIdStr := mongodb.BsonIdToSId(groupTaskId)
  516. groupTaskIdArr = append(groupTaskIdArr, groupTaskIdStr)
  517. gt := util.Task{
  518. UserId: groupId,
  519. GiveNum: givenum,
  520. }
  521. groupIdTask[groupTaskIdStr] = gt
  522. groupTask := map[string]interface{}{
  523. "_id": groupTaskId, //生成任务id
  524. "s_projectid": projectid, //项目标识
  525. "s_projectname": projectname, //项目名称
  526. "s_status": "未开始", //任务状态
  527. "s_personid": qu.ObjToString(groupInfo["s_personid"]), //任务负责人标识
  528. "s_personname": qu.ObjToString(groupInfo["s_personname"]), //任务负责人
  529. "s_groupname": qu.ObjToString(groupInfo["s_groupname"]), //用户组名称
  530. "s_groupid": groupId, //用户组标识
  531. "i_givenum": givenum, //分发数据量
  532. "s_createname": username, //创建人
  533. "i_createtime": time.Now().Unix(), //创建时间
  534. "s_progress": "0%", //完成进度
  535. "s_stype": "group", //任务类型
  536. "s_entname": qu.ObjToString((*project)["s_entname"]), //公司名称
  537. "s_departname": qu.ObjToString((*project)["s_departname"]), //部门名称
  538. "s_rulename": qu.ObjToString((*project)["s_rulename"]), //规则名称
  539. "s_datatype": qu.ObjToString((*project)["s_datatype"]), //数据类型
  540. }
  541. realNum = realNum - givenum
  542. taskArr = append(taskArr, groupTask)
  543. }
  544. }
  545. if len(taskArr) > 0 {
  546. //分发数据后更新项目中用户组标识信息和用户组任务id
  547. success = util.Mgo.UpdateById(util.PROJECTCOLLNAME, projectid, map[string]interface{}{
  548. "$push": map[string]interface{}{
  549. "v_groupids": map[string]interface{}{
  550. "$each": groupIdArr,
  551. },
  552. "v_grouptaskids": map[string]interface{}{
  553. "$each": groupTaskIdArr,
  554. },
  555. },
  556. })
  557. if !success {
  558. msg = "更新项目:" + projectname + "用户组标识失败"
  559. } else { //用户组分发任务
  560. success = util.Mgo.SaveBulk(util.TASKCOLLNAME, taskArr...)
  561. if success {
  562. msg = "任务分发成功"
  563. UpdateSourceInfoByGroup(stype, appid, groupIdTask) //用户组分发任务成功后,给数据源打上用户组标识
  564. } else {
  565. msg = "任务分发失败"
  566. }
  567. }
  568. }
  569. qu.Debug("Success:", success, "Msg:", msg)
  570. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  571. }
  572. // ProjectGetEntnameList 模糊查询公司名称
  573. func (f *Front) ProjectGetEntnameList() {
  574. defer qu.Catch()
  575. var entnameList []string
  576. entname := f.GetString("entname")
  577. query := map[string]interface{}{
  578. "username": map[string]interface{}{
  579. "$regex": entname,
  580. },
  581. }
  582. list, _ := util.MgoJy.Find(util.JyUser, query, nil, map[string]interface{}{"username": 1}, false, -1, -1)
  583. if len(*list) > 0 {
  584. for _, l := range *list {
  585. entnameList = append(entnameList, qu.ObjToString(l["username"]))
  586. }
  587. f.ServeJson(map[string]interface{}{"entname": entnameList})
  588. } else {
  589. f.ServeJson(map[string]interface{}{"entname": []string{}})
  590. }
  591. }
  592. // ProjectGroupTaskRepulse 用户组任务打回
  593. func (f *Front) ProjectGroupTaskRepulse() {
  594. defer qu.Catch()
  595. success := false
  596. msg := ""
  597. user := f.GetSession("user").(map[string]interface{})
  598. username := qu.ObjToString(user["s_login"])
  599. //status := f.GetString("s_status")
  600. groupTaskId := f.GetString("taskid")
  601. appid := f.GetString("appid")
  602. currenttime := time.Now().Unix()
  603. //更新数据源
  604. success = util.Mgo.Update(util.DATACOLLNAME, map[string]interface{}{"s_grouptaskid": groupTaskId, "appid": appid}, map[string]interface{}{
  605. "$set": map[string]interface{}{
  606. "b_istag": false,
  607. "b_check": false, // 质检标记
  608. "i_ckdata": 0,
  609. "b_isgiveuser": false,
  610. "i_updatetime": currenttime,
  611. },
  612. "$unset": map[string]interface{}{
  613. "s_userid": "",
  614. "s_usertaskid": "",
  615. "s_login": "",
  616. "v_taginfo": "",
  617. "v_checkinfo": "",
  618. },
  619. }, false, true)
  620. if success {
  621. util.Mgo.Update(util.TASKCOLLNAME, map[string]interface{}{
  622. "s_stype": "user",
  623. "s_parentid": groupTaskId,
  624. }, map[string]interface{}{
  625. "$set": map[string]interface{}{
  626. "s_status": "已关闭",
  627. "s_progress": "%0",
  628. "i_updatetime": currenttime,
  629. "s_updateperson": username,
  630. },
  631. }, false, true)
  632. //更新用户组任务 清除最迟完成时间,更新任务状态
  633. success = util.Mgo.UpdateById(util.TASKCOLLNAME, groupTaskId, map[string]interface{}{
  634. "$set": map[string]interface{}{
  635. "s_status": "未开始",
  636. "s_updateperson": username,
  637. "i_updatetime": currenttime,
  638. "s_progress": "0%",
  639. },
  640. "$unset": map[string]interface{}{
  641. "i_completetime": "",
  642. },
  643. })
  644. if !success {
  645. msg = "更新用户组任务失败"
  646. }
  647. } else {
  648. msg = "更新数据源信息失败"
  649. }
  650. qu.Debug("Task Repulse:", success, " Msg:", msg)
  651. f.ServeJson(map[string]interface{}{"success": success, "msg": msg})
  652. }
  653. // DataRepulse 单条数据打回
  654. func (f *Front) DataRepulse() {
  655. defer qu.Catch()
  656. if f.Method() == "POST" {
  657. //tid := f.GetString("tid")
  658. did := f.GetString("s_infoid")
  659. //更新数据源
  660. success := util.Mgo.UpdateById(util.DATACOLLNAME, did, bson.M{
  661. "$set": map[string]interface{}{
  662. "b_istag": false,
  663. "b_check": false, // 质检标记
  664. "i_ckdata": 0,
  665. "i_updatetime": time.Now().Unix(),
  666. },
  667. "$unset": map[string]interface{}{
  668. "v_taginfo": "",
  669. "v_checkinfo": "",
  670. },
  671. })
  672. //util.Mgo.UpdateById(util.TASKCOLLNAME, tid, bson.M{"s_status"})
  673. f.ServeJson(map[string]interface{}{"success": success, "msg": ""})
  674. }
  675. }
  676. // ProjectGroupTaskRetrieve 用户组任务收回
  677. func (f *Front) ProjectGroupTaskRetrieve() {
  678. defer qu.Catch()
  679. user := f.GetSession("user").(map[string]interface{})
  680. username := qu.ObjToString(user["s_login"])
  681. groupTaskId := f.GetString("taskid")
  682. appid := f.GetString("appid")
  683. //status := f.GetString("s_status") //未开始、进行中
  684. //giveNum, _ := f.GetInteger("i_givenum") //收回时要更新的分发数据量
  685. msg := ""
  686. success := false
  687. count := 0
  688. groupTask, _ := util.Mgo.FindById(util.TASKCOLLNAME, groupTaskId, map[string]interface{}{"v_sonids": 1, "s_status": 1})
  689. if len(*groupTask) <= 0 {
  690. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询任务失败"})
  691. return
  692. }
  693. status := qu.ObjToString((*groupTask)["s_status"])
  694. if status == "未开始" { //未开始的用户组任务,暂未给用户分发任务
  695. success = true
  696. } else { //进行中的用户组任务需更新其下用户信息
  697. if groupTask != nil && len(*groupTask) > 0 {
  698. if sonIds, ok := (*groupTask)["v_sonids"].([]interface{}); ok && len(sonIds) > 0 { //更新所有用户任务信息
  699. userTaskIdStatus := map[string]string{} //封装要回收的用户任务信息
  700. for _, sId := range sonIds {
  701. userTaskId := qu.ObjToString(sId)
  702. userTask, _ := util.Mgo.FindById(util.TASKCOLLNAME, userTaskId, map[string]interface{}{"s_status": 1})
  703. if userTask != nil && len(*userTask) > 0 {
  704. if statusTmp := qu.ObjToString((*userTask)["s_status"]); statusTmp != "已完成" && statusTmp != "已关闭" { //已完成和已关闭的任务不收回
  705. userTaskIdStatus[userTaskId] = statusTmp
  706. }
  707. } else {
  708. qu.Debug("Find User Task:", userTaskId, "Error")
  709. }
  710. }
  711. qu.Debug("userTaskIdStatus:", len(userTaskIdStatus))
  712. if len(userTaskIdStatus) > 0 { //收回用户组下所有用户信息
  713. //用户组收回时,若已有用户任务在未开始时收回或关闭,调用RetrieveTaskByUser返回的总收回量count就遗漏了用户收回或关闭任务的量
  714. msg, _, success = RetrieveCloseTaskByUser(username, userTaskIdStatus) //用户信息收回
  715. } else { //用户组下所有用户任务都已完成
  716. success = true
  717. }
  718. } else { //没有分配给用户任务
  719. success = true
  720. }
  721. } else {
  722. msg = "用户组任务查找失败"
  723. }
  724. }
  725. if success { //所有用户信息收回成功后,更新用户组任务相关信息
  726. count = util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{ //统计该用户组任务下未标注的数据量
  727. "appid": appid,
  728. "s_grouptaskid": groupTaskId,
  729. "b_istag": false,
  730. })
  731. UpdateGroupTaskAndSourceInfo(groupTaskId, appid, username, status, count, &msg, &success)
  732. }
  733. qu.Debug(success, count, msg)
  734. f.ServeJson(map[string]interface{}{"success": success, "msg": msg, "count": count})
  735. }
  736. // ProjectGroupTaskClose 用户组任务关闭
  737. func (f *Front) ProjectGroupTaskClose() {
  738. defer qu.Catch()
  739. user := f.GetSession("user").(map[string]interface{})
  740. username := qu.ObjToString(user["s_login"])
  741. groupTaskId := f.GetString("taskid")
  742. appid := f.GetString("appid")
  743. //status := f.GetString("s_status") //未开始、进行中
  744. msg := ""
  745. success := false
  746. count := 0
  747. groupTask, _ := util.Mgo.FindById(util.TASKCOLLNAME, groupTaskId, map[string]interface{}{"s_status": 1})
  748. if len(*groupTask) <= 0 {
  749. f.ServeJson(map[string]interface{}{"success": false, "msg": "查询任务失败"})
  750. return
  751. }
  752. status := qu.ObjToString((*groupTask)["s_status"])
  753. if status == "未开始" { //未开始的用户组任务,暂未给用户分发任务;已完成只更新用户组任务
  754. success = true
  755. } else { //进行中的用户组任务需更新其下用户信息
  756. //groupTask, _ := util.Mgo.FindById(util.TASKCOLLNAME, groupTaskId, map[string]interface{}{"v_sonids": 1})
  757. //if groupTask != nil && len(*groupTask) > 0 {
  758. // if sonIds, ok := (*groupTask)["v_sonids"].([]interface{}); ok && len(sonIds) > 0 { //更新所有用户任务信息
  759. // userTaskIdStatus := map[string]string{} //封装要关闭的用户任务信息
  760. // for _, sId := range sonIds {
  761. // userTaskId := qu.ObjToString(sId)
  762. // userTask, _ := util.Mgo.FindById(util.TASKCOLLNAME, userTaskId, map[string]interface{}{"s_status": 1})
  763. // if userTask != nil && len(*userTask) > 0 {
  764. // if statusTmp := qu.ObjToString((*userTask)["s_status"]); statusTmp == "已完成" && statusTmp != "已关闭" { //已关闭的任务不更新
  765. // userTaskIdStatus[userTaskId] = statusTmp
  766. // }
  767. // } else {
  768. // qu.Debug("Find User Task:", userTaskId, "Error")
  769. // }
  770. // }
  771. // if len(userTaskIdStatus) > 0 { //关闭用户组下所有用户信息
  772. // msg, _, success = RetrieveCloseTaskByUser(sourceInfo, username, userTaskIdStatus) //用户信息收回
  773. // } else { //用户组下所有用户任务都已关闭
  774. // success = true
  775. // }
  776. // } else { //没有分配给用户任务
  777. // success = true
  778. // }
  779. //} else {
  780. // msg = "用户组任务查找失败"
  781. //}
  782. }
  783. if success { //所有用户信息关闭成功后,更新用户组任务相关信息
  784. count = util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{ //统计该用户组任务下未标注的数据量
  785. "s_grouptaskid": groupTaskId,
  786. "b_istag": false,
  787. })
  788. UpdateGroupTaskAndSourceInfo(groupTaskId, appid, username, status, count, &msg, &success)
  789. }
  790. qu.Debug(success, count, msg)
  791. f.ServeJson(map[string]interface{}{"success": success, "msg": msg, "count": count})
  792. }
  793. // UpdateGroupTaskAndSourceInfo 更新用户组任务相关信息
  794. func UpdateGroupTaskAndSourceInfo(groupTaskId, appid, username, status string, count int, msg *string, success *bool) {
  795. defer qu.Catch()
  796. qu.Debug("GroupTaskStatus:", status, " Count:", count)
  797. if count != 0 { //更新数据源
  798. query := map[string]interface{}{
  799. "appid": appid,
  800. "s_grouptaskid": groupTaskId,
  801. "b_istag": false,
  802. }
  803. set := map[string]interface{}{
  804. "b_isgivegroup": false,
  805. "i_updatetime": time.Now().Unix(),
  806. }
  807. unset := map[string]interface{}{
  808. "s_groupid": "",
  809. "s_grouptaskid": "",
  810. }
  811. *success = util.Mgo.Update(util.DATACOLLNAME, query, map[string]interface{}{"$set": set, "$unset": unset}, false, true)
  812. }
  813. //更新用户组任务
  814. if *success {
  815. taskSet := map[string]interface{}{
  816. "s_status": "已完成",
  817. "s_updateperson": username,
  818. "i_updatetime": time.Now().Unix(),
  819. "i_completetime": time.Now().Unix(),
  820. "s_progress": "100%",
  821. }
  822. if status == "未开始" {
  823. taskSet["i_starttime"] = time.Now().Unix()
  824. taskSet["s_status"] = "已关闭"
  825. }
  826. inc := map[string]interface{}{
  827. "i_givenum": -count,
  828. }
  829. *success = util.Mgo.UpdateById(util.TASKCOLLNAME, groupTaskId, map[string]interface{}{"$set": taskSet, "$inc": inc})
  830. if !*success {
  831. *msg = "更新用户组任务失败"
  832. }
  833. } else {
  834. *msg = "更新数据源信息失败"
  835. }
  836. }
  837. // DeleleDataTagInfo 删除标注记录
  838. func DeleleDataTagInfo(sourceinfo string) {
  839. defer qu.Catch()
  840. sess := util.Mgo.GetMgoConn()
  841. defer util.Mgo.DestoryMongoConn(sess)
  842. ch := make(chan bool, 5)
  843. wg := &sync.WaitGroup{}
  844. lock := &sync.Mutex{}
  845. query := map[string]interface{}{ //达标数据可能会分发后收回、打回再分发
  846. "b_istagging": false, //达标数据
  847. "b_cleartag": false, //未进行一次标注信息清理
  848. }
  849. fields := map[string]interface{}{
  850. "v_taginfo": 1,
  851. "v_check": 1,
  852. }
  853. updateArr := [][]map[string]interface{}{}
  854. it := sess.DB(util.Mgo.DbName).C(util.DATACOLLNAME).Find(&query).Select(&fields).Iter()
  855. count, _ := sess.DB(util.Mgo.DbName).C(util.DATACOLLNAME).Find(&query).Count()
  856. qu.Debug("Find Needs To Clearn Data Count:", count)
  857. n := 0
  858. for tmp := make(map[string]interface{}); it.Next(tmp); n++ {
  859. ch <- true
  860. wg.Add(1)
  861. go func(tmp map[string]interface{}) {
  862. defer func() {
  863. <-ch
  864. wg.Done()
  865. }()
  866. update := []map[string]interface{}{}
  867. update = append(update, map[string]interface{}{"_id": tmp["_id"]})
  868. tagInfo, _ := tmp["v_taginfo"].(map[string]interface{})
  869. checkInfo, _ := tmp["v_check"].(map[string]interface{})
  870. set := map[string]interface{}{
  871. "b_cleartag": true,
  872. }
  873. unset := map[string]interface{}{}
  874. if len(tagInfo) != 0 && len(checkInfo) != 0 { //有质检信息,删除v_taginfo未质检的字段
  875. for f := range tagInfo {
  876. if checkInfo[f] == nil {
  877. delete(tagInfo, f)
  878. }
  879. }
  880. set["v_taginfo"] = tagInfo
  881. } else if len(tagInfo) != 0 && len(checkInfo) == 0 { //没有质检删除v_taginfo字段
  882. unset["v_taginfo"] = ""
  883. }
  884. if len(unset) > 0 {
  885. update = append(update, map[string]interface{}{
  886. "$set": set,
  887. "$unset": unset,
  888. })
  889. } else {
  890. update = append(update, map[string]interface{}{
  891. "$set": set,
  892. })
  893. }
  894. lock.Lock()
  895. updateArr = append(updateArr, update)
  896. if len(updateArr) > 500 {
  897. util.Mgo.UpdateBulk(util.DATACOLLNAME, updateArr...)
  898. updateArr = [][]map[string]interface{}{}
  899. }
  900. lock.Unlock()
  901. }(tmp)
  902. if n%100 == 0 {
  903. qu.Debug("current:", n)
  904. }
  905. tmp = map[string]interface{}{}
  906. }
  907. wg.Wait()
  908. lock.Lock()
  909. if len(updateArr) > 0 {
  910. util.Mgo.UpdateBulk(util.DATACOLLNAME, updateArr...)
  911. updateArr = [][]map[string]interface{}{}
  912. }
  913. lock.Unlock()
  914. }
  915. // UpdateSourceInfoByGroup 用户组分发任务成功后,给数据源打上用户组标识
  916. func UpdateSourceInfoByGroup(stype, appid string, groupIdInfo map[string]util.Task) {
  917. defer qu.Catch()
  918. for groupTaskId, tInfo := range groupIdInfo {
  919. groupId := tInfo.UserId
  920. num := tInfo.GiveNum
  921. sess := util.Mgo.GetMgoConn()
  922. defer util.Mgo.DestoryMongoConn(sess)
  923. ch := make(chan bool, 5)
  924. wg := &sync.WaitGroup{}
  925. lock := &sync.Mutex{}
  926. query := map[string]interface{}{ //查找未分配且未标注对应stype的数据分发
  927. "appid": appid,
  928. "b_isgivegroup": false,
  929. "b_istag": false,
  930. }
  931. if stype == "notag" { //达标数据
  932. query["b_istagging"] = false
  933. } else if stype == "tag" { //未达标数据
  934. query["b_istagging"] = true
  935. }
  936. fields := map[string]interface{}{
  937. "v_baseinfo": 1,
  938. }
  939. updateArr := [][]map[string]interface{}{}
  940. qu.Debug("Query:", query)
  941. it := sess.DB(util.Mgo.DbName).C(util.DATACOLLNAME).Find(&query).Select(&fields).Limit(int64(num)).Iter()
  942. n := 0
  943. for tmp := make(map[string]interface{}); it.Next(tmp); n++ {
  944. ch <- true
  945. wg.Add(1)
  946. go func(tmp map[string]interface{}) {
  947. defer func() {
  948. <-ch
  949. wg.Done()
  950. }()
  951. update := []map[string]interface{}{}
  952. update = append(update, map[string]interface{}{"_id": tmp["_id"]})
  953. update = append(update, map[string]interface{}{
  954. "$set": map[string]interface{}{
  955. "s_groupid": groupId,
  956. "s_grouptaskid": groupTaskId,
  957. "b_isgivegroup": true,
  958. "i_updatetime": time.Now().Unix(),
  959. },
  960. // 分发时 删除程序检测的标记
  961. "$unset": map[string]interface{}{
  962. "s_excp": "",
  963. "s_excp_info": "",
  964. },
  965. })
  966. lock.Lock()
  967. updateArr = append(updateArr, update)
  968. //saveArr = append(saveArr, save)
  969. if len(updateArr) > 500 {
  970. util.Mgo.UpdateBulk(util.DATACOLLNAME, updateArr...)
  971. updateArr = [][]map[string]interface{}{}
  972. }
  973. lock.Unlock()
  974. }(tmp)
  975. if n%100 == 0 {
  976. qu.Debug("current:", n)
  977. }
  978. tmp = map[string]interface{}{}
  979. }
  980. wg.Wait()
  981. lock.Lock()
  982. if len(updateArr) > 0 {
  983. util.Mgo.UpdateBulk(util.DATACOLLNAME, updateArr...)
  984. updateArr = [][]map[string]interface{}{}
  985. }
  986. lock.Unlock()
  987. }
  988. }
  989. // ImportDataByExcel 通过excel获取数据源
  990. func ImportDataByExcel(mf multipart.File, success *bool, msg *string, successNum *int64, newCreate bool) (importDataNum int, appidNum string) {
  991. defer qu.Catch()
  992. binary, _ := io.ReadAll(mf)
  993. xls, _ := xlsx.OpenBinary(binary)
  994. sheet := xls.Sheets[0]
  995. rows := sheet.Rows
  996. idcolnum := -1
  997. appidColnum := -1
  998. appid := ""
  999. cellFieldName := map[int]string{} //记录客户需求字段所在的列
  1000. idInfoArr := []util.Data{} //记录数据id及需要保存的字段信息
  1001. for rn, row := range rows {
  1002. if rn == 0 {
  1003. for index, cell := range row.Cells {
  1004. title := cell.Value
  1005. if fieldName := util.CustomerFieldMap_HE[title]; fieldName != "" { //客户需求字段
  1006. cellFieldName[index] = fieldName
  1007. }
  1008. if title == "唯一标识" || title == "信息标识" { //id所在列
  1009. idcolnum = index
  1010. }
  1011. if title == "企业客户id" { //id所在列
  1012. appidColnum = index
  1013. }
  1014. }
  1015. if idcolnum == -1 {
  1016. break
  1017. }
  1018. if appidColnum == -1 {
  1019. qu.Debug("ImportDataByExcel:", "企业客户id为空")
  1020. return 0, ""
  1021. }
  1022. continue
  1023. }
  1024. if len(row.Cells) < len(rows[0].Cells) {
  1025. break
  1026. }
  1027. tmp := map[string]interface{}{}
  1028. for index, f := range cellFieldName {
  1029. if val := row.Cells[index].Value; val != "" {
  1030. if f == "capital" { //注册资金(万元)
  1031. cf, _ := row.Cells[index].Float()
  1032. tmp[f] = cf
  1033. } else if f == "createtime" { //创建时间
  1034. ci, _ := row.Cells[index].Int64()
  1035. tmp[f] = ci
  1036. } else {
  1037. tmp[f] = val
  1038. }
  1039. }
  1040. }
  1041. id := row.Cells[idcolnum].String() //加密的id
  1042. if id == "" {
  1043. break
  1044. }
  1045. id = util.SE.DecodeString(id) //解密后id
  1046. idInfoArr = append(idInfoArr, util.Data{
  1047. ID: id,
  1048. Info: tmp,
  1049. })
  1050. if appid == "" {
  1051. appid = qu.ObjToString(tmp["appid"])
  1052. }
  1053. }
  1054. importDataNum = len(idInfoArr)
  1055. if util.Appid[appid] != 0 {
  1056. i := util.Appid[appid]
  1057. if newCreate { // 新增/追加
  1058. i++
  1059. }
  1060. appidNum = fmt.Sprintf("%s-%03d", appid, i)
  1061. util.Appid[appid] = i
  1062. } else {
  1063. appidNum = fmt.Sprintf("%s-%03d", appid, 1)
  1064. util.Appid[appid] = 1
  1065. }
  1066. qu.Debug("Load Excel Count:", importDataNum, appid)
  1067. if importDataNum > 0 {
  1068. GetDataById(idInfoArr, appidNum, "excel", success, msg, successNum)
  1069. } else {
  1070. *success = false
  1071. *msg = "查询数据失败"
  1072. }
  1073. idInfoArr = []util.Data{}
  1074. return
  1075. }
  1076. // ImportDataByColl 通过表获取数据源
  1077. func ImportDataByColl(collName string, query map[string]interface{}, success *bool, msg *string, successNum *int64, newCreate bool) (departname, entname, appid string, rulename []string, importDataNum int) {
  1078. defer qu.Catch()
  1079. rulenameMap := map[string]bool{}
  1080. sess := util.MgoJy.GetMgoConn()
  1081. defer util.MgoJy.DestoryMongoConn(sess)
  1082. ch := make(chan bool, 3)
  1083. wg := &sync.WaitGroup{}
  1084. lock := &sync.Mutex{}
  1085. idInfoArr := []util.Data{} //记录数据id及需要保存的字段信息
  1086. it := sess.DB(util.MgoJy.DbName).C(collName).Find(&query).Iter()
  1087. n := 0
  1088. for tmp := make(map[string]interface{}); it.Next(tmp); n++ {
  1089. ch <- true
  1090. wg.Add(1)
  1091. go func(tmp map[string]interface{}) {
  1092. defer func() {
  1093. <-ch
  1094. wg.Done()
  1095. }()
  1096. id := qu.ObjToString(tmp["id"]) //bidding id
  1097. if appid == "" {
  1098. appid = qu.ObjToString(tmp["appid"]) //根据appid查user表获取公司名称
  1099. }
  1100. departname = qu.ObjToString(tmp["departname"]) //部门名称。所有数据都应部门名称,若不一致,随机取
  1101. needField := map[string]interface{}{}
  1102. for f := range util.CustomerFieldMap_EH {
  1103. if tmp[f] != nil {
  1104. needField[f] = tmp[f]
  1105. }
  1106. }
  1107. if entname == "" { //获取一次公司名称即可
  1108. user, _ := util.MgoJy.FindOne(util.JyUser, map[string]interface{}{"appid": appid})
  1109. entname = qu.ObjToString((*user)["username"]) //公司名称
  1110. }
  1111. rname := qu.ObjToString(tmp["rulename"])
  1112. lock.Lock()
  1113. for _, r := range strings.Split(rname, ",") {
  1114. rulenameMap[r] = true
  1115. }
  1116. //rulename = append(rulename, qu.ObjToString(tmp["rulename"])) //规则名称
  1117. //idInfoMap[id] = needField
  1118. idInfoArr = append(idInfoArr, util.Data{
  1119. ID: id,
  1120. Info: needField,
  1121. })
  1122. lock.Unlock()
  1123. }(tmp)
  1124. if n%100 == 0 {
  1125. qu.Debug("current:", n)
  1126. }
  1127. tmp = map[string]interface{}{}
  1128. }
  1129. wg.Wait()
  1130. for r := range rulenameMap {
  1131. rulename = append(rulename, r)
  1132. }
  1133. importDataNum = len(idInfoArr) //查询数据总数
  1134. if util.Appid[appid] != 0 {
  1135. i := util.Appid[appid]
  1136. if newCreate { // 新增
  1137. i++
  1138. }
  1139. appid = fmt.Sprintf("%s-%03d", appid, i)
  1140. util.Appid[appid] = i
  1141. } else {
  1142. appid = fmt.Sprintf("%s-%03d", appid, 1)
  1143. util.Appid[appid] = 1
  1144. }
  1145. if importDataNum > 0 {
  1146. GetDataById(idInfoArr, appid, "coll", success, msg, successNum)
  1147. } else {
  1148. *msg = "查询数据失败"
  1149. }
  1150. idInfoArr = []util.Data{}
  1151. return
  1152. }
  1153. // GetDataById 通过id集从bidding、extract、project获取数据所有信息
  1154. func GetDataById(idInfoArr []util.Data, appid, importType string, success *bool, msg *string, successNum *int64) {
  1155. *success = true
  1156. var msgArr []string
  1157. wg := &sync.WaitGroup{}
  1158. lock := &sync.Mutex{}
  1159. ch := make(chan bool, 10)
  1160. //num := int64(0) //计数
  1161. for i, data := range idInfoArr {
  1162. wg.Add(1)
  1163. ch <- true
  1164. go func(index int, tmpData util.Data) {
  1165. defer func() {
  1166. wg.Done()
  1167. <-ch
  1168. }()
  1169. /*
  1170. 1.查询数据是否存在 f_data
  1171. 1.查询bidding
  1172. 2.查extract
  1173. 3.extract合并到bidding(删除item字段与客户需要的item不是一个含义)
  1174. 4.对比marked表,替换已标注过的字段值,补充标记
  1175. 5.合并客户所需字段信息,补充id字段
  1176. //6.若为同步时,删除原有id对应的信息,新增该id对应的_id信息
  1177. 6.mgo查询项目信息
  1178. */
  1179. tagInfoMap := map[string]interface{}{} //记录数据已标注过的信息
  1180. baseInfoMap := map[string]interface{}{} //记录其他信息
  1181. id := tmpData.ID
  1182. tmp := tmpData.Info
  1183. m, _ := util.Mgo.FindById(util.DATACOLLNAME, id, nil)
  1184. if len(*m) > 0 {
  1185. appids := qu.ObjArrToStringArr((*m)["appid"].([]interface{}))
  1186. if !strings.Contains(strings.Join(appids, ","), appid) {
  1187. util.Mgo.UpdateById(util.DATACOLLNAME, id, bson.M{"$push": bson.M{"appid": appid}})
  1188. }
  1189. } else {
  1190. //markData, _ := util.MgoHM.FindById("bidding", id, nil)
  1191. //if len(*markData) > 0 {
  1192. //
  1193. //}
  1194. //1.查bidding
  1195. tmpBidColl := util.BidColl1 //bidding
  1196. if id < util.BIDDINGSTARTID {
  1197. tmpBidColl = util.BidColl2 //bidding_back
  1198. }
  1199. bidData, _ := util.MgoB.FindById(tmpBidColl, id, nil)
  1200. if qu.ObjToString((*bidData)["toptype"]) != "采购意向" {
  1201. // 导入数据时,删掉purchasinglist(排除采购意向数据)
  1202. delete(*bidData, "purchasinglist")
  1203. // 删除多包字段 20230518
  1204. delete(*bidData, "package")
  1205. }
  1206. if bidData != nil && len(*bidData) > 0 { //bidding表数据存在
  1207. //2.查extract
  1208. extData, _ := util.MgoE.FindById(util.ExtColl1, id, map[string]interface{}{"attach_text": 0, "field_source": 0, "log": 0})
  1209. if extData == nil || len(*extData) == 0 {
  1210. extData, _ = util.MgoE.FindById(util.ExtColl2, id, map[string]interface{}{"attach_text": 0, "field_source": 0, "log": 0})
  1211. }
  1212. //抽取表字段合并到bidding
  1213. if extData != nil && len(*extData) > 0 {
  1214. for k, v := range *extData {
  1215. if k == "publishtime" {
  1216. continue
  1217. }
  1218. (*bidData)[k] = v
  1219. }
  1220. }
  1221. //3.删除item
  1222. //删除item
  1223. delete((*bidData), "item")
  1224. //合并导入表中客户所需的字段
  1225. if len(tmp) > 0 {
  1226. for k, v := range tmp {
  1227. (*bidData)[k] = v
  1228. }
  1229. }
  1230. //补充id
  1231. //(*bidData)["id"] = id
  1232. //if stype == "syncoll" { //同步数据时删除原始数据
  1233. // if util.MgoM.Delete(coll, `{"id":"`+id+`"}`) == 0 {
  1234. // lock.Lock()
  1235. // *msg += "同步未删除成功数据id:" + id + ";\n"
  1236. // *success = false
  1237. // lock.Unlock()
  1238. // }
  1239. //}
  1240. // 处理 package winner_all
  1241. if p, o1 := (*bidData)["package"].(map[string]interface{}); o1 {
  1242. for _, v := range p {
  1243. v1 := v.(map[string]interface{})
  1244. t := make(map[string]interface{})
  1245. if v1["winner"] != nil {
  1246. t["winner"] = v1["winner"]
  1247. }
  1248. if v1["bidamount"] != nil {
  1249. t["bidamount"] = qu.Float64All(v1["bidamount"])
  1250. }
  1251. if len(t) > 0 {
  1252. v1["winner_all"] = append([]map[string]interface{}{}, t)
  1253. }
  1254. }
  1255. }
  1256. // 补充filetext
  1257. (*bidData)["filetext"] = util.GetFileText(*bidData)
  1258. // 6.项目合并信息
  1259. project, _ := util.MgoE.Find(util.ProjectColl, bson.M{"ids": id}, nil, nil, true, -1, -1)
  1260. if project != nil && len((*project)[0]) > 0 {
  1261. ids := qu.ObjArrToStringArr((*project)[0]["ids"].([]interface{}))
  1262. if len(ids) > 0 {
  1263. var infolist []map[string]interface{}
  1264. for _, v := range ids {
  1265. if v == id { // 当前公告
  1266. continue
  1267. }
  1268. if v < util.BIDDINGSTARTID {
  1269. tmpBidColl = util.BidColl2 //bidding_back
  1270. }
  1271. bid, b := util.MgoB.FindById(tmpBidColl, v, nil)
  1272. if b && len(*bid) > 0 {
  1273. tmp1 := make(map[string]interface{})
  1274. tmp1["id"] = v
  1275. tmp1["title"] = (*bid)["title"]
  1276. tmp1["href"] = (*bid)["href"]
  1277. tmp1["toptype"] = (*bid)["toptype"]
  1278. tmp1["subtype"] = (*bid)["subtype"]
  1279. tmp1["publishtime"] = (*bid)["publishtime"]
  1280. tmp1["detail"] = (*bid)["detail"]
  1281. tmp1["filetext"] = util.GetFileText(*bid)
  1282. infolist = append(infolist, tmp1)
  1283. }
  1284. }
  1285. (*bidData)["info"] = infolist
  1286. }
  1287. } else {
  1288. qu.Debug("Projectset Find Error", id)
  1289. }
  1290. baseInfoMap["id"] = id
  1291. _id := (*bidData)["_id"]
  1292. delete(*bidData, "_id")
  1293. //保存数据
  1294. baseInfoMap["_id"] = _id
  1295. baseInfoMap["v_baseinfo"] = bidData
  1296. if len(tagInfoMap) > 0 {
  1297. baseInfoMap["v_taginfo"] = tagInfoMap
  1298. }
  1299. baseInfoMap["i_createtime"] = time.Now().Unix()
  1300. baseInfoMap["appid"] = []string{appid}
  1301. baseInfoMap["b_isgivegroup"] = false //是否分配给用户组
  1302. baseInfoMap["b_istag"] = false //是否已标注
  1303. //baseInfoMap["b_cleartag"] = false //是否清理标注信息
  1304. baseInfoMap["b_isgiveuser"] = false //是否分配给用户
  1305. baseInfoMap["b_check"] = false // 质检标记
  1306. baseInfoMap["b_isEff"] = false // 标的物有效性
  1307. baseInfoMap["b_istagging"] = true
  1308. if util.Mgo.SaveByOriID(util.DATACOLLNAME, baseInfoMap) {
  1309. atomic.AddInt64(successNum, 1) //保存成功计数
  1310. } else {
  1311. lock.Lock()
  1312. //*success = false
  1313. if importType == "excel" {
  1314. msgArr = append(msgArr, "第"+fmt.Sprint(index+2)+"行未导入id:"+id)
  1315. //*msg += "第" + fmt.Sprint(num+2) + "行未保存成功数据_id:" + id + ";\n"
  1316. } else {
  1317. msgArr = append(msgArr, "未导入id:"+id)
  1318. //*msg += "未保存成功数据_id:" + id + ";\n"
  1319. }
  1320. lock.Unlock()
  1321. }
  1322. } else {
  1323. lock.Lock()
  1324. *success = false
  1325. qu.Debug(id)
  1326. if importType == "excel" {
  1327. msgArr = append(msgArr, "第"+fmt.Sprint(index+2)+"行,未查询到id:"+id)
  1328. //*msg += "第" + fmt.Sprint(num+2) + "行未查询到数据:" + id + ";\n"
  1329. } else {
  1330. msgArr = append(msgArr, "未查询id:"+id)
  1331. //*msg += "未查询到数据_id:" + id + ";\n"
  1332. }
  1333. lock.Unlock()
  1334. }
  1335. }
  1336. }(i, data)
  1337. }
  1338. wg.Wait()
  1339. sort.Strings(msgArr)
  1340. *msg = strings.Join(msgArr, ";<br>")
  1341. }
  1342. func (f *Front) ProjectCheckSuc() {
  1343. defer qu.Catch()
  1344. if f.Method() == "POST" {
  1345. appid := f.GetString("appid")
  1346. query := map[string]interface{}{
  1347. "appid": appid,
  1348. "b_istagging": false,
  1349. }
  1350. b := util.Mgo.Update(util.DATACOLLNAME, query, map[string]interface{}{"$set": map[string]interface{}{"b_istag": true}}, false, true)
  1351. f.ServeJson(map[string]interface{}{"success": b, "msg": "更新数据失败"})
  1352. }
  1353. }
  1354. func (f *Front) ProjectPassSuc() {
  1355. defer qu.Catch()
  1356. if f.Method() == "POST" {
  1357. appid := f.GetString("appid")
  1358. query := map[string]interface{}{
  1359. "appid": appid,
  1360. "b_istag": false,
  1361. }
  1362. b := util.Mgo.Update(util.DATACOLLNAME, query, map[string]interface{}{"$set": map[string]interface{}{"b_istag": true, "i_ckdata": 2}}, false, true)
  1363. f.ServeJson(map[string]interface{}{"success": b, "msg": "更新数据失败"})
  1364. }
  1365. }
  1366. func (f *Front) ProjectTagNum() {
  1367. defer qu.Catch()
  1368. if f.Method() == "POST" {
  1369. appid := f.GetString("appid")
  1370. count := util.Mgo.Count(util.DATACOLLNAME, map[string]interface{}{"i_ckdata": 2, "appid": appid})
  1371. if count > 0 {
  1372. f.ServeJson(map[string]interface{}{"success": true})
  1373. } else {
  1374. f.ServeJson(map[string]interface{}{"success": false, "msg": "暂时没有可质检的数据"})
  1375. }
  1376. }
  1377. }
  1378. func (f *Front) ProjectField() {
  1379. defer qu.Catch()
  1380. if f.Method() == "POST" {
  1381. pid := f.GetString("pid")
  1382. d1 := f.GetString("fields") //配置字段
  1383. var bObj []map[string]interface{}
  1384. err := json.Unmarshal([]byte(d1), &bObj)
  1385. if err != nil {
  1386. qu.Debug("Json Unmarshal Error")
  1387. f.ServeJson(map[string]interface{}{"success": false, "msg": "解析数据失败"})
  1388. return
  1389. }
  1390. b := util.Mgo.UpdateById(util.PROJECTCOLLNAME, pid, bson.M{"$set": bson.M{"v_fields": bObj}})
  1391. if b {
  1392. f.ServeJson(map[string]interface{}{"success": b, "msg": "保存数据成功"})
  1393. } else {
  1394. f.ServeJson(map[string]interface{}{"success": b, "msg": "字段保存失败"})
  1395. }
  1396. } else {
  1397. pid := f.GetString("id")
  1398. project, _ := util.Mgo.FindById(util.PROJECTCOLLNAME, pid, map[string]interface{}{"v_fields": 1})
  1399. if (*project)["v_fields"] != nil {
  1400. fields := util.Copy(util.FieldsArr).([]map[string]interface{})
  1401. var a1 []string // 标注基本字段
  1402. a2 := make(map[string]interface{}) // 多包、标的物、采购意向、中标候选
  1403. for _, m := range qu.ObjArrToMapArr((*project)["v_fields"].([]interface{})) {
  1404. if m["child"] != nil {
  1405. if qu.ObjToString(m["key"]) == "extend" {
  1406. m["enable"] = true
  1407. f.T["diy_fields"] = m["child"]
  1408. } else {
  1409. var a []string
  1410. for _, m2 := range qu.ObjArrToMapArr(m["child"].([]interface{})) {
  1411. a = append(a, qu.ObjToString(m2["key"]))
  1412. }
  1413. a2[qu.ObjToString(m["key"])] = a
  1414. }
  1415. } else {
  1416. a1 = append(a1, qu.ObjToString(m["key"]))
  1417. }
  1418. }
  1419. for _, m := range fields {
  1420. if qu.ObjToString(m["descript"]) == "基本字段" {
  1421. if len(a1) > 0 {
  1422. m["enable"] = true
  1423. s := strings.Join(a1, ",")
  1424. for _, m2 := range m["child"].([]map[string]interface{}) {
  1425. if strings.Contains(s, qu.ObjToString(m2["key"])) {
  1426. m2["enable"] = true
  1427. }
  1428. }
  1429. }
  1430. } else {
  1431. if a3 := a2[qu.ObjToString(m["key"])]; a3 != nil {
  1432. m["enable"] = true
  1433. for _, m2 := range m["child"].([]map[string]interface{}) {
  1434. s := strings.Join(a3.([]string), ",")
  1435. if strings.Contains(s, qu.ObjToString(m2["key"])) {
  1436. m2["enable"] = true
  1437. }
  1438. }
  1439. } else {
  1440. continue
  1441. }
  1442. }
  1443. }
  1444. f.T["fields"] = fields
  1445. } else {
  1446. f.T["fields"] = util.FieldsArr
  1447. }
  1448. f.T["pid"] = pid
  1449. _ = f.Render("project/project_field.html", &f.T)
  1450. }
  1451. }
  1452. func (f *Front) ProjectData() {
  1453. defer qu.Catch() //项目id
  1454. appid := f.GetString("appid")
  1455. if f.Method() == "POST" {
  1456. start, _ := f.GetInteger("start")
  1457. limit, _ := f.GetInteger("length")
  1458. draw, _ := f.GetInteger("draw")
  1459. searchStr := f.GetString("search[value]")
  1460. searchStr = strings.TrimSpace(searchStr)
  1461. query := map[string]interface{}{}
  1462. query["appid"] = appid
  1463. if searchStr != "" {
  1464. query["$or"] = []interface{}{
  1465. map[string]interface{}{"v_baseinfo.projectname": map[string]interface{}{"$regex": searchStr}},
  1466. map[string]interface{}{"v_baseinfo.title": map[string]interface{}{"$regex": searchStr}},
  1467. }
  1468. }
  1469. list, _ := util.Mgo.Find(util.DATACOLLNAME, query, bson.M{"_id": 1}, nil, false, start, limit)
  1470. count := util.Mgo.Count(util.DATACOLLNAME, query)
  1471. f.ServeJson(map[string]interface{}{"draw": draw, "data": *list, "recordsFiltered": count, "recordsTotal": count})
  1472. } else {
  1473. f.T["appid"] = appid
  1474. _ = f.Render("project/project_data.html", &f.T)
  1475. }
  1476. }