// extpackage
package extract

import (
	"jy/clear"
	ju "jy/util"
	"log"
	qu "qfw/util"
	"reflect"
	"regexp"
	"sort"
	"unicode/utf8"
)


func pkvdata(pkg *ju.BlockPackage, sonJobResult *map[string]interface{}, e *ExtractTask, isSite bool, codeSite string, isclearMoney string) {

	if pkg.ColonKV != nil {
		kvparse(pkg.ColonKV, e, sonJobResult, isSite, codeSite, isclearMoney)
	}
	if pkg.TableKV != nil {
		kvparse(pkg.TableKV, e, sonJobResult, isSite, codeSite, isclearMoney)
	}
	if pkg.SpaceKV != nil {
		kvparse(pkg.SpaceKV, e, sonJobResult, isSite, codeSite, isclearMoney)
	}
}

func kvparse(p *ju.JobKv, e *ExtractTask, sonJobResult *map[string]interface{}, isSite bool, codeSite string, isclearMoney string) {
	if p != nil {
		for pk, pv2 := range p.KvTags {
			if len(pv2) > 1 && !(pk == "预算" || pk == "中标金额"||pk == "招标代理费（中标服务费）") {
				tmp := []*ju.Tag{}
				var tmpindex, tmpweight int = -9999, -9999
				for ii, vv := range pv2 {
					if pk == "中标单位" && regexp.MustCompile("[0-9.元人￥$]").MatchString(vv.Value) {
						continue
					}
					if tmpweight < vv.Weight {
						tmpindex = ii
						tmpweight = vv.Weight
					}
				}
				if tmpindex == -9999 {
					continue
				}
				tmp = append(tmp, pv2[tmpindex])
				p.KvTags[pk] = tmp
			}
		}
		for pk, pv := range p.KvTags {
			if len(pv) == 0 {
				continue
			}
			tags := ju.GetTags(pk, isSite, codeSite)
			if tags.Len() > 0 {
				if qu.Float64All((*sonJobResult)["budget"]) == 0 && tags[0].Key == "预算" {
					lock.Lock()
					cfn := e.ClearFn["budget"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{pv[0].Value, ""}, codeSite, isclearMoney)
					if data[0] == 0 {
						if istrue, ok := data[len(data)-1].(bool); istrue && ok {
							(*sonJobResult)["budget"] = data[0]
						}
					}
					continue
				}
				if qu.Float64All((*sonJobResult)["bidamount"]) == 0 && tags[0].Key == "中标金额" {
					lock.Lock()
					cfn := e.ClearFn["bidamount"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{pv[0].Value, ""}, codeSite, isclearMoney)
					if istrue, ok := data[len(data)-1].(bool); istrue && ok {
						(*sonJobResult)["bidamount"] = data[0]
					}
					continue
				}
				if qu.Float64All((*sonJobResult)["agencyfee"]) == 0 && tags[0].Key == "招标代理费（中标服务费）" {
					lock.Lock()
					cfn := e.ClearFn["agencyfee"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{pv[0].Value, ""}, codeSite, isclearMoney)
					if istrue, ok := data[len(data)-1].(bool); istrue && ok {
						(*sonJobResult)["agencyfee"] = data[0]
					}
					continue
				}

				if ((*sonJobResult)["winner"] == nil || (*sonJobResult)["winner"] == "") && tags[0].Key == "中标单位" {
					if winnerorderNotReg.MatchString(pv[0].Value) {
						continue
					}
					for _, ev := range e.PkgRuleCores {
						for _, evb := range ev.RuleBacks {
							if evb.Field == "winner" && !evb.IsLua && pv[0].Value != "" {
								pv[0].Value = evb.RegPreBac.Reg.ReplaceAllString(pv[0].Value, evb.RegPreBac.Replace)
							}
						}
					}
					if pv[0].Value != "" {
						(*sonJobResult)["winner"] = pv[0].Value
					}
				}
			}
		}
	}
}

var winnerorderNotReg = regexp.MustCompile(`(附件|否决原因|候选|招标失败|注册表|交易中心|序号内容|不足|公告|变更|采购|招标|废标|废止|流标|中标|投标|评标|开标|供应商|金额|万元|元整|预算|报价|单价|第(\d|一|二|三|四|五)(名|包)|排名|候选|确定|标段|(标|一|二|三|四|五)包|中选|成交|包号|(A|B|C|D|E|F|G)包|地址|详情|要求|推荐|名称|评审|得分|合同|平方米|公示期|结果|备注|说明|单位|代表|委托|工作日|营业(执|期)|通过|代码|电话|联系|条件|合理|费率|以上|以下|拟定|为|注：|\d[\s]{0,10}(\.|元|包|米|平米|平方米|吨|辆|千克|克|毫克|毫升|公升|套|件|瓶|箱|只|台|年|月|日|天|号)|(:|：|；|;|？|￥|\*|%)|^[a-zA-Z0-9-]{5,100}|^[a-zA-Z0-9-]{1,100}$|[a-zA-Z0-9-]{10,100})`)

//处理分包信息
func PackageDetail(j *ju.Job, e *ExtractTask, isSite bool, codeSite string) {
	qu.Try(func() {
		if len(j.BlockPackage) > 0 {
			for kk, vv := range j.BlockPackage {
				if vv.Bidamount > 0 {
					lock.Lock()
					cfn := e.ClearFn["bidamount"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{vv.Bidamount, ""}, codeSite, j.IsClearnMoney)
					if istrue, ok := data[len(data)-1].(bool); istrue && ok {
						vv.Bidamount = qu.Float64All(data[0])
						j.BlockPackage[kk] = vv
					}
				}
				if vv.Budget > 0 {
					lock.Lock()
					cfn := e.ClearFn["budget"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{vv.Budget, ""}, codeSite, j.IsClearnMoney)
					if istrue, ok := data[len(data)-1].(bool); istrue && ok {
						vv.Budget = qu.Float64All(data[0])
						j.BlockPackage[kk] = vv
					}
				}
				if vv.Agencyfee > 0 {
					lock.Lock()
					cfn := e.ClearFn["agencyfee"]
					lock.Unlock()
					data := clear.DoClearFn(cfn, []interface{}{vv.Agencyfee, ""}, codeSite, j.IsClearnMoney)
					if istrue, ok := data[len(data)-1].(bool); istrue && ok {
						vv.Agencyfee = qu.Float64All(data[0])
						j.BlockPackage[kk] = vv
					}
				}
			}
			for _, ev := range e.PkgRuleCores {
				for _, eve := range ev.RuleCores {
					if !eve.IsLua {
						ExtRuleCoreByPkgReg(j, eve, e) // 分包正则抽取   预算   中标单位 中标价 成交状态
					}
				}
				for _, evb := range ev.RuleBacks {
					if !evb.IsLua {
						ExtRegBackPkg(j, evb) // 分包正则清理  中标单位 成交状态   内容 名称
					}
				}
			}
			ordertmp := map[int][]map[string]interface{}{}
			ordertmpint := []int{} //中标排序人一共几组
			//中标候选人
			for _, v := range j.Winnerorder {
				if vtype, ok := v["type"].(int); ok {
					if ordertmp[vtype] == nil {
						ordertmpint = append(ordertmpint, vtype)
						tmp := make([]map[string]interface{}, 0)
						tmp = append(tmp, v)
						ordertmp[vtype] = tmp
					} else {
						ordertmp[vtype] = append(ordertmp[vtype], v)
					}
				}
			}
			tmpkeys := []string{}
			for k, _ := range j.BlockPackage {
				if k == "" {
					continue
				}
				tmpkeys = append(tmpkeys, k)
			}
			sort.Strings(tmpkeys)
			packageResult := map[string]map[string]interface{}{}
			//packagenum := len(j.BlockPackage)
			tmpindex := -1
			for _, pkName := range tmpkeys {
				tmpindex++
				pkg, ok := j.BlockPackage[pkName]
				if !ok || (utf8.RuneCountInString(pkName) > 7 && len(tmpkeys)>=1) {
					continue
				}
				//是否清理标记
				clearmap := map[string]bool{}
				sonJobResult := map[string]interface{}{}
				if pkg != nil {
					sonJobResult["origin"] = pkg.Origin
					sonJobResult["text"] = pkg.Text
					sonJobResult["name"] = pkg.Name
					if pkg.Winner != "" {
						sonJobResult["winner"] = pkg.Winner
					}
					if pkg.WinnerPerson != "" {
						sonJobResult["winnertel"] = pkg.WinnerTel
						sonJobResult["winnerperson"] = pkg.WinnerPerson
					}
					if pkg.IsTrueBudget {
						sonJobResult["budget"] = pkg.Budget
					}
					if pkg.IsTrueAgencyfee {
						sonJobResult["agencyfee"] = pkg.Agencyfee
					}
					if pkg.IsTrueBidamount {
						sonJobResult["bidamount"] = pkg.Bidamount
					}
					if pkg.Winner == "" && len(j.Winnerorder) > 0 {
						if sonJobResult["winnerorder"] == nil && len(tmpkeys) == len(ordertmpint) { //分包和中标候选人长度一样
							//ordertmp[ordertmpint[tmpindex]] 取中标候选人组
							sonJobResult["winnerorder"] = ordertmp[ordertmpint[tmpindex]]
							if sonJobResult["bidamount"] == nil || sonJobResult["bidamount"].(float64) <= 0 {
								if ordertmp[ordertmpint[tmpindex]][0]["price"] != nil {
									moneys := clear.ObjToMoney([]interface{}{ordertmp[ordertmpint[tmpindex]][0]["price"], ""}, j.SpiderCode, j.IsClearnMoney)
									if len(moneys) > 0 && moneys[len(moneys)-1].(bool) {
										if vf, ok := moneys[0].(float64); ok {
											sonJobResult["bidamount"] = vf
										}
									}
								}
							}
							if sonJobResult["winner"] == nil || sonJobResult["winner"] == "" {
								sonJobResult["winner"] = ordertmp[ordertmpint[tmpindex]][0]["entname"]
							}
						}
					} else {
						if (sonJobResult["winner"] == nil || sonJobResult["winner"] == "") && len(j.Winnerorder) > 0 {
							if j.Winnerorder[0]["price"] != nil {
								sonJobResult["bidamount"] = qu.Float64All(j.Winnerorder[0]["price"])
							}
							sonJobResult["winner"] = j.Winnerorder[0]["entname"]
						}
						if len(pkg.WinnerOrder) > 0 {
							sonJobResult["winnerorder"] = pkg.WinnerOrder
							sonJobResult["winner"] = pkg.WinnerOrder[0]["entname"]
						}
						if sonJobResult["winner"] == nil || sonJobResult["winner"] == "" {
							sonJobResult["winner"] = pkg.Winner
						}
					}
					pkvdata(pkg, &sonJobResult, e, isSite, codeSite, j.IsClearnMoney)

					sonJobResult["type"] = pkg.Type
					if len(tmpkeys) == 1 {
						if qu.Float64All(sonJobResult["budget"]) == 0 && pkg.IsTrueBudget {
							for _, bv := range j.Block {
								kvparse(bv.ColonKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
								kvparse(bv.TableKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
								kvparse(bv.SpaceKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
							}
						}
						if qu.Float64All(sonJobResult["agencyfee"]) == 0 && pkg.IsTrueAgencyfee {
							for _, bv := range j.Block {
								kvparse(bv.ColonKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
								kvparse(bv.TableKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
								kvparse(bv.SpaceKV, e, &sonJobResult, isSite, codeSite, j.IsClearnMoney)
							}
						}
					}
					if sonJobResult["name"] == nil || sonJobResult["name"] == "" {
						sonJobResult["name"] = j.Title
					}
				}
				//如果有中标候选人排序，优先用第一中标候选人的中标单位和中标金额覆盖该包里面相应的字段的值
				if pkg.WinnerOrder != nil && len(pkg.WinnerOrder) > 0 {
					firstWinnerOrder := pkg.WinnerOrder[0]
					if qu.ObjToString(sonJobResult["winner"]) == "" || (!pkg.Accuracy && qu.ObjToString(firstWinnerOrder["entname"]) != "" && qu.Int64All(firstWinnerOrder["sort"]) == 1) {
						sonJobResult["winner"] = firstWinnerOrder["entname"]
					}
					if (qu.Float64All(sonJobResult["bidamount"]) == 0 && pkg.IsTrueBidamount) || (!pkg.Accuracy && qu.Float64All(firstWinnerOrder["price"]) > 0 && qu.Int64All(firstWinnerOrder["sort"]) == 1) {
						if firstWinnerOrder["price"] != nil {
							sonJobResult["bidamount"] = firstWinnerOrder["price"]
						}
					}
				}
				//log.Println(pkName, sonJobResult)
				sonJobResult["clear"] = clearmap
				packageResult[pkName] = sonJobResult

			}
			if len(packageResult) > 0 {
				j.PackageInfo = packageResult
				if len(j.Result["winner"]) == 0 {
					tmpsss := []*ju.ExtField{}
					for k, v := range packageResult {
						tmpsss = append(tmpsss, &ju.ExtField{Field: "winner", ExtFrom: "j.PackageInfo." + k + ".winner", Value: v["winner"], Weight: -999})
					}
					j.Result["winner"] = tmpsss
				}
			}
		}
		//extRegBackPack(j, e)
	}, func(err interface{}) {
		log.Println("PackageDetail err", err)
	})
}

//清理分包信息
func extRegBackPack(j *ju.Job, e *ExtractTask) {
	defer qu.Catch()
	//正则清理
	if j.CategorySecond == "" {
		for _, rc1 := range e.RuleCores[j.Category] {
			for _, rc := range rc1 {
				for pk, pack := range j.PackageInfo {
					clear, _ := pack["clear"].(map[string]interface{})
					for k, val := range pack {
						if b, ok := clear[k].(bool); ok && b {
							if rc.Field == k {
								text := qu.ObjToString(val)
								for _, in := range rc.RuleBacks {
									if text != "" && !in.IsLua {
										text = in.RegPreBac.Reg.ReplaceAllString(text, in.RegPreBac.Replace)
									}
								}
								pack[k] = text
							}
						}
					}
					j.PackageInfo[pk] = pack
				}
			}
		}
	} else {
		for _, rc1 := range e.RuleCores[j.Category+"_"+j.CategorySecond] {
			for _, rc := range rc1 {
				for pk, pack := range j.PackageInfo {
					clear, _ := pack["clear"].(map[string]interface{})
					for k, val := range pack {
						if b, ok := clear[k].(bool); ok && b {
							if rc.Field == k {
								text := qu.ObjToString(val)
								for _, in := range rc.RuleBacks {
									if text != "" && !in.IsLua {
										text = in.RegPreBac.Reg.ReplaceAllString(text, in.RegPreBac.Replace)
									}
								}
								pack[k] = text
							}
						}
					}
					j.PackageInfo[pk] = pack
				}
			}
		}
	}
	//通用正则清理
	for _, in := range e.RuleBacks {
		for _, pack := range j.PackageInfo {
			for k, val := range pack {
				if in.Field == k {
					text := qu.ObjToString(val)
					if text != "" && !in.IsLua {
						text = in.RegPreBac.Reg.ReplaceAllString(text, in.RegPreBac.Replace)
					}
					pack[k] = text
				}
			}
		}
	}
	//函数清理
	for _, pack := range j.PackageInfo {
		for key, val := range pack {
			if reflect.TypeOf(val) != nil && (reflect.TypeOf(val).String() == "float64" || reflect.TypeOf(val).String() == "int64") {
				continue
			} else {
				lock.Lock()
				cfn := e.ClearFn[key]
				lock.Unlock()
				data := clear.DoClearFn(cfn, []interface{}{val, j.Content}, j.SpiderCode, j.IsClearnMoney)
				pack[key] = data[0]
			}
		}
	}

	//特殊属性的分包清理
	for _, rc := range e.PkgRuleCores {
		for pk, pack := range j.PackageInfo {
			for k, val := range pack {
				if rc.Field == k {
					text := qu.ObjToString(val)
					for _, in := range rc.RuleBacks {
						if text != "" {
							if !in.IsLua { //正则
								text = in.RegPreBac.Reg.ReplaceAllString(text, in.RegPreBac.Replace)
							} else { //lua
								result := GetResultMapForLua(j)
								lua := ju.LuaScript{Code: in.Code, Name: in.Name, Result: result, Script: in.RuleText}
								if j != nil {
									lua.Block = j.Block
								}
								extinfo := lua.RunScript("back")
								if extinfo["value"] != nil {
									text = qu.ObjToString(extinfo["value"])
								}
							}
						}
					}
					pack[k] = text
				}
			}
			j.PackageInfo[pk] = pack
		}
	}
}
