Bladeren bron

Merge branch 'master' of http://192.168.3.207:8080/data_processing/fieldproject

zhengkun 2 jaren geleden
bovenliggende
commit
ac31bd7f41
49 gewijzigde bestanden met toevoegingen van 1685 en 9101 verwijderingen
  1. 16 4
      README.md
  2. 0 165
      common_utils/clearHtml.go
  3. 0 696
      common_utils/common.go
  4. 0 99
      common_utils/config.go
  5. 0 79
      common_utils/date.go
  6. 0 0
      common_utils/elastic/city.json
  7. 0 357
      common_utils/elastic/elasticSim.go
  8. 0 1169
      common_utils/elastic/elasticutil.go
  9. 0 60
      common_utils/encryptarticle.go
  10. 0 17
      common_utils/go.mod
  11. 0 180
      common_utils/go.sum
  12. 0 230
      common_utils/log/log.go
  13. 0 53
      common_utils/log/log_test.go
  14. 0 318
      common_utils/logger.go
  15. 0 614
      common_utils/mongodb/mongodb.go
  16. 0 504
      common_utils/mysql.go
  17. 0 504
      common_utils/mysqldb/mysql.go
  18. 0 161
      common_utils/protocol.go
  19. 0 70
      common_utils/redis/redisloginutil.go
  20. 0 517
      common_utils/redis/redisutil.go
  21. 0 86
      common_utils/redis/redisutil_test.go
  22. 0 135
      common_utils/simple_encrypt.go
  23. 0 78
      common_utils/udp.go
  24. 0 64
      common_utils/validator/converter.go
  25. 0 47
      common_utils/validator/error.go
  26. 0 96
      common_utils/validator/numerics.go
  27. 0 107
      common_utils/validator/patterns.go
  28. 0 655
      common_utils/validator/types.go
  29. 0 270
      common_utils/validator/utils.go
  30. 0 1622
      common_utils/validator/validator.go
  31. 51 6
      fieldproject_com/common.toml
  32. 28 7
      fieldproject_com/config/conf.go
  33. 33 1
      fieldproject_com/config/conf_test.go
  34. 9 5
      fieldproject_com/go.mod
  35. 54 95
      fieldproject_com/go.sum
  36. 46 9
      fieldproject_com/init.go
  37. 168 21
      fieldproject_com/main.go
  38. BIN
      fieldproject_com/orgdata
  39. BIN
      fieldproject_com/orgdata_linux
  40. 392 0
      fieldproject_com/task.go
  41. 180 0
      fieldproject_com/taskEs.go
  42. 272 0
      fieldproject_com/util.go
  43. 41 0
      fieldproject_inc_data/common.toml
  44. 92 0
      fieldproject_inc_data/config/conf.go
  45. 66 0
      fieldproject_inc_data/config/conf_test.go
  46. 9 0
      fieldproject_inc_data/go.mod
  47. 100 0
      fieldproject_inc_data/go.sum
  48. 95 0
      fieldproject_inc_data/init.go
  49. 33 0
      fieldproject_inc_data/main.go

+ 16 - 4
README.md

@@ -1,13 +1,25 @@
 ## 领域化产品-数据处理项目
 
-
-### common_utils 公共包
-
 ###  fieldproject_com(公共数据处理模块)
 ####  org_data
 + 组织机构处理,包含企业、医院、事业单位等信息
-+   
++ es表数据处理,代码
+
+#### 处理逻辑
++ 医疗机构表信息处理,同步法人基本信息到法人表
+  + 医疗机构数据分为三部分信息:
+  + 1、凭安数据找到company_id直接同步更新
+  + 2、找
++ 基于bidding表医疗领域标签,处理标讯数据的企业信息
+  + mark_id = 1,直接入法人库
+  + mark_id = 2,待处理的信息入法人库
+  + mark_id = 3,暂时不进法人库
+  + mark_id = 4, 进法人信息库
 
+### fieldproject_inc_data 增量数据
++ 配合任务调度平台定时发送udp任务
++ 标讯处理完之后,处理es领域字段、项目数据领域字段
+  + 
 
 ### fieldproject_medical(医疗数据处理模块) 
 + data_preparation (基础信息~数据准备~)

+ 0 - 165
common_utils/clearHtml.go

@@ -1,165 +0,0 @@
-package util
-
-import (
-	"github.com/PuerkitoBio/goquery"
-	"regexp"
-	"strings"
-	"unicode/utf8"
-)
-
-//
-type Cut struct {
-	annotate      *regexp.Regexp
-	tag           *regexp.Regexp
-	scripttag     *regexp.Regexp
-	inputag       *regexp.Regexp
-	isborder      *regexp.Regexp
-	hiddentag     *regexp.Regexp
-	styletag      *regexp.Regexp
-	colstag       *regexp.Regexp
-	rowstag       *regexp.Regexp
-	display       *regexp.Regexp
-	multiCR       *regexp.Regexp
-	replBlankLine *regexp.Regexp
-	replStartWrap *regexp.Regexp
-	replTags2CR   []string
-	retainTags2CR []string
-}
-
-//
-func NewCut() *Cut {
-	t, _ := regexp.Compile("<[^>]+>")
-	m, _ := regexp.Compile("([\r\n][\u3000\u2003\u00a0\\s]*)+|[\r\n]+")
-	//sc, _ := regexp.Compile("\\<script[^\\>]*\\>*[^\\>]+\\</script\\>")
-	//ss, _ := regexp.Compile("\\<style[^\\>]*\\>*[^\\>]+\\</style\\>")
-	scs := regexp.MustCompile("(?s)<(script|style)[^>]*>.+?</(script|style)>")
-	at := regexp.MustCompile("(?s)<(!%-%-|!--).*?(%-%-|--)>") //注释 css
-	hiddentag := regexp.MustCompile(`<\s*input[^<]*type=("|')hidden("|')[^<]*>`)
-	input := regexp.MustCompile(`<\s*input[^<]*value=("|')([^>"']*)[^<]*>`)
-	cols, _ := regexp.Compile(`colspan="\d+"`)
-	rows, _ := regexp.Compile(`rowspan="\d+"`)
-	border, _ := regexp.Compile(`(border="(\d+)")|(cellpadding="(\d+)")|(cellspacing="(\d+)")`)
-	dis, _ := regexp.Compile(`display:none`)
-	return &Cut{
-		annotate:      at,
-		tag:           t,
-		scripttag:     scs,
-		hiddentag:     hiddentag,
-		inputag:       input,
-		colstag:       cols,
-		isborder:      border,
-		rowstag:       rows,
-		display:       dis,
-		multiCR:       m,
-		replBlankLine: regexp.MustCompile("\\s+[\r\n]"),
-		replStartWrap: regexp.MustCompile("^[\u3000\u2003\u00a0\\s]+|[\u3000\u2003\u00a0\\s]+$"),
-		replTags2CR:   []string{"div", "p", "br", "h1", "h2", "h3", "h4", "h5"},
-		retainTags2CR: []string{"table", "thead", "tfoot", "tbody", "th", "td", "tr"},
-	}
-}
-
-//清理HTML标签
-func (c *Cut) ClearHtml(src string) string {
-	src = c.replBlankLine.ReplaceAllString(src, "")
-	src = strings.Replace(src, ">\n", ">", -1)
-	src = strings.Replace(src, " ", "", -1)
-	//标签全转小写
-	src = c.tag.ReplaceAllStringFunc(src, strings.ToLower)
-	//清script,style
-	src = c.scripttag.ReplaceAllString(src, "")
-	//清理注释文本
-	src = c.annotate.ReplaceAllString(src, "")
-	//清理input
-	src = c.hiddentag.ReplaceAllString(src, "")
-	src = c.inputag.ReplaceAllString(src, "$2")
-	document, err := goquery.NewDocumentFromReader(strings.NewReader(src))
-	if err == nil {
-		if tmpstr, err := document.Each(func(i int, sel *goquery.Selection) {
-			sel.Find("td").Each(func(i int, selection *goquery.Selection) {
-				val, b := selection.Attr("title")
-				if b && strings.Trim(val, " ") != "" {
-					tmpstr := strings.TrimFunc(selection.Text(), func(r rune) bool {
-						return r == 9 || r == 32
-					})
-					if utf8.RuneCountInString(strings.Trim(tmpstr, " ")) < utf8.RuneCountInString(strings.Trim(val, " ")) {
-						selection.SetText(strings.Trim(val, " "))
-					}
-				}
-			})
-		}).Html(); err == nil {
-			src = tmpstr
-		}
-	}
-	//换结束标签
-	src = c.tag.ReplaceAllStringFunc(src, func(tmp string) string {
-		tmp = strings.Replace(tmp, " ", "", -1)
-		//保留这些标签
-		for _, v := range c.retainTags2CR {
-			if "<"+v+">" == tmp || "</"+v+">" == tmp {
-				if tmp == "</table>" {
-					return tmp + "\n"
-				}
-				return tmp
-			}
-			if strings.HasPrefix(tmp, "<"+v) {
-				dispstrs := c.display.FindAllString(tmp, -1)
-				rowstrs := c.rowstag.FindAllString(tmp, -1)
-				colstrs := c.colstag.FindAllString(tmp, -1)
-				con := "<" + v
-				if con == "<table" {
-					if isHasBoder(tmp, c.isborder) {
-						con = con + ` border="1"`
-					}
-				}
-				if len(colstrs) > 0 { //处理多列合并
-					con += " " + colstrs[0]
-				}
-				if len(rowstrs) > 0 { //处理多行合并
-					con += " " + rowstrs[0]
-				}
-				if len(dispstrs) > 0 {
-					con += " style=\"" + dispstrs[0] + "\""
-				}
-				return con + ">"
-
-			}
-		}
-		if tmp == "<br>" || tmp == "<br/>" || tmp == "<center>" || tmp == "</center>" || tmp == "<ul>" || tmp == "</ul>" {
-			return "\n"
-		}
-		if tmp[1] != 47 { //开始标签
-			for _, v := range c.replTags2CR {
-				if v == tmp[1:len(tmp)-1] {
-					return "\n"
-				}
-			}
-			return ""
-		}
-		for _, v := range c.replTags2CR {
-			if v == tmp[2:len(tmp)-1] {
-				return "\n"
-			}
-		}
-		return ""
-	})
-	src = c.replStartWrap.ReplaceAllString(src, "")
-	src = c.replBlankLine.ReplaceAllString(src, "\n")
-	//清除多余换行
-	c.multiCR.ReplaceAllString(src, "\n")
-	return strings.Replace(src, "\n", "<br/>", -1)
-}
-
-//判断table是否加表格线
-func isHasBoder(con string, reg *regexp.Regexp) bool {
-	res := reg.FindAllStringSubmatch(con, -1)
-	hasBorder := false
-	for _, v := range res {
-		for k, val := range v {
-			if k > 0 && k%2 == 0 && IntAll(val) > 0 {
-				hasBorder = true
-				break
-			}
-		}
-	}
-	return hasBorder
-}

+ 0 - 696
common_utils/common.go

@@ -1,696 +0,0 @@
-package util
-
-import (
-	"crypto/md5"
-	cryptoRand "crypto/rand"
-	"encoding/hex"
-	"encoding/json"
-	"encoding/xml"
-	"fmt"
-	bson "gopkg.in/mgo.v2/bson"
-	"io"
-	"log"
-	"math"
-	"math/big"
-	mathRand "math/rand"
-	"net/url"
-	"reflect"
-	"regexp"
-	"runtime"
-	"sort"
-	"strconv"
-	"strings"
-	"time"
-
-	"github.com/dchest/captcha"
-)
-
-const (
-	tmp = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ12345678900"
-)
-
-//短地址加密
-func EncodeArticleId(keys ...string) string {
-	kstr := strings.Join(keys, ",")
-	return SE.EncodeString(kstr)
-}
-
-//短地址解密
-func DecodeArticleId(id string) []string {
-	return strings.Split(SE.DecodeString(id), ",")
-}
-
-//短地址加密,二次加密带校验和
-func EncodeArticleId2ByCheck(keys ...string) string {
-	kstr := strings.Join(keys, ",")
-	kstr = SE.EncodeStringByCheck(kstr)
-	return url.QueryEscape("ABC" + SE2.EncodeStringByCheck(kstr))
-}
-
-//短地址解密,二次解密带校验和
-func DecodeArticleId2ByCheck(id string) []string {
-	if !strings.Contains(id, "+") { //新加密算法解密
-		id, _ = url.QueryUnescape(id)
-	}
-	if id[:3] == "ABC" { //前三位为ABC是新加密数据
-		kstr := SE2.DecodeStringByCheck(id[3:])
-		return strings.Split(SE.DecodeStringByCheck(kstr), ",")
-	} else { //历史数据
-		rep := DecodeArticleId(id)
-		oldpushid := "58f87a9561a0721f157bc74d" //剑鱼1.9发版前最后一次推送信息id
-		if rep[0] > oldpushid {
-			return []string{""}
-		} else {
-			return rep
-		}
-	}
-}
-
-func Uuid(length int) string {
-	ret := []string{}
-	r := mathRand.New(mathRand.NewSource(time.Now().UnixNano()))
-	for i := 0; i < length; i++ {
-		index := r.Intn(62)
-		ret = append(ret, tmp[index:index+1])
-	}
-	return strings.Join(ret, "")
-}
-
-//计算字符串和值
-func Sumstring(code string) (sum int) {
-	tmp := []rune(code)
-	for _, v := range tmp {
-		sum = sum + int(v)
-	}
-	return
-}
-
-//获取随机数
-func GetRandom(n int) string {
-	var idChars = []byte("0123456789")
-	b := captcha.RandomDigits(n)
-	for i, c := range b {
-		b[i] = idChars[c]
-	}
-	return string(b)
-}
-
-//获取复杂的随机数
-func GetLetterRandom(length int, flag ...bool) string {
-	var idChars = []byte("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz")
-	var mod byte = 52
-	if len(flag) > 0 && flag[0] {
-		idChars = []byte("ABCDEFGHIJKLMNOPQRSTUVWXYZ")
-		mod = 26
-	}
-	b := make([]byte, length)
-	maxrb := byte(256 - (256 % int(mod)))
-	i := 0
-EXIT:
-	for {
-		r := make([]byte, length+(length/4))
-		if _, err := io.ReadFull(cryptoRand.Reader, r); err != nil {
-			panic("captcha: error reading random source: " + err.Error())
-		}
-		for _, c := range r {
-			if c > maxrb {
-				continue
-			}
-			b[i] = c % mod
-			i++
-			if i == length {
-				break EXIT
-			}
-		}
-	}
-	for i, c := range b {
-		b[i] = idChars[c]
-	}
-	return string(b)
-}
-
-/*获取复杂的随机数,数字和字母的组合
- * c > 2 数字的个数和字母的个数随机分配
- * n 数字的个数
- * l 字母的个数
- */
-func GetComplexRandom(c, n, l int) string {
-	if c < 2 && (n < 1 || l < 1) {
-		return "--"
-	}
-	r := mathRand.New(mathRand.NewSource(time.Now().UnixNano()))
-	myCommonMethod := func(flag bool) int {
-		if flag {
-			return r.Intn(c-1) + 1
-		} else {
-			return r.Intn(c)
-		}
-	}
-	if c >= 2 {
-		n = myCommonMethod(true)
-		l = c - n
-	} else {
-		c = l + n
-	}
-	value := GetRandom(n) + GetLetterRandom(l)
-	var array = strings.Split(value, "")
-	for i := 0; i < c/2; i++ {
-		r1 := myCommonMethod(false)
-		r2 := myCommonMethod(false)
-		o := array[r1]
-		array[r1] = array[r2]
-		array[r2] = o
-	}
-	return strings.Join(array, "")
-}
-
-/*隐藏部分账号
- *返回手机号:150...70765 邮箱:...shenjun@vip.qq.com
- */
-func EncryCode(value string) string {
-	if len(value) == 0 {
-		return value
-	} else if strings.Contains(value, "@") {
-		start := strings.Index(value, "@") / 2
-		if start == 0 {
-			start++
-		}
-		value = "...." + string(value[start:])
-	} else {
-		value = string(value[0:3]) + "..." + string(value[len(value)-4:])
-	}
-	return value
-}
-
-//生成32位md5字串
-func GetMd5String(s string) string {
-	h := md5.New()
-	h.Write([]byte(s))
-	return hex.EncodeToString(h.Sum(nil))
-}
-
-//obj(string,M)转M,查询用到
-func ObjToMap(obj interface{}) *map[string]interface{} {
-	data := make(map[string]interface{})
-	if s, ok := obj.(string); ok {
-		json.Unmarshal([]byte(strings.Replace(s, "'", "\"", -1)), &data)
-	} else if s1, ok1 := obj.(map[string]interface{}); ok1 {
-		data = s1
-	} else if s1, ok1 := obj.(*map[string]interface{}); ok1 {
-		return s1
-	} else {
-		data = nil
-	}
-	return &data
-}
-
-/*UTC类型时间转字符串
- *flag==true,日期格式yyyy-mm-dd hh:mm:ss
- *flag==false,日期格式yyyy-mm-dd
- */
-func LongToDate(date interface{}, flag bool) string {
-	var int64Date int64
-	if l1, ok1 := date.(float64); ok1 {
-		int64Date = int64(l1)
-	} else if l2, ok2 := date.(int64); ok2 {
-		int64Date = l2
-	} else if l3, ok3 := date.(int); ok3 {
-		int64Date = int64(l3)
-	}
-	t := time.Unix(int64Date, 0)
-	if flag {
-		return t.Format("2006-01-02 15:04:05")
-	} else {
-		return t.Format("2006-01-02")
-	}
-}
-
-func IntAll(num interface{}) int {
-	return IntAllDef(num, 0)
-}
-
-func Int64All(num interface{}) int64 {
-	if i, ok := num.(int64); ok {
-		return int64(i)
-	} else if i0, ok0 := num.(int32); ok0 {
-		return int64(i0)
-	} else if i1, ok1 := num.(float64); ok1 {
-		return int64(i1)
-	} else if i2, ok2 := num.(int); ok2 {
-		return int64(i2)
-	} else if i3, ok3 := num.(float32); ok3 {
-		return int64(i3)
-	} else if i4, ok4 := num.(string); ok4 {
-		i64, _ := strconv.ParseInt(i4, 10, 64)
-		//in, _ := strconv.Atoi(i4)
-		return i64
-	} else if i5, ok5 := num.(int16); ok5 {
-		return int64(i5)
-	} else if i6, ok6 := num.(int8); ok6 {
-		return int64(i6)
-	} else if i7, ok7 := num.(*big.Int); ok7 {
-		in, _ := strconv.ParseInt(fmt.Sprint(i7), 10, 64)
-		return int64(in)
-	} else if i8, ok8 := num.(*big.Float); ok8 {
-		in, _ := strconv.ParseInt(fmt.Sprint(i8), 10, 64)
-		return int64(in)
-	} else {
-		return 0
-	}
-}
-
-func Float64All(num interface{}) float64 {
-	if i, ok := num.(float64); ok {
-		return float64(i)
-	} else if i0, ok0 := num.(int32); ok0 {
-		return float64(i0)
-	} else if i1, ok1 := num.(int64); ok1 {
-		return float64(i1)
-	} else if i2, ok2 := num.(int); ok2 {
-		return float64(i2)
-	} else if i3, ok3 := num.(float32); ok3 {
-		return float64(i3)
-	} else if i4, ok4 := num.(string); ok4 {
-		in, _ := strconv.ParseFloat(i4, 64)
-		return in
-	} else if i5, ok5 := num.(int16); ok5 {
-		return float64(i5)
-	} else if i6, ok6 := num.(int8); ok6 {
-		return float64(i6)
-	} else if i6, ok6 := num.(uint); ok6 {
-		return float64(i6)
-	} else if i6, ok6 := num.(uint8); ok6 {
-		return float64(i6)
-	} else if i6, ok6 := num.(uint16); ok6 {
-		return float64(i6)
-	} else if i6, ok6 := num.(uint32); ok6 {
-		return float64(i6)
-	} else if i6, ok6 := num.(uint64); ok6 {
-		return float64(i6)
-	} else if i7, ok7 := num.(*big.Float); ok7 {
-		in, _ := strconv.ParseFloat(fmt.Sprint(i7), 64)
-		return float64(in)
-	} else if i8, ok8 := num.(*big.Int); ok8 {
-		in, _ := strconv.ParseFloat(fmt.Sprint(i8), 64)
-		return float64(in)
-	} else {
-		return 0
-	}
-}
-
-func IntAllDef(num interface{}, defaultNum int) int {
-	if i, ok := num.(int); ok {
-		return int(i)
-	} else if i0, ok0 := num.(int32); ok0 {
-		return int(i0)
-	} else if i1, ok1 := num.(float64); ok1 {
-		return int(i1)
-	} else if i2, ok2 := num.(int64); ok2 {
-		return int(i2)
-	} else if i3, ok3 := num.(float32); ok3 {
-		return int(i3)
-	} else if i4, ok4 := num.(string); ok4 {
-		in, _ := strconv.Atoi(i4)
-		return int(in)
-	} else if i5, ok5 := num.(int16); ok5 {
-		return int(i5)
-	} else if i6, ok6 := num.(int8); ok6 {
-		return int(i6)
-	} else if i7, ok7 := num.(*big.Int); ok7 {
-		in, _ := strconv.Atoi(fmt.Sprint(i7))
-		return int(in)
-	} else if i8, ok8 := num.(*big.Float); ok8 {
-		in, _ := strconv.Atoi(fmt.Sprint(i8))
-		return int(in)
-	} else {
-		return defaultNum
-	}
-}
-
-func ObjToString(old interface{}) string {
-	if nil == old {
-		return ""
-	} else {
-		r, _ := old.(string)
-		return r
-	}
-}
-
-func ObjToStringDef(old interface{}, defaultstr string) string {
-	if nil == old {
-		return defaultstr
-	} else {
-		r, _ := old.(string)
-		if r == "" {
-			return defaultstr
-		}
-		return r
-	}
-}
-
-//对象数组转成string数组
-func ObjArrToStringArr(old []interface{}) []string {
-	if old != nil {
-		new := make([]string, len(old))
-		for i, v := range old {
-			new[i] = v.(string)
-		}
-		return new
-	} else {
-		return nil
-	}
-}
-
-//对象数组转成map数组
-func ObjArrToMapArr(old []interface{}) []map[string]interface{} {
-	if old != nil {
-		new := make([]map[string]interface{}, len(old))
-		for i, v := range old {
-			new[i] = v.(map[string]interface{})
-		}
-		return new
-	} else {
-		return nil
-	}
-}
-
-//map数组转成对象数组
-func MapArrToObjArr(old []map[string]interface{}) []interface{} {
-	if old != nil {
-		new := make([]interface{}, len(old))
-		for i, v := range old {
-			new[i] = v
-		}
-		return new
-	} else {
-		return nil
-	}
-}
-
-func SubstrByByte(str string, length int) string {
-	bs := []byte(str)[:length]
-	bl := 0
-	for i := len(bs) - 1; i >= 0; i-- {
-		switch {
-		case bs[i] >= 0 && bs[i] <= 127:
-			return string(bs[:i+1])
-		case bs[i] >= 128 && bs[i] <= 191:
-			bl++
-		case bs[i] >= 192 && bs[i] <= 253:
-			cl := 0
-			switch {
-			case bs[i]&252 == 252:
-				cl = 6
-			case bs[i]&248 == 248:
-				cl = 5
-			case bs[i]&240 == 240:
-				cl = 4
-			case bs[i]&224 == 224:
-				cl = 3
-			default:
-				cl = 2
-			}
-			if bl+1 == cl {
-				return string(bs[:i+cl])
-			}
-			return string(bs[:i])
-		}
-	}
-	return ""
-}
-
-func SubString(str string, begin, length int) (substr string) {
-	// 将字符串的转换成[]rune
-	rs := []rune(str)
-	lth := len(rs)
-	// 简单的越界判断
-	if begin < 0 {
-		begin = 0
-	}
-	if begin >= lth {
-		begin = lth
-	}
-	end := begin + length
-	if end > lth {
-		end = lth
-	}
-
-	// 返回子串
-	return string(rs[begin:end])
-}
-
-//捕获异常
-func Try(fun func(), handler func(interface{})) {
-	defer func() {
-		if err := recover(); err != nil {
-			for skip := 1; ; skip++ {
-				_, file, line, ok := runtime.Caller(skip)
-				if !ok {
-					break
-				}
-				go log.Printf("%v,%v\n", file, line)
-			}
-			handler(err)
-		}
-	}()
-	fun()
-}
-
-//3目运算
-func If(b bool, to, fo interface{}) interface{} {
-	if b {
-		return to
-	} else {
-		return fo
-	}
-}
-
-//HashCode值
-func HashCode(uid string) int {
-	var h uint32 = 0
-	rs := []rune(uid)
-	for i := 0; i < len(rs); i++ {
-		h = 31*h + uint32(rs[i])
-	}
-	return int(h)
-}
-
-//获取离n天的秒差
-func GetDayStartSecond(n int) int64 {
-	now := time.Now()
-	tom := time.Date(now.Year(), now.Month(), now.Day()+n, 0, 0, 0, 0, time.Local)
-	return tom.Unix()
-}
-
-func InterfaceArrTointArr(arr []interface{}) []int {
-	tmp := make([]int, 0)
-	for _, v := range arr {
-		tmp = append(tmp, int(v.(float64)))
-	}
-	return tmp
-}
-func InterfaceArrToint64Arr(arr []interface{}) []int64 {
-	tmp := make([]int64, 0)
-	for _, v := range arr {
-		tmp = append(tmp, int64(v.(float64)))
-	}
-	return tmp
-}
-
-//根据bsonID转string
-func BsonIdToSId(uid interface{}) string {
-	if uid == nil {
-		return ""
-	} else if u, ok := uid.(string); ok {
-		return u
-	} else {
-		return fmt.Sprintf("%x", string(uid.(bson.ObjectId)))
-	}
-}
-
-func StringTOBsonId(id string) (bid bson.ObjectId) {
-	defer Catch()
-	if id != "" {
-		bid = bson.ObjectIdHex(id)
-	}
-	return
-}
-
-func GetSubDay(t1 int64) int {
-	tt1 := time.Unix(t1, 0)
-	tt2 := time.Now()
-	nt1 := time.Date(tt1.Year(), tt1.Month(), tt1.Day(), 0, 0, 0, 0, time.Local)
-	nt2 := time.Date(tt2.Year(), tt2.Month(), tt2.Day(), 0, 0, 0, 0, time.Local)
-	return int((nt1.Unix() - nt2.Unix()) / 86400)
-}
-func StartWith(value, str string) bool {
-	ok, _ := regexp.MatchString("^"+str, value)
-	return ok
-}
-func EndWith(value, str string) bool {
-	ok, _ := regexp.MatchString(str+"$", value)
-	return ok
-}
-
-//出错拦截
-func Catch() {
-	if r := recover(); r != nil {
-		log.Println(r)
-		for skip := 0; ; skip++ {
-			_, file, line, ok := runtime.Caller(skip)
-			if !ok {
-				break
-			}
-			go log.Printf("%v,%v\n", file, line)
-		}
-	}
-}
-
-func ConvertFileSize(s int) string {
-	size := float64(s)
-	var kb float64 = 1024
-	var mb float64 = kb * 1024
-	var gb float64 = mb * 1024
-	if size >= gb {
-		return fmt.Sprintf("%.1f GB", float64(size/gb))
-	} else if size >= mb {
-		f := float64(size / mb)
-		if f > 100 {
-			return fmt.Sprintf("%.0f MB", f)
-		}
-		return fmt.Sprintf("%.1f MB", f)
-	} else if size >= kb {
-		f := float64(size / kb)
-		if f > 100 {
-			return fmt.Sprintf("%.0f KB", f)
-		}
-		return fmt.Sprintf("%.1f KB", f)
-	}
-	return fmt.Sprintf("%d B", s)
-}
-
-//MD5签名
-func WxSign(format string, param ...interface{}) string {
-	data := fmt.Sprintf(format, param...)
-	h := md5.New()
-	h.Write([]byte(data))
-	sign := strings.ToUpper(hex.EncodeToString(h.Sum(nil)))
-	return sign
-}
-
-//计算时差
-func TimeDiff(date time.Time) string {
-	var date1 = date                        //开始时间
-	var date2 = time.Now()                  //结束时间
-	var date3 = date2.Unix() - date1.Unix() //时间差的毫秒数
-	//计算出相差天数
-	var days = math.Floor(float64(date3 / (24 * 3600)))
-	//计算出小时数
-	var leave1 = date3 % (24 * 3600) //计算天数后剩余的毫秒数
-	var hours = math.Floor(float64(leave1 / (3600)))
-	//计算相差分钟数
-	var leave2 = leave1 % (3600) //计算小时数后剩余的毫秒数
-	var minutes = math.Floor(float64(leave2 / (60)))
-	//计算相差秒数
-	var td = "30秒前"
-	if days > 0 {
-		if days > 10 {
-			if date1.Year() < date2.Year() {
-				td = FormatDate(&date, Date_Short_Layout)
-			} else {
-				td = FormatDate(&date, Date_Small_Layout)
-			}
-		} else {
-			td = fmt.Sprint(days) + "天前"
-		}
-	} else if hours > 0 {
-		td = fmt.Sprint(hours) + "小时前"
-	} else if minutes > 0 {
-		td = fmt.Sprint(minutes) + "分钟前"
-	}
-	return td
-}
-
-func FloatFormat(tmp float64, n int) float64 {
-	fs := fmt.Sprintf("%."+fmt.Sprint(n)+"f", tmp)
-	f, _ := strconv.ParseFloat(fs, 64)
-	return f
-}
-
-//生成微信支付的签名
-func CreateWxSign(afterStr string, obj interface{}, filter ...string) string {
-	filter = append(filter, "sign", "xml")
-	keys := []string{}
-	m := make(map[string]string)
-	t := reflect.TypeOf(obj)
-	v := reflect.ValueOf(obj)
-	k := t.Kind()
-	if t.Kind() == reflect.Ptr {
-		t = t.Elem()
-		k = t.Kind()
-		v = v.Elem()
-	}
-	if k == reflect.Map {
-		for _, key := range v.MapKeys() {
-			keys = append(keys, key.String())
-			m[key.String()] = fmt.Sprint(v.MapIndex(key).Interface())
-		}
-	} else if k == reflect.Struct {
-		for n := 0; n < t.NumField(); n++ {
-			tagName := t.Field(n).Tag.Get("xml")
-			if tagName == "" {
-				tagName = t.Field(n).Tag.Get("json")
-			}
-			if tagName == "" {
-				tagName = t.Field(n).Name
-			}
-			keys = append(keys, tagName)
-			m[tagName] = fmt.Sprint(v.Field(n))
-		}
-	}
-	sort.Strings(keys)
-	vs := []string{}
-L:
-	for _, v := range keys {
-		for _, f := range filter {
-			if f == v {
-				continue L
-			}
-		}
-		if strings.TrimSpace(m[v]) == "" {
-			continue
-		}
-		vs = append(vs, fmt.Sprintf("%s=%s", v, m[v]))
-	}
-	return WxSign(strings.Join(vs, "&") + afterStr)
-}
-
-//简单的xml转map,只有一个层级,没有多层嵌套
-func XmlToMap(input string) map[string]string {
-	var t xml.Token
-	var err error
-	inputReader := strings.NewReader(input)
-	decoder := xml.NewDecoder(inputReader)
-	isStart := false
-	nodeName := ""
-	m := make(map[string]string)
-	for t, err = decoder.Token(); err == nil; t, err = decoder.Token() {
-		switch token := t.(type) {
-		// 处理元素开始(标签)
-		case xml.StartElement:
-			isStart = true
-			nodeName = token.Name.Local
-		// 处理元素结束(标签)
-		case xml.EndElement:
-			isStart = false
-		// 处理字符数据(这里就是元素的文本)
-		case xml.CharData:
-			if isStart {
-				m[nodeName] = string([]byte(token))
-			}
-		default:
-			// ...
-		}
-	}
-	return m
-}

+ 0 - 99
common_utils/config.go

@@ -1,99 +0,0 @@
-package util
-
-import (
-	"encoding/json"
-	"errors"
-	"io/ioutil"
-
-	"os"
-	"strings"
-	"sync"
-)
-
-var lock sync.Mutex
-
-//读取配置文件,可以有2个参数,
-//第一个参数是配置文件路径,如果只有一个参数时,默认配置文件路径为./config.json
-//第二个参数是要注入的对象,可以是结构体,或者是interface对象
-func ReadConfig(config ...interface{}) {
-	var r *os.File
-	if len(config) > 1 {
-		filepath, _ := config[0].(string)
-		println(filepath)
-		r, _ = os.Open(filepath)
-		defer r.Close()
-		bs, _ := ioutil.ReadAll(r)
-		json.Unmarshal(bs, config[1])
-	} else {
-		r, _ = os.Open("./config.json")
-		defer r.Close()
-		bs, _ := ioutil.ReadAll(r)
-		json.Unmarshal(bs, config[0])
-	}
-}
-
-//程序修改SysConfig配置表后,调用写入配置文件
-func WriteSysConfig(config ...interface{}) {
-	var r *os.File
-	var configobj interface{}
-	if len(config) > 1 {
-		filepath, _ := config[0].(string)
-		r, _ = os.OpenFile(filepath, os.O_WRONLY|os.O_TRUNC, 0x644)
-		configobj = config[1]
-	} else {
-		r, _ = os.OpenFile("./config.json", os.O_WRONLY|os.O_TRUNC, 0x644)
-		configobj = config[0]
-	}
-	defer r.Close()
-	if s, ok := configobj.(string); ok {
-		r.Write([]byte(s))
-
-	} else {
-		bs, _ := json.Marshal(configobj)
-		r.Write(bs)
-	}
-}
-
-//按路径查map配置
-//TODO 暂未处理查询路径中是数组的情况
-func GetPropertie(qpath /*map的查询路径*/ string, config map[string]interface{}) (ret interface{}) {
-	//tmp := new(map[string]interface{})
-	tmp := config
-	qps := strings.Split(qpath, ".")
-	length := len(qps)
-	for i, v := range qps {
-		if v1, ok := tmp[v]; ok {
-			//log.Println("类型:", reflect.TypeOf(v1))
-			if v2, ok2 := v1.(map[string]interface{}); ok2 {
-				tmp = v2
-			} else if i == length-1 {
-				//map断了,没有下一层了
-				ret = v1
-			}
-		} else {
-			return nil
-		}
-	}
-	return
-}
-
-//设置值
-//TODO 未处理数组,仅处理map递归型
-func SetPropertie(qpath string, value interface{}, config map[string]interface{}) (err error) {
-	tmp := config
-	qps := strings.Split(qpath, ".")
-	length := len(qps)
-	for i := 0; i < length-1; i++ {
-		if v1, ok1 := (tmp[qps[i]]).(map[string]interface{}); ok1 {
-			tmp = v1
-		} else {
-			err = errors.New("路径查找失败")
-			break
-		}
-
-	}
-	if err == nil {
-		tmp[qps[length-1]] = value
-	}
-	return
-}

+ 0 - 79
common_utils/date.go

@@ -1,79 +0,0 @@
-//日期处理工具类
-package util
-
-import (
-	"fmt"
-	"time"
-)
-
-const (
-	Date_Full_Layout    = "2006-01-02 15:04:05"
-	Date_Short_Layout   = "2006-01-02"
-	Date_Small_Layout   = "01-02"
-	Date_Time_Layout    = "15:04"
-	Date_yyyyMMdd       = "20060102"
-	Date_yyyyMMdd_Point = "2006.01.02"
-)
-
-//当前日期格式化
-func NowFormat(layout string) string {
-	return time.Now().Local().Format(layout)
-}
-
-//日期格式化
-func FormatDate(src *time.Time, layout string) string {
-	return (*src).Local().Format(layout)
-}
-
-//兼容从Java转换过来的数据,java生成的时间戳是按微秒算的,Go中只能按毫秒或纳秒算
-func formatDateWithInt64(src *int64, layout string) string {
-	var tmp int64
-	if *src > 0 {
-		if len(fmt.Sprint(*src)) >= 12 {
-			tmp = (*src) / 1000
-		} else {
-			tmp = (*src)
-		}
-	} else {
-		if len(fmt.Sprint(*src)) >= 13 {
-			tmp = (*src) / 1000
-		} else {
-			tmp = (*src)
-		}
-	}
-	date := time.Unix(tmp, 0)
-	return FormatDate(&date, layout)
-}
-
-func FormatDateByInt64(src *int64, layout string) string {
-	var tmp int64
-	if *src > 0 {
-		if len(fmt.Sprint(*src)) >= 12 {
-			tmp = (*src) / 1000
-		} else {
-			tmp = (*src)
-		}
-	} else {
-		if len(fmt.Sprint(*src)) >= 13 {
-			tmp = (*src) / 1000
-		} else {
-			tmp = (*src)
-		}
-	}
-	date := time.Unix(tmp, 0)
-	return FormatDate(&date, layout)
-}
-
-//支持源端多种格式
-func FormatDateWithObj(src *interface{}, layout string) string {
-	if tmp, ok := (*src).(int64); ok {
-		return formatDateWithInt64(&tmp, layout)
-	} else if tmp2, ok2 := (*src).(float64); ok2 {
-		tmpe := int64(tmp2)
-		return formatDateWithInt64(&tmpe, layout)
-	} else if tmp3, ok3 := (*src).(*time.Time); ok3 {
-		return tmp3.Format(layout)
-	} else {
-		return ""
-	}
-}

File diff suppressed because it is too large
+ 0 - 0
common_utils/elastic/city.json


+ 0 - 357
common_utils/elastic/elasticSim.go

@@ -1,357 +0,0 @@
-package elastic
-
-import (
-	"encoding/json"
-	"fmt"
-	es "gopkg.in/olivere/elastic.v2"
-	"log"
-	"runtime"
-	"strings"
-	"sync"
-	"time"
-)
-
-type Elastic struct {
-	S_esurl      string
-	I_size       int
-	Addrs        []string
-	Pool         chan *es.Client
-	lastTime     int64
-	lastTimeLock sync.Mutex
-	ntimeout     int
-}
-
-func (e *Elastic) InitElasticSize() {
-	e.Pool = make(chan *es.Client, e.I_size)
-	for _, s := range strings.Split(e.S_esurl, ",") {
-		e.Addrs = append(e.Addrs, s)
-	}
-	for i := 0; i < e.I_size; i++ {
-		client, _ := es.NewClient(es.SetURL(e.Addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-		e.Pool <- client
-	}
-}
-
-//关闭连接
-func (e *Elastic) DestoryEsConn(client *es.Client) {
-	select {
-	case e.Pool <- client:
-		break
-	case <-time.After(time.Second * 1):
-		if client != nil {
-			client.Stop()
-		}
-		client = nil
-	}
-}
-
-func (e *Elastic) GetEsConn() *es.Client {
-	select {
-	case c := <-e.Pool:
-		if c == nil || !c.IsRunning() {
-			log.Println("new esclient.", len(e.Pool))
-			client, err := es.NewClient(es.SetURL(e.Addrs...),
-				es.SetMaxRetries(2), es.SetSniff(false))
-			if err == nil && client.IsRunning() {
-				return client
-			}
-		}
-		return c
-	case <-time.After(time.Second * 4):
-		//超时
-		e.ntimeout++
-		e.lastTimeLock.Lock()
-		defer e.lastTimeLock.Unlock()
-		//12秒后允许创建链接
-		c := time.Now().Unix() - e.lastTime
-		if c > 12 {
-			e.lastTime = time.Now().Unix()
-			log.Println("add client..", len(e.Pool))
-			c, _ := es.NewClient(es.SetURL(e.Addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-			go func() {
-				for i := 0; i < 2; i++ {
-					client, _ := es.NewClient(es.SetURL(e.Addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-					e.Pool <- client
-				}
-			}()
-			return c
-		}
-		return nil
-	}
-}
-
-func (e *Elastic) Get(index, itype, query string) *[]map[string]interface{} {
-	client := e.GetEsConn()
-	defer func() {
-		go e.DestoryEsConn(client)
-	}()
-	var res []map[string]interface{}
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			if resNum < 5000 {
-				res = make([]map[string]interface{}, resNum)
-				for i, hit := range searchResult.Hits.Hits {
-					parseErr := json.Unmarshal(*hit.Source, &res[i])
-					if parseErr == nil && hit.Highlight != nil && res[i] != nil {
-						res[i]["highlight"] = map[string][]string(hit.Highlight)
-					}
-				}
-			} else {
-				log.Println("查询结果太多,查询到:", resNum, "条")
-			}
-		}
-	}
-	return &res
-}
-
-//关闭elastic
-func (e *Elastic) Close() {
-	for i := 0; i < e.I_size; i++ {
-		cli := <-e.Pool
-		cli.Stop()
-		cli = nil
-	}
-	e.Pool = nil
-	e = nil
-}
-
-//获取连接
-//func (e *Elastic) GetEsConn() (c *es.Client) {
-//	defer util.Catch()
-//	select {
-//	case c = <-e.Pool:
-//		if c == nil || !c.IsRunning() {
-//			client, err := es.NewClient(es.SetURL(addrs...),
-//				es.SetMaxRetries(2), es.SetSniff(false))
-//			if err == nil && client.IsRunning() {
-//				return client
-//			}
-//			return nil
-//		}
-//		return
-//	case <-time.After(time.Second * 7):
-//		//超时
-//		ntimeout++
-//		log.Println("timeout times:", ntimeout)
-//		return nil
-//	}
-//}
-
-func (e *Elastic) BulkSave(index, itype string, obj *[]map[string]interface{}, isDelBefore bool) {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	if client != nil {
-		req := client.Bulk()
-		for _, v := range *obj {
-			if isDelBefore {
-				req = req.Add(es.NewBulkDeleteRequest().Index(index).Type(itype).Id(fmt.Sprintf("%v", v["_id"])))
-			}
-			req = req.Add(es.NewBulkIndexRequest().Index(index).Type(itype).Doc(v))
-		}
-		_, err := req.Do()
-		if err != nil {
-			log.Println("批量保存到ES出错", err.Error())
-		}
-	}
-}
-
-//根据id删除索引对象
-func (e *Elastic) DelById(index, itype, id string) bool {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	b := false
-	if client != nil {
-		var err error
-		_, err = client.Delete().Index(index).Type(itype).Id(id).Do()
-		if err != nil {
-			log.Println("更新检索出错:", err.Error())
-		} else {
-			b = true
-		}
-	}
-	return b
-}
-func (e *Elastic) GetNoLimit(index, itype, query string) *[]map[string]interface{} {
-	//log.Println("query  -- ", query)
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	var res []map[string]interface{}
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			res = make([]map[string]interface{}, resNum)
-			for i, hit := range searchResult.Hits.Hits {
-				json.Unmarshal(*hit.Source, &res[i])
-			}
-		}
-	}
-	return &res
-}
-func (e *Elastic) GetByIdField(index, itype, id, fields string) *map[string]interface{} {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		query := `{"query":{"term":{"_id":"` + id + `"}}`
-		if len(fields) > 0 {
-			query = query + `,"_source":[` + fields + `]`
-		}
-		query = query + "}"
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-		var res map[string]interface{}
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			if resNum == 1 {
-				res = make(map[string]interface{})
-				for _, hit := range searchResult.Hits.Hits {
-					json.Unmarshal(*hit.Source, &res)
-				}
-				return &res
-			}
-		}
-	}
-	return nil
-}
-
-func (e *Elastic) Count(index, itype string, query interface{}) int64 {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		var qq es.Query
-		if qi, ok2 := query.(es.Query); ok2 {
-			qq = qi
-		}
-		n, err := client.Count(index).Type(itype).Query(qq).Do()
-		if err != nil {
-			log.Println("统计出错", err.Error())
-		}
-
-		return n
-	}
-	return 0
-}
-
-//更新一个字段
-func (e *Elastic) BulkUpdateArr(index, itype string, update []map[string]string) {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		for _, data := range update {
-			id := data["id"]
-			updateStr := data["updateStr"]
-			if id != "" && updateStr != "" {
-				_, err := client.Update().Index(index).Type(itype).Id(id).Script(updateStr).ScriptLang("groovy").Do()
-				if err != nil {
-					log.Println("更新检索出错:", err.Error())
-				}
-			} else {
-				log.Println("数据错误")
-			}
-		}
-	}
-}
-
-//更新多个字段
-func (e *Elastic) BulkUpdateMultipleFields(index, itype string, arrs [][]map[string]interface{}) {
-	client := e.GetEsConn()
-	defer e.DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		for _, arr := range arrs {
-			id := arr[0]["id"].(string)
-			update := arr[1]["update"].([]string)
-			for _, str := range update {
-				_, err := client.Update().Index(index).Type(itype).Id(id).Script(str).ScriptLang("groovy").Do()
-				if err != nil {
-					log.Println("更新检索出错:", err.Error())
-				}
-			}
-		}
-	}
-}

+ 0 - 1169
common_utils/elastic/elasticutil.go

@@ -1,1169 +0,0 @@
-package elastic
-
-import (
-	"encoding/json"
-	"fmt"
-	es "gopkg.in/olivere/elastic.v2"
-	"log"
-	"net/url"
-	"reflect"
-	"runtime"
-	"strconv"
-	"strings"
-	"sync"
-	"time"
-)
-
-//检索库服务地址
-var addrs []string
-var LocCity = map[string]string{}
-var SIZE = 30
-
-const (
-	QStr = `{"query":{"bool":{"must":[$and],"must_not":[],
-	"should":[$or],"minimum_should_match" : 1}}}`
-)
-
-var pool chan *es.Client
-var ntimeout int
-
-var syncPool sync.Pool
-
-//自定义HttpClient
-/**
-var httpclient = &http.Client{Transport: &http.Transport{
-	Dial: func(netw, addr string) (net.Conn, error) {
-		deadline := time.Now().Add(5000 * time.Millisecond)
-		c, err := net.DialTimeout(netw, addr, 10000*time.Millisecond)
-		if err != nil {
-			return nil, err
-		}
-		tcp_conn := c.(*net.TCPConn)
-		tcp_conn.SetKeepAlive(false)
-		tcp_conn.SetDeadline(deadline)
-		return tcp_conn, nil
-	},
-	DisableKeepAlives: true, //不保持,这样才能释放
-}}
-**/
-//var op = es.SetHttpClient(httpclient)
-var poolsize = int32(20)
-
-//n倍的池
-func InitElasticSize(addr string, size int) {
-	poolsize = int32(3 * size)
-	pool = make(chan *es.Client, poolsize)
-	for _, s := range strings.Split(addr, ",") {
-		addrs = append(addrs, s)
-	}
-	for i := 0; i < size; i++ {
-		client, _ := es.NewClient(es.SetURL(addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-		pool <- client
-	}
-}
-
-//关闭连接
-func DestoryEsConn(client *es.Client) {
-	select {
-	case pool <- client:
-		break
-	case <-time.After(time.Second * 1):
-		if client != nil {
-			client.Stop()
-		}
-		client = nil
-	}
-}
-
-var (
-	lastTime     = int64(0)
-	lastTimeLock = &sync.Mutex{}
-)
-
-//获取连接
-
-func GetEsConn() *es.Client {
-	select {
-	case c := <-pool:
-		if c == nil || !c.IsRunning() {
-			log.Println("new esclient.", len(pool))
-			client, err := es.NewClient(es.SetURL(addrs...),
-				es.SetMaxRetries(2), es.SetSniff(false))
-			if err == nil && client.IsRunning() {
-				return client
-			}
-		}
-		return c
-	case <-time.After(time.Second * 4):
-		//超时
-		ntimeout++
-		lastTimeLock.Lock()
-		defer lastTimeLock.Unlock()
-		//12秒后允许创建链接
-		c := time.Now().Unix() - lastTime
-		if c > 12 {
-			lastTime = time.Now().Unix()
-			log.Println("add client..", len(pool))
-			c, _ := es.NewClient(es.SetURL(addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-			go func() {
-				for i := 0; i < 2; i++ {
-					client, _ := es.NewClient(es.SetURL(addrs...), es.SetMaxRetries(2), es.SetSniff(false))
-					pool <- client
-				}
-			}()
-			return c
-		}
-		return nil
-	}
-}
-
-//通用查询
-//{"query": {"bool":{"must":[{"query_string":{"default_field":"name","query":"*"}}]}}}
-//{"query":{"bool":{"must":{"match":{"content":{"query":"fulltextsearch","operator":"and"}}},"should":[{"match":{"content":{"query":"Elasticsearch","boost":3}}},{"match":{"content":{"query":"Lucene","boost":2}}}]}}}
-//prefix
-//{"query":{"match":{"title":{"query":"brownfox","operator":"and"}}}} //默认为or
-//{"query":{"multi_match":{"query":"PolandStreetW1V","type":"most_fields","fields":["*_street","city^2","country","postcode"]}}}
-//{"query":{"wildcard":{"postcode":"W?F*HW"}}}
-//{"query":{"regexp":{"postcode":"W[0-9].+"}}}
-//{"query":{"filtered":{"filter":{"range":{"price":{"gte":10000}}}}},"aggs":{"single_avg_price":{"avg":{"field":"price"}}}}
-//{"query":{"match":{"make":"ford"}},"aggs":{"colors":{"terms":{"field":"color"}}}}//查fork有几种颜色
-//过滤器不会计算相关度的得分,所以它们在计算上更快一些
-//{"query":{"filtered":{"query":{"match_all":{}},"filter":{"range":{"balance":{"gte":20000,"lte":30000}}}}}}
-//{"query":{"match_all":{}},"from":10,"size":10,"_source":["account_number","balance"],"sort":{"balance":{"order":"desc"}}}
-//{"query":{"match_phrase":{"address":"milllane"}}}和match不同会去匹配整个短语,相当于must[]
-func Get(index, itype, query string) *[]map[string]interface{} {
-	log.Println("query  -- ", query)
-	client := GetEsConn()
-	defer func() {
-		go DestoryEsConn(client)
-	}()
-	var res []map[string]interface{}
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			if resNum < 5000 {
-				res = make([]map[string]interface{}, resNum)
-				for i, hit := range searchResult.Hits.Hits {
-					//d := json.NewDecoder(bytes.NewBuffer(*hit.Source))
-					//d.UseNumber()
-					//d.Decode(&res[i])
-					parseErr := json.Unmarshal(*hit.Source, &res[i])
-					if parseErr == nil && hit.Highlight != nil && res[i] != nil {
-						res[i]["highlight"] = map[string][]string(hit.Highlight)
-					}
-				}
-			} else {
-				log.Println("查询结果太多,查询到:", resNum, "条")
-			}
-
-		}
-	}
-	return &res
-}
-func GetOA(index, itype, query string) (*[]map[string]interface{}, int) {
-	//log.Println("query  -- ", query)
-	client := GetEsConn()
-	defer func() {
-		go DestoryEsConn(client)
-	}()
-	var res []map[string]interface{}
-	var resNum int
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil, 0
-		}
-
-		if searchResult.Hits != nil {
-			resNum = len(searchResult.Hits.Hits)
-			if resNum < 5000 {
-				res = make([]map[string]interface{}, resNum)
-				for i, hit := range searchResult.Hits.Hits {
-					//d := json.NewDecoder(bytes.NewBuffer(*hit.Source))
-					//d.UseNumber()
-					//d.Decode(&res[i])
-					parseErr := json.Unmarshal(*hit.Source, &res[i])
-					if parseErr == nil && hit.Highlight != nil && res[i] != nil {
-						res[i]["highlight"] = map[string][]string(hit.Highlight)
-					}
-				}
-			} else {
-				log.Println("查询结果太多,查询到:", resNum, "条")
-			}
-
-		}
-	}
-	return &res, resNum
-}
-
-func GetNoLimit(index, itype, query string) *[]map[string]interface{} {
-	//log.Println("query  -- ", query)
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	var res []map[string]interface{}
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			res = make([]map[string]interface{}, resNum)
-			for i, hit := range searchResult.Hits.Hits {
-				json.Unmarshal(*hit.Source, &res[i])
-			}
-		}
-	}
-	return &res
-}
-
-//分页查询
-//{"name":"张三","$and":[{"age":{"$gt":10}},{"age":{"$lte":20}}]}
-//fields直接是 `"_id","title"`
-func GetPage(index, itype, query, order, field string, start, limit int) *[]map[string]interface{} {
-	return Get(index, itype, MakeQuery(query, order, field, start, limit))
-}
-
-//openapi
-func GetOAPage(index, itype, query, order, field string, start, limit int) (*[]map[string]interface{}, int) {
-	return GetOA(index, itype, MakeQuery(query, order, field, start, limit))
-}
-
-var SR = strings.Replace
-
-func MakeQuery(query, order, fileds string, start, limit int) string {
-	log.Println(query)
-	res := AnalyQuery(query, "", QStr)
-	log.Println(len(res), query)
-	if len(res) > 10 {
-		res = SR(SR(SR(SR(res, ",$and", "", -1), "$and", "", -1), ",$or", "", -1), "$or", "", -1)
-		log.Println("1", res)
-		if len(fileds) > 0 {
-			//"_source":["account_number","balance"]
-			res = res[:len(res)-1] + `,"_source":[` + fileds + "]}"
-		}
-		log.Println("2", res)
-		//{"name":-1,"age":1}
-		if len(order) > 0 {
-			res = res[:len(res)-1] + `,"sort":[` + SR(SR(SR(SR(order, ",", "},{", -1), " ", "", -1), ":-1", `:"desc"`, -1), ":1", `:"asc"`, -1) + `]}`
-		}
-		log.Println("3", res)
-		if start > -1 {
-			res = res[:len(res)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		log.Println("4", res)
-		return res
-	}
-	return ""
-}
-
-//{"name":"aaa"}
-func AnalyQuery(query interface{}, parent string, result string) string {
-	m := make(map[string]interface{})
-	if q1, ok := query.(string); ok {
-		json.Unmarshal([]byte(q1), &m)
-	} else if q2, ok2 := query.(map[string]interface{}); ok2 {
-		m = q2
-	}
-	if len(parent) == 0 {
-		for k, v := range m {
-			if k == "$and" || k == "$or" {
-				temps := ""
-				if map1, ok := v.([]interface{}); ok {
-					for i := 0; i < len(map1); i++ {
-						temps += "," + AnalyQuery(map1[i], k, "")
-					}
-				}
-				if len(temps) > 0 {
-					temps = temps[1:]
-				}
-				result = SR(result, k, temps+","+k, 1)
-			} else {
-				switch reflect.TypeOf(v).String() {
-				case "string":
-					if strings.Index(k, "TERM_") == 0 {
-						result = SR(result, "$and", `{"term":{"`+SR(k, "TERM_", "", 1)+`":"`+fmt.Sprintf("%v", v)+`"}},$and`, 1)
-					} else {
-						result = SR(result, "$and", `{"query_string":{"default_field":"`+k+`","query":"`+fmt.Sprintf("%v", v)+`"}},$and`, 1)
-					}
-				case "int", "int8", "int32", "int64", "float32", "float64":
-					if strings.Index(k, "TERM_") == 0 {
-						result = SR(result, "$and", `{"term":{"`+SR(k, "TERM_", "", 1)+`":`+fmt.Sprintf("%v", v)+`}},$and`, 1)
-					} else {
-						result = SR(result, "$and", `{"query_string":{"default_field":"`+k+`","query":`+fmt.Sprintf("%v", v)+`}},$and`, 1)
-					}
-				default:
-					result = SR(result, "$and", AnalyQuery(v, k, "")+",$and", 1)
-				}
-			}
-		}
-		return result
-	} else {
-		for k, v := range m {
-			if k == "$in" {
-				s := ""
-				if map1, ok := v.([]interface{}); ok {
-					for i := 0; i < len(map1); i++ {
-						s += "," + `"` + fmt.Sprintf("%v", map1[i]) + `"`
-					}
-				}
-				if len(s) > 0 {
-					s = s[1:]
-				}
-				return `{"terms":{"` + parent + `":[` + s + `]}}`
-			} else if strings.Contains(k, "$lt") || strings.Contains(k, "$gt") {
-				return `{"range":{"` + parent + `":{"` + SR(k, "$", "", 1) + `":` + fmt.Sprintf("%v", v) + `}}}`
-			} else {
-				switch reflect.TypeOf(v).String() {
-				case "string":
-					if strings.Index(k, "TERM_") == 0 {
-						return `{"term":{"` + SR(k, "TERM_", "", 1) + `":"` + fmt.Sprintf("%v", v) + `"}}`
-					} else {
-						return `{"query_string":{"default_field":"` + k + `","query":"` + fmt.Sprintf("%v", v) + `"}}`
-					}
-				case "int", "int8", "int32", "int64", "float32", "float64":
-					if strings.Index(k, "TERM_") == 0 {
-						return `{"term":{"` + SR(k, "TERM_", "", 1) + `":` + fmt.Sprintf("%v", v) + `}}`
-					} else {
-						return `{"query_string":{"default_field":"` + k + `","query":` + fmt.Sprintf("%v", v) + `}}`
-					}
-				default:
-					return AnalyQuery(v, k, result)
-				}
-			}
-		}
-	}
-	return result
-}
-func GetByIdField(index, itype, id, fields string) *map[string]interface{} {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		query := `{"query":{"term":{"_id":"` + id + `"}}`
-		if len(fields) > 0 {
-			query = query + `,"_source":[` + fields + `]`
-		}
-		query = query + "}"
-		searchResult, err := client.Search().Index(index).Type(itype).Source(query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-		var res map[string]interface{}
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			if resNum == 1 {
-				res = make(map[string]interface{})
-				for _, hit := range searchResult.Hits.Hits {
-					json.Unmarshal(*hit.Source, &res)
-				}
-				return &res
-			}
-		}
-	}
-	return nil
-}
-
-//根据id来查询文档
-func GetById(index, itype string, ids ...string) *[]map[string]interface{} {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	var res []map[string]interface{}
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		query := es.NewIdsQuery().Ids(ids...)
-		searchResult, err := client.Search().Index(index).Type(itype).Query(&query).Do()
-		if err != nil {
-			log.Println("从ES查询出错", err.Error())
-			return nil
-		}
-
-		if searchResult.Hits != nil {
-			resNum := len(searchResult.Hits.Hits)
-			if resNum < 5000 {
-				res = make([]map[string]interface{}, resNum)
-				for i, hit := range searchResult.Hits.Hits {
-					json.Unmarshal(*hit.Source, &res[i])
-				}
-			} else {
-				log.Println("查询结果太多,查询到:", resNum, "条")
-			}
-
-		}
-	}
-	return &res
-}
-
-//删除某个索引,根据查询
-func Del(index, itype string, query interface{}) bool {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	b := false
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		var err error
-		if qi, ok2 := query.(es.Query); ok2 {
-			_, err = client.DeleteByQuery().Index(index).Type(itype).Query(qi).Do()
-		}
-		if err != nil {
-			log.Println("删除索引出错:", err.Error())
-		} else {
-			b = true
-		}
-	}
-	return b
-}
-
-//根据语句更新对象
-func Update(index, itype, id string, updateStr string) bool {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	b := false
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		var err error
-		_, err = client.Update().Index(index).Type(itype).Id(id).Script(updateStr).ScriptLang("groovy").Do()
-		if err != nil {
-			log.Println("更新检索出错:", err.Error())
-		} else {
-			b = true
-		}
-	}
-	return b
-}
-
-func BulkUpdate(index, itype string, ids []string, updateStr string) {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		for _, id := range ids {
-			_, err := client.Update().Index(index).Type(itype).Id(id).Script(updateStr).ScriptLang("groovy").Do()
-			if err != nil {
-				log.Println("更新检索出错:", err.Error())
-			}
-		}
-	}
-}
-
-func BulkUpdateArr(index, itype string, update []map[string]string) {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		for _, data := range update {
-			id := data["id"]
-			updateStr := data["updateStr"]
-			if id != "" && updateStr != "" {
-				_, err := client.Update().Index(index).Type(itype).Id(id).Script(updateStr).ScriptLang("groovy").Do()
-				if err != nil {
-					log.Println("更新检索出错:", err.Error())
-				}
-			} else {
-				log.Println("数据错误")
-			}
-		}
-
-	}
-}
-
-//根据id删除索引对象
-func DelById(index, itype, id string) bool {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	b := false
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		var err error
-		_, err = client.Delete().Index(index).Type(itype).Id(id).Do()
-		if err != nil {
-			log.Println("更新检索出错:", err.Error())
-		} else {
-			b = true
-		}
-	}
-	return b
-}
-
-//把地市代码转为地市
-func getLoc(code string, res *map[string]string) (loc string) {
-	switch len(code) {
-	case 6:
-		loc = (*res)[code[:2]] + " " + (*res)[code[:4]] + " " + (*res)[code]
-		break
-	case 4:
-		loc = (*res)[code[:2]] + " " + (*res)[code]
-		break
-	case 2:
-		loc = (*res)[code]
-		break
-	}
-	return
-}
-
-//把地市代码转为地市
-func Loop(m interface{}, res *map[string]string) {
-	m1, ok := m.([]interface{})
-	if !ok {
-		m2, _ := m.([]map[string]interface{})
-		for i := 0; i < len(m2); i++ {
-			ms := m2[i]
-			(*res)[fmt.Sprintf("%1.0f", ms["k"])] = fmt.Sprintf("%s", ms["n"])
-			s := ms["s"]
-			if nil != s {
-				mss, _ := s.([]interface{})
-				if nil != mss {
-					Loop(mss, res)
-				}
-			}
-		}
-	} else {
-		for i := 0; i < len(m1); i++ {
-			ms, _ := m1[i].(map[string]interface{})
-			(*res)[fmt.Sprintf("%1.0f", ms["k"])] = fmt.Sprintf("%s", ms["n"])
-			s := ms["s"]
-			if nil != s {
-				mss, _ := s.([]interface{})
-				if nil != mss {
-					Loop(mss, res)
-				}
-			}
-		}
-	}
-}
-
-func ConverData(ent *map[string]interface{}) map[string]interface{} {
-	tmp := *ent
-	id64, _ := tmp["ID"].(int64)
-	ids := fmt.Sprintf("%d", id64)
-	tmp2 := make(map[string]interface{})
-	tmp2["ID"] = ids
-	tmp2["_id"] = tmp["_id"]
-	tmp2["Area"] = tmp["Area"]
-	tmp2["LeRep"] = tmp["LeRep"]
-	tmp2["RegNo"] = tmp["RegNo"]
-	tmp2["EntType"] = tmp["EntType"]
-	tmp2["EntName"] = tmp["EntName"]
-	tmp2["EntTypeName"] = tmp["EntTypeName"]
-	tmp2["Dom"] = tmp["Dom"]
-	tmp2["EstDate"] = tmp["EstDate"]
-	tmp2["OpStateName"] = tmp["OpStateName"]
-	tmp2["OpScope"] = tmp["OpScope"]
-	tmp2["OpState"] = tmp["OpState"]
-	tmp2["s_submitid"] = tmp["s_submitid"]
-	tmp2["l_submittime"] = tmp["l_submittime"]
-	tmp2["s_submitname"] = tmp["s_submitname"]
-	tmp2["RegCapCurName"] = tmp["RegCapCurName"]
-	//增加营业状态排序
-	if tmp2["OpState"] == "06" {
-		tmp2["OpSint"] = true
-	} else {
-		tmp2["OpSint"] = false
-	}
-	tmp2["OpLocDistrict"] = tmp["OpLocDistrict"]
-	//增加代码转名称
-	tmpLoc, _ := tmp["OpLocDistrict"].(string)
-	tmp2["OpLocDistrictName"] = getLoc(tmpLoc, &LocCity)
-
-	tmp2["RecCap"] = tmp["RecCap"]
-	tmp2["RegCap"] = tmp["RegCap"]
-	tmp2["IndustryPhy"] = tmp["IndustryPhy"]
-	tmp2["IndustryPhyName"] = tmp["IndustryPhyName"]
-	tmp2["RegOrg"] = tmp["RegOrg"]
-	tmp2["RegOrgName"] = tmp["RegOrgName"]
-	tmp2["Tel"] = tmp["Tel"]
-	tmp2["CompForm"] = tmp["CompForm"]
-	tmp2["CompFormName"] = tmp["CompFormName"]
-	//增加异常名录标记 Ycml可能是bool也可能是string
-	Ycmlb, _ := tmp["Ycml"].(bool)
-	Ycmls, _ := tmp["Ycml"].(string)
-	if Ycmlb || Ycmls == "1" {
-		tmp2["Ycml"] = true
-	} else {
-		tmp2["Ycml"] = false
-	}
-	//增加年报联系信息
-	if tmp["Nb_email"] != nil {
-		tmp2["Nb_email"] = tmp["Nb_email"]
-	}
-	if tmp["Nb_tel"] != nil {
-		tmp2["Nb_tel"] = tmp["Nb_tel"]
-	}
-	if tmp["Nb_addr"] != nil {
-		tmp2["Nb_addr"] = tmp["Nb_addr"]
-	}
-
-	s_synopsis := tmp["s_synopsis"]
-	if s_synopsis == nil {
-		s_synopsis = ""
-	}
-	tmp2["s_synopsis"] = s_synopsis //企业简介
-
-	//股东
-	stock := getStock(tmp["investor"])
-	tmp2["stock"] = stock
-
-	tmp2["LegCerNO"] = tmp["LegCerNO"]
-	if tmp["s_microwebsite"] != nil {
-		tmp2["s_microwebsite"] = tmp["s_microwebsite"]
-	}
-
-	tmp2["SourceType"] = tmp["SourceType"] //数据来源
-	s_servicenames := tmp["s_servicenames"]
-	if s_servicenames == nil {
-		s_servicenames = ""
-	}
-	tmp2["s_servicenames"] = s_servicenames //服务名称
-	s_action := tmp["s_action"]
-	if s_action == nil {
-		s_action = "N"
-	}
-	tmp2["s_action"] = s_action
-	tmp2["s_persion"] = tmp["s_persion"]
-	tmp2["s_mobile"] = tmp["s_mobile"]
-	tmp2["s_enturl"] = tmp["s_enturl"]
-	tmp2["s_weixin"] = tmp["s_weixin"]
-	tmp2["s_avatar"] = tmp["s_avatar"]
-	return tmp2
-}
-
-func getStock(obj interface{}) string {
-	stock := ""
-	if ns, ok := obj.([]interface{}); ok {
-		stock = " "
-		for _, ns1 := range ns {
-			if nn, ok1 := ns1.(map[string]interface{}); ok1 {
-				tmp := fmt.Sprintf("%s", nn["Inv"])
-				if strings.Index(stock, tmp) < 0 {
-					stock += tmp + " "
-				}
-			}
-		}
-	}
-	return stock
-}
-
-func BulkSave(index, itype string, obj *[]map[string]interface{}, isDelBefore bool) {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		req := client.Bulk()
-		for _, v := range *obj {
-			if isDelBefore {
-				req = req.Add(es.NewBulkDeleteRequest().Index(index).Type(itype).Id(fmt.Sprintf("%v", v["_id"])))
-			}
-			req = req.Add(es.NewBulkIndexRequest().Index(index).Type(itype).Doc(v))
-		}
-		_, err := req.Do()
-		if err != nil {
-			log.Println("批量保存到ES出错", err.Error())
-		}
-	}
-}
-
-func Count(index, itype string, query interface{}) int64 {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	if client != nil {
-		defer func() {
-			if r := recover(); r != nil {
-				log.Println("[E]", r)
-				for skip := 1; ; skip++ {
-					_, file, line, ok := runtime.Caller(skip)
-					if !ok {
-						break
-					}
-					go log.Printf("%v,%v\n", file, line)
-				}
-			}
-		}()
-		var qq es.Query
-		if qi, ok2 := query.(es.Query); ok2 {
-			qq = qi
-		}
-		n, err := client.Count(index).Type(itype).Query(qq).Do()
-		if err != nil {
-			log.Println("统计出错", err.Error())
-		}
-
-		return n
-	}
-	return 0
-}
-
-//ngram精确查询
-/*
-{
-  "query": {
-    "bool": {
-      "should": [
-        {
-	"bool":{
-	  "must":[
-	  {     "multi_match": {
-            "query": "智能",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-        },{
-          "multi_match": {
-            "query": "机器",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-        },{
-          "multi_match": {
-            "query": "2016",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-	  }
-	  ]
-	}
-        },
-
-{
-	"bool":{
-	  "must":[
-	  {          "multi_match": {
-            "query": "河南",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-        },{
-          "multi_match": {
-            "query": "工商",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-        },{
-          "multi_match": {
-            "query": "2016",
-            "type": "phrase",
-            "fields": [
-              "title"
-            ],
-           "analyzer": "my_ngram"
-          }
-	  }
-	  ]
-	}
-        }
-      ],"minimum_should_match": 1
-    }
-  },
-  "_source": [
-    "_id",
-    "title"
-  ],
-  "from": 0,
-  "size": 10,
-  "sort": [{
-      "publishtime": "desc"
-    }]
-}
-
-*/
-//"2016+智能+办公,"河南+工商"
-//["2016+智能+办公","河南+工商"]
-//QStr = `{"query":{"bool":{should":[$or],"minimum_should_match" : 1}}}`
-//{"bool":{"must":[]}}
-//{"multi_match": {"query": "$word","type": "phrase", "fields": [$field],"analyzer": "my_ngram"}}
-//"highlight": {"pre_tags": [""],"post_tags": [""],"fields": {"detail": {"fragment_size": 1,"number_of_fragments": 1},"title": {"fragment_size": 1,"number_of_fragments": 1}}}
-const (
-	//此处最后少一个},正好NgramStr取[1:]多一个}
-	FilterQuery     = `{"query": {"filtered": {"filter": {"bool": {"must": [%s]}},%s}}`
-	NgramStr        = `{"query":{"bool":{"must":[%s],"should":[%s],"minimum_should_match": 1}}}`
-	NgramMust       = `{"bool":{"must":[%s]}}`
-	NgramMustAndNot = `{"bool":{"must":[%s],"must_not":[%s]}}`
-	minq            = `{"multi_match": {"query": "%s","type": "phrase", "fields": [%s]}}`
-	HL              = `"highlight": {"pre_tags": [""],"post_tags": [""],"fields": {%s}}`
-	highlightStr    = `%s: {"fragment_size": %d,"number_of_fragments": 1}`
-
-	FilterQuery_New  = `{"query":{"bool":{"must": [%s%s%s],"should":[]}}}`
-	MatchQueryString = `{"match": {%s: { "query":"%s", "operator": "and"}}}`
-	HL_New           = `"highlight": {"pre_tags": ["<HL>"],"post_tags": ["<HL>"],"fields": {%s}}`
-
-	//数据查询高亮标记2019-07-10
-	HL_MP = `"highlight": {"pre_tags": ["<HL>"],"post_tags": ["</HL>"],"fields": {%s}}`
-
-	ik_highlightStr = `%s: {"fragment_size": %d,"number_of_fragments": 1,"require_field_match": true}`
-	IK_pre_tags     = `<font class=\"es-highlight\">`
-	IK_post_tags    = `</font>`
-	HL_IK           = `"highlight": {"pre_tags": ["` + IK_pre_tags + `"],"post_tags": ["` + IK_post_tags + `"],"fields": {%s}}`
-)
-
-type KeyConfig struct {
-	Keys      []string `json:"key"`
-	NotKeys   []string `json:"notkey"`
-	InfoTypes []string `json:"infotype"`
-	Areas     []string `json:"area"`
-}
-
-//替换了"号
-func GetResForJY(index, itype string, keys []KeyConfig, allquery, findfields, SortQuery, fields string, start, limit int) *[]map[string]interface{} {
-	if len(keys) > 0 {
-		qstr := ""
-		new_minq := fmt.Sprintf(minq, "%s", findfields)
-		not_new_minq := fmt.Sprintf(minq, "%s", findfields) //排除词只查询标题
-		musts := []string{}
-		for _, qs_words := range keys {
-			mq := []string{}
-			notmq := []string{}
-			for _, qs_word := range qs_words.Keys {
-				mq = append(mq, fmt.Sprintf(new_minq, ReplaceYH(qs_word)))
-				/*
-					qs := AnalyzerWord("bidding", qs_word)
-					for _, qw := range qs {
-						mq = append(mq, fmt.Sprintf(new_minq, ReplaceYH(qw)))
-					}
-				*/
-			}
-			for _, qs_word := range qs_words.NotKeys {
-				notmq = append(notmq, fmt.Sprintf(not_new_minq, ReplaceYH(qs_word)))
-			}
-			if len(qs_words.Areas) > 0 {
-				mq = append(mq, fmt.Sprintf(`{"terms":{"area":["%s"]}}`, strings.Join(qs_words.Areas, `","`)))
-			}
-			if len(qs_words.InfoTypes) > 0 {
-				mq = append(mq, fmt.Sprintf(`{"terms":{"toptype":["%s"]}}`, strings.Join(qs_words.InfoTypes, `","`)))
-			}
-			musts = append(musts, fmt.Sprintf(NgramMustAndNot, strings.Join(mq, ","), strings.Join(notmq, ",")))
-		}
-		qstr = fmt.Sprintf(NgramStr, "", strings.Join(musts, ","))
-
-		qstr = fmt.Sprintf(FilterQuery, allquery, qstr[1:])
-		ws := []string{}
-		for _, w := range strings.Split(findfields, ",") {
-			ws = append(ws, fmt.Sprintf(highlightStr, w, 1))
-		}
-		qstr = qstr[:len(qstr)-1] + `,` + fmt.Sprintf(HL, strings.Join(ws, ",")) + `}`
-		if len(fields) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"_source":[` + fields + "]}"
-		}
-		if len(SortQuery) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"sort":` + SortQuery + `}`
-		}
-		if start > -1 {
-			qstr = qstr[:len(qstr)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		//log.Println("jy-ngram-find", qstr)
-		return Get(index, itype, qstr)
-	} else {
-		return nil
-	}
-}
-
-func ReplaceYH(src string) (rpl string) {
-	return strings.Replace(src, `"`, `\"`, -1)
-}
-
-//
-func GetAllByNgram(index, itype, qstr, findfields, order, fields string, start, limit, count int, highlight bool) *[]map[string]interface{} {
-	if qstr != "" {
-		if highlight {
-			ws := []string{}
-			for _, w := range strings.Split(findfields, ",") {
-				ws = append(ws, fmt.Sprintf(highlightStr, w, count))
-			}
-			qstr = qstr[:len(qstr)-1] + `,` + fmt.Sprintf(HL, strings.Join(ws, ",")) + `}`
-		}
-		if len(fields) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"_source":[` + fields + "]}"
-		}
-		if len(order) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"sort":[` + SR(SR(SR(SR(order, ",", "},{", -1), " ", "", -1), ":-1", `:"desc"`, -1), ":1", `:"asc"`, -1) + `]}`
-		}
-		if start > -1 {
-			qstr = qstr[:len(qstr)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		log.Println("GetAllByNgram:", qstr)
-		return Get(index, itype, qstr)
-	} else {
-		return nil
-	}
-}
-
-//数据标记2019-07-10
-func GetAllByNgram_MP(index, itype, qstr, findfields, order, fields string, start, limit, count int, highlight bool) *[]map[string]interface{} {
-	if qstr != "" {
-		if highlight {
-			ws := []string{}
-			for _, w := range strings.Split(findfields, ",") {
-				ws = append(ws, fmt.Sprintf(highlightStr, w, count))
-			}
-			qstr = qstr[:len(qstr)-1] + `,` + fmt.Sprintf(HL_MP, strings.Join(ws, ",")) + `}`
-		}
-		if len(fields) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"_source":[` + fields + "]}"
-		}
-		if len(order) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"sort":[` + SR(SR(SR(SR(order, ",", "},{", -1), " ", "", -1), ":-1", `:"desc"`, -1), ":1", `:"asc"`, -1) + `]}`
-		}
-		if start > -1 {
-			qstr = qstr[:len(qstr)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		//		log.Println("GetAllByNgram:", qstr)
-		return Get(index, itype, qstr)
-	} else {
-		return nil
-	}
-}
-
-//ik 分词
-func GetAllByIk(index, itype, qstr, findfields, order, fields string, start, limit, count int, highlight bool) *[]map[string]interface{} {
-	if qstr != "" {
-		if highlight {
-			ws := []string{}
-			for _, w := range strings.Split(findfields, ",") {
-				ws = append(ws, fmt.Sprintf(ik_highlightStr, w, count))
-			}
-			qstr = qstr[:len(qstr)-1] + `,` + fmt.Sprintf(HL_IK, strings.Join(ws, ",")) + `}`
-		}
-		if len(fields) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"_source":[` + fields + "]}"
-		}
-		if len(order) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"sort":[` + SR(SR(SR(SR(order, ",", "},{", -1), " ", "", -1), ":-1", `:"desc"`, -1), ":1", `:"asc"`, -1) + `]}`
-		}
-		if start > -1 {
-			qstr = qstr[:len(qstr)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		//log.Println("GetAllByNgram:", qstr)
-		return Get(index, itype, qstr)
-	} else {
-		return nil
-	}
-}
-
-//分词
-func AnalyzerWord(index, word string) (result []string) {
-	client := GetEsConn()
-	defer DestoryEsConn(client)
-	result = []string{}
-	p := url.Values{}
-	p["text"] = []string{word}
-	p["analyzer"] = []string{"ik"}
-	by, err := client.PerformRequest("GET", "/"+index+"/_analyze", p, nil)
-	if err != nil {
-		log.Println("AnalyzerWord Error:", err)
-		return
-	}
-	b, err := by.Body.MarshalJSON()
-	if err != nil {
-		log.Println("AnalyzerWord MarshalJSON Error:", err)
-		return
-	}
-	var res map[string][]map[string]interface{}
-	err = json.Unmarshal(b, &res)
-	if err != nil {
-		log.Println("AnalyzerWord Unmarshal Error:", err)
-		return
-	}
-	if res == nil {
-		return
-	}
-	for _, v := range res["tokens"] {
-		token, _ := v["token"].(string)
-		if token != "" {
-			result = append(result, token)
-		}
-	}
-	return
-}
-
-func GetResForJYView(index, itype string, keys []KeyConfig, allquery, findfields, SortQuery, fields string, start, limit int) *[]map[string]interface{} {
-	if len(keys) > 0 {
-		qstr := ""
-		new_minq := fmt.Sprintf(minq, "%s", findfields)
-		not_new_minq := fmt.Sprintf(minq, "%s", findfields) //排除词只查询标题
-		musts := []string{}
-		for _, qs_words := range keys {
-			mq := []string{}
-			notmq := []string{}
-			for _, qs_word := range qs_words.Keys {
-				mq = append(mq, fmt.Sprintf(new_minq, ReplaceYH(qs_word)))
-			}
-			for _, qs_word := range qs_words.NotKeys {
-				notmq = append(notmq, fmt.Sprintf(not_new_minq, ReplaceYH(qs_word)))
-			}
-			if len(qs_words.Areas) > 0 {
-				mq = append(mq, fmt.Sprintf(`{"terms":{"area":["%s"]}}`, strings.Join(qs_words.Areas, `","`)))
-			}
-			if len(qs_words.InfoTypes) > 0 {
-				mq = append(mq, fmt.Sprintf(`{"terms":{"toptype":["%s"]}}`, strings.Join(qs_words.InfoTypes, `","`)))
-			}
-			musts = append(musts, fmt.Sprintf(NgramMustAndNot, strings.Join(mq, ","), strings.Join(notmq, ",")))
-		}
-		qstr = fmt.Sprintf(NgramStr, "", strings.Join(musts, ","))
-
-		qstr = fmt.Sprintf(FilterQuery, allquery, qstr[1:])
-		ws := []string{}
-		for _, w := range strings.Split(findfields, ",") {
-			ws = append(ws, fmt.Sprintf(highlightStr, w, 1))
-		}
-		qstr = qstr[:len(qstr)-1] + `,` + fmt.Sprintf(HL, strings.Join(ws, ",")) + `}`
-		if len(fields) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"_source":[` + fields + "]}"
-		}
-		if len(SortQuery) > 0 {
-			qstr = qstr[:len(qstr)-1] + `,"sort":` + SortQuery + `}`
-		}
-		if start > -1 {
-			qstr = qstr[:len(qstr)-1] + `,"from":` + strconv.Itoa(start) + `,"size":` + strconv.Itoa(limit) + "}"
-		}
-		return Get(index, itype, qstr)
-	} else {
-		return nil
-	}
-}

+ 0 - 60
common_utils/encryptarticle.go

@@ -1,60 +0,0 @@
-package util
-
-import (
-	"net/url"
-	"strings"
-)
-
-//正文
-var SE = &SimpleEncrypt{Key: "topnet2015topnet2015"}
-var SE2 = &SimpleEncrypt{Key: "2017jianyu"}
-
-//百度
-var BSE = &SimpleEncrypt{Key: "HNtopnet2017jy"}
-var BSE2 = &SimpleEncrypt{Key: "TOP2017jianyu"}
-
-//订阅推送邮件
-var ESE = &SimpleEncrypt{Key: "PEjy2018topnet"}
-var ESE2 = &SimpleEncrypt{Key: "TopnetJy2018Pe"}
-
-//通用加密
-func CommonEncodeArticle(stype string, keys ...string) (id string) {
-	switch stype {
-	case "content":
-		id = BEncodeArticleId2ByCheck("A", SE, SE2, keys...)
-	case "bdprivate":
-		id = BEncodeArticleId2ByCheck("B", BSE, BSE2, keys...)
-	case "mailprivate":
-		id = BEncodeArticleId2ByCheck("C", ESE, ESE2, keys...)
-	}
-	return
-}
-
-//通用解密
-func CommonDecodeArticle(stype string, id string) (res []string) {
-	switch stype {
-	case "content":
-		res = BDecodeArticleId2ByCheck(id, SE, SE2)
-	case "bdprivate":
-		res = BDecodeArticleId2ByCheck(id, BSE, BSE2)
-	case "mailprivate":
-		res = BDecodeArticleId2ByCheck(id, ESE, ESE2)
-	}
-	return
-}
-
-//短地址加密,二次加密带校验和
-func BEncodeArticleId2ByCheck(h string, s1, s2 *SimpleEncrypt, keys ...string) string {
-	kstr := strings.Join(keys, ",")
-	kstr = s1.EncodeStringByCheck(kstr)
-	return url.QueryEscape(h + GetLetterRandom(2) + s2.EncodeStringByCheck(kstr))
-}
-
-//短地址解密,二次解密带校验和
-func BDecodeArticleId2ByCheck(id string, s1, s2 *SimpleEncrypt) []string {
-	if !strings.Contains(id, "+") { //新加密算法解密
-		id, _ = url.QueryUnescape(id)
-	}
-	kstr := s2.DecodeStringByCheck(id[3:])
-	return strings.Split(s1.DecodeStringByCheck(kstr), ",")
-}

+ 0 - 17
common_utils/go.mod

@@ -1,17 +0,0 @@
-module common_utils
-
-go 1.14
-
-require (
-	github.com/PuerkitoBio/goquery v1.8.0
-	github.com/dchest/captcha v0.0.0-20200903113550-03f5f0333e1f
-	github.com/fortytw2/leaktest v1.3.0 // indirect
-	github.com/go-sql-driver/mysql v1.5.0
-	github.com/gomodule/redigo v1.8.2
-	github.com/natefinch/lumberjack v2.0.0+incompatible
-	go.mongodb.org/mongo-driver v1.4.1
-	go.uber.org/zap v1.21.0
-	gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22
-	gopkg.in/natefinch/lumberjack.v2 v2.0.0 // indirect
-	gopkg.in/olivere/elastic.v2 v2.0.61
-)

+ 0 - 180
common_utils/go.sum

@@ -1,180 +0,0 @@
-github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
-github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
-github.com/PuerkitoBio/goquery v1.8.0 h1:PJTF7AmFCFKk1N6V6jmKfrNH9tV5pNE6lZMkG0gta/U=
-github.com/PuerkitoBio/goquery v1.8.0/go.mod h1:ypIiRMtY7COPGk+I/YbZLbxsxn9g5ejnI2HSMtkjZvI=
-github.com/andybalholm/cascadia v1.3.1 h1:nhxRkql1kdYCc8Snf7D5/D3spOX+dBgjA6u8x004T2c=
-github.com/andybalholm/cascadia v1.3.1/go.mod h1:R4bJ1UQfqADjvDa4P6HZHLh/3OxWWEqc0Sk8XGwHqvA=
-github.com/aws/aws-sdk-go v1.29.15 h1:0ms/213murpsujhsnxnNKNeVouW60aJqSd992Ks3mxs=
-github.com/aws/aws-sdk-go v1.29.15/go.mod h1:1KvfttTE3SPKMpo8g2c6jL3ZKfXtFvKscTgahTma5Xg=
-github.com/benbjohnson/clock v1.1.0 h1:Q92kusRqC1XV2MjkWETPvjJVqKetz1OzxZB7mHJLju8=
-github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
-github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
-github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
-github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
-github.com/dchest/captcha v0.0.0-20200903113550-03f5f0333e1f h1:q/DpyjJjZs94bziQ7YkBmIlpqbVP7yw179rnzoNVX1M=
-github.com/dchest/captcha v0.0.0-20200903113550-03f5f0333e1f/go.mod h1:QGrK8vMWWHQYQ3QU9bw9Y9OPNfxccGzfb41qjvVeXtY=
-github.com/fortytw2/leaktest v1.3.0 h1:u8491cBMTQ8ft8aeV+adlcytMZylmA5nnwwkRZjI8vw=
-github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g=
-github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs=
-github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
-github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk=
-github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
-github.com/gobuffalo/attrs v0.0.0-20190224210810-a9411de4debd/go.mod h1:4duuawTqi2wkkpB4ePgWMaai6/Kc6WEz83bhFwpHzj0=
-github.com/gobuffalo/depgen v0.0.0-20190329151759-d478694a28d3/go.mod h1:3STtPUQYuzV0gBVOY3vy6CfMm/ljR4pABfrTeHNLHUY=
-github.com/gobuffalo/depgen v0.1.0/go.mod h1:+ifsuy7fhi15RWncXQQKjWS9JPkdah5sZvtHc2RXGlg=
-github.com/gobuffalo/envy v1.6.15/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI=
-github.com/gobuffalo/envy v1.7.0/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI=
-github.com/gobuffalo/flect v0.1.0/go.mod h1:d2ehjJqGOH/Kjqcoz+F7jHTBbmDb38yXA598Hb50EGs=
-github.com/gobuffalo/flect v0.1.1/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI=
-github.com/gobuffalo/flect v0.1.3/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI=
-github.com/gobuffalo/genny v0.0.0-20190329151137-27723ad26ef9/go.mod h1:rWs4Z12d1Zbf19rlsn0nurr75KqhYp52EAGGxTbBhNk=
-github.com/gobuffalo/genny v0.0.0-20190403191548-3ca520ef0d9e/go.mod h1:80lIj3kVJWwOrXWWMRzzdhW3DsrdjILVil/SFKBzF28=
-github.com/gobuffalo/genny v0.1.0/go.mod h1:XidbUqzak3lHdS//TPu2OgiFB+51Ur5f7CSnXZ/JDvo=
-github.com/gobuffalo/genny v0.1.1/go.mod h1:5TExbEyY48pfunL4QSXxlDOmdsD44RRq4mVZ0Ex28Xk=
-github.com/gobuffalo/gitgen v0.0.0-20190315122116-cc086187d211/go.mod h1:vEHJk/E9DmhejeLeNt7UVvlSGv3ziL+djtTr3yyzcOw=
-github.com/gobuffalo/gogen v0.0.0-20190315121717-8f38393713f5/go.mod h1:V9QVDIxsgKNZs6L2IYiGR8datgMhB577vzTDqypH360=
-github.com/gobuffalo/gogen v0.1.0/go.mod h1:8NTelM5qd8RZ15VjQTFkAW6qOMx5wBbW4dSCS3BY8gg=
-github.com/gobuffalo/gogen v0.1.1/go.mod h1:y8iBtmHmGc4qa3urIyo1shvOD8JftTtfcKi+71xfDNE=
-github.com/gobuffalo/logger v0.0.0-20190315122211-86e12af44bc2/go.mod h1:QdxcLw541hSGtBnhUc4gaNIXRjiDppFGaDqzbrBd3v8=
-github.com/gobuffalo/mapi v1.0.1/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc=
-github.com/gobuffalo/mapi v1.0.2/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc=
-github.com/gobuffalo/packd v0.0.0-20190315124812-a385830c7fc0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4=
-github.com/gobuffalo/packd v0.1.0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4=
-github.com/gobuffalo/packr/v2 v2.0.9/go.mod h1:emmyGweYTm6Kdper+iywB6YK5YzuKchGtJQZ0Odn4pQ=
-github.com/gobuffalo/packr/v2 v2.2.0/go.mod h1:CaAwI0GPIAv+5wKLtv8Afwl+Cm78K/I/VCm/3ptBN+0=
-github.com/gobuffalo/syncx v0.0.0-20190224160051-33c29581e754/go.mod h1:HhnNqWY95UYwwW3uSASeV7vtgYkT2t16hJgV3AEPUpw=
-github.com/golang/snappy v0.0.1 h1:Qgr9rKW7uDUkrbSmQeiDsGa8SjGyCOGtuasMWwvp2P4=
-github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
-github.com/gomodule/redigo v1.8.2 h1:H5XSIre1MB5NbPYFp+i1NBbb5qN1W8Y8YAQoAYbkm8k=
-github.com/gomodule/redigo v1.8.2/go.mod h1:P9dn9mFrCBvWhGE1wpxx6fgq7BAeLBk+UUUzlpkBYO0=
-github.com/google/go-cmp v0.2.0 h1:+dTQ8DZQJz0Mb/HjFlkptS1FeQ4cWSnN941F8aEG4SQ=
-github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
-github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
-github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af h1:pmfjZENx5imkbgOkpRUYLnmbU7UEFbjtDA2hxJ1ichM=
-github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k=
-github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg=
-github.com/karrick/godirwalk v1.8.0/go.mod h1:H5KPZjojv4lE+QYImBI8xVtrBRgYrIVsaRPx4tDPEn4=
-github.com/karrick/godirwalk v1.10.3/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA=
-github.com/klauspost/compress v1.9.5 h1:U+CaK85mrNNb4k8BNOfgJtJ/gr6kswUCFj6miSzVC6M=
-github.com/klauspost/compress v1.9.5/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A=
-github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
-github.com/konsorten/go-windows-terminal-sequences v1.0.2/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
-github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
-github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
-github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
-github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
-github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
-github.com/markbates/oncer v0.0.0-20181203154359-bf2de49a0be2/go.mod h1:Ld9puTsIW75CHf65OeIOkyKbteujpZVXDpWK6YGZbxE=
-github.com/markbates/safe v1.0.1/go.mod h1:nAqgmRi7cY2nqMc92/bSEeQA+R4OheNU2T1kNSCBdG0=
-github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
-github.com/natefinch/lumberjack v2.0.0+incompatible h1:4QJd3OLAMgj7ph+yZTuX13Ld4UpgHp07nNdFX7mqFfM=
-github.com/natefinch/lumberjack v2.0.0+incompatible/go.mod h1:Wi9p2TTF5DG5oU+6YfsmYQpsTIOm0B1VNzQg9Mw6nPk=
-github.com/pelletier/go-toml v1.4.0/go.mod h1:PN7xzY2wHTK0K9p34ErDQMlFxa51Fk0OUruD3k1mMwo=
-github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
-github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
-github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
-github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
-github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
-github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
-github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/sirupsen/logrus v1.4.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo=
-github.com/sirupsen/logrus v1.4.1/go.mod h1:ni0Sbl8bgC9z8RoU9G6nDWqqs/fq4eDPysMBDgk/93Q=
-github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE=
-github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ=
-github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
-github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
-github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
-github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
-github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
-github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
-github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
-github.com/tidwall/pretty v1.0.0 h1:HsD+QiTn7sK6flMKIvNmpqz1qrpP3Ps6jOKIKMooyg4=
-github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
-github.com/xdg/scram v0.0.0-20180814205039-7eeb5667e42c h1:u40Z8hqBAAQyv+vATcGgV0YCnDjqSL7/q/JyPhhJSPk=
-github.com/xdg/scram v0.0.0-20180814205039-7eeb5667e42c/go.mod h1:lB8K/P019DLNhemzwFU4jHLhdvlE6uDZjXFejJXr49I=
-github.com/xdg/stringprep v0.0.0-20180714160509-73f8eece6fdc h1:n+nNi93yXLkJvKwXNP9d55HC7lGK4H/SRcwB5IaUZLo=
-github.com/xdg/stringprep v0.0.0-20180714160509-73f8eece6fdc/go.mod h1:Jhud4/sHMO4oL310DaZAKk9ZaJ08SJfe+sJh0HrGL1Y=
-github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
-go.mongodb.org/mongo-driver v1.4.1 h1:38NSAyDPagwnFpUA/D5SFgbugUYR3NzYRNa4Qk9UxKs=
-go.mongodb.org/mongo-driver v1.4.1/go.mod h1:llVBH2pkj9HywK0Dtdt6lDikOjFLbceHVu/Rc0iMKLs=
-go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw=
-go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
-go.uber.org/goleak v1.1.11 h1:wy28qYRKZgnJTxGxvye5/wgWr1EKjmUDGYox5mGlRlI=
-go.uber.org/goleak v1.1.11/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ=
-go.uber.org/multierr v1.6.0 h1:y6IPFStTAIT5Ytl7/XYmHvzXQ7S3g/IeZW9hyZ5thw4=
-go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU=
-go.uber.org/zap v1.21.0 h1:WefMeulhovoZ2sYXz7st6K0sLj7bBhpiFaud4r4zST8=
-go.uber.org/zap v1.21.0/go.mod h1:wjWOCqI0f2ZZrJF/UufIOkiC8ii6tm1iqIsLo76RfJw=
-golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
-golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
-golang.org/x/crypto v0.0.0-20190422162423-af44ce270edf/go.mod h1:WFFai1msRO1wXaEeE5yQxYXgSfI8pQAWXbQop6sCtWE=
-golang.org/x/crypto v0.0.0-20190530122614-20be4c3c3ed5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
-golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550 h1:ObdrDkeb4kJdCP557AjRjq69pTHfNouLtWZG7j9rPN8=
-golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
-golang.org/x/lint v0.0.0-20190930215403-16217165b5de h1:5hukYrvBGR8/eNkX5mdUezrA6JiaEZDtJb9Ei+1LlBs=
-golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
-golang.org/x/mod v0.4.2 h1:Gz96sIWK3OalVv/I/qNygP42zyoKp3xptRVCWRFEBvo=
-golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
-golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
-golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
-golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
-golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
-golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
-golang.org/x/net v0.0.0-20210916014120-12bc252f5db8 h1:/6y1LfuqNuQdHAm0jjtPtgRcxIxjVZgm5OTu8/QhZvk=
-golang.org/x/net v0.0.0-20210916014120-12bc252f5db8/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
-golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20190412183630-56d357773e84/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20210220032951-036812b2e83c h1:5KslGYwFpkhGh+Q16bwMP3cOontH8FOep7tGV86Y7SQ=
-golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20190403152447-81d4e9dc473e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190419153524-e8e3143a4f4a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190531175056-4c3a928424d2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210510120138-977fb7262007 h1:gG67DSER+11cZvqIMb8S8bt0vZtiN6xWYARwirrOSfE=
-golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
-golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
-golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
-golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M=
-golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
-golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
-golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190329151228-23e29df326fe/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190416151739-9c9e1878f421/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190420181800-aa740d480789/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190531172133-b3315ee88b7d/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
-golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
-golang.org/x/tools v0.1.5 h1:ouewzE6p+/VEB31YYnTbEJdi8pFqKp4P4n85vwo3DHA=
-golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
-golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
-golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
-golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
-golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
-gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
-gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
-gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
-gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI=
-gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22 h1:VpOs+IwYnYBaFnrNAeB8UUWtL3vEUnzSCL1nVjPhqrw=
-gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22/go.mod h1:yeKp02qBN3iKW1OzL3MGk2IdtZzaj7SFntXj72NppTA=
-gopkg.in/natefinch/lumberjack.v2 v2.0.0 h1:1Lc07Kr7qY4U2YPouBjpCLxpiyxIVoxqXgkXLknAOE8=
-gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24xpD6X8LsfU/+k=
-gopkg.in/olivere/elastic.v2 v2.0.61 h1:7cpl3MW8ysa4GYFBXklpo5mspe4NK0rpZTdyZ+QcD4U=
-gopkg.in/olivere/elastic.v2 v2.0.61/go.mod h1:CTVyl1gckiFw1aLZYxC00g3f9jnHmhoOKcWF7W3c6n4=
-gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
-gopkg.in/yaml.v2 v2.2.8 h1:obN1ZagJSUGI0Ek/LBmuj4SNLPfIny3KsKFopxRdj10=
-gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
-gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
-gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo=
-gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

+ 0 - 230
common_utils/log/log.go

@@ -1,230 +0,0 @@
-package log
-
-import (
-	"io"
-	"os"
-
-	"go.uber.org/zap"
-	"go.uber.org/zap/zapcore"
-	"gopkg.in/natefinch/lumberjack.v2"
-)
-
-var (
-	_logger *zap.Logger
-)
-
-const (
-	// FormatText format log text
-	FormatText = "text"
-	// FormatJSON format log json
-	FormatJSON = "json"
-)
-
-// type Level uint
-
-// 日志配置
-type logConfig struct {
-	LogPath    string
-	LogLevel   string
-	Compress   bool
-	MaxSize    int
-	MaxAge     int
-	MaxBackups int
-	Format     string
-}
-
-func getzapLevel(level string) zapcore.Level {
-	switch level {
-	case "debug":
-		return zap.DebugLevel
-	case "info":
-		return zap.InfoLevel
-	case "warn":
-		return zap.WarnLevel
-	case "error":
-		return zap.ErrorLevel
-	case "panic":
-		return zap.PanicLevel
-	case "fatal":
-		return zap.FatalLevel
-	default:
-		return zap.InfoLevel
-	}
-}
-
-func newLogWriter(logpath string, maxsize int, compress bool) io.Writer {
-	if logpath == "" || logpath == "-" {
-		return os.Stdout
-	}
-	return &lumberjack.Logger{
-		Filename: logpath,
-		MaxSize:  maxsize,
-		Compress: compress,
-	}
-}
-
-func newZapEncoder() zapcore.EncoderConfig {
-	encoderConfig := zapcore.EncoderConfig{
-		TimeKey:        "time",
-		LevelKey:       "level",
-		NameKey:        "logger",
-		CallerKey:      "line",
-		MessageKey:     "msg",
-		StacktraceKey:  "stacktrace",
-		LineEnding:     zapcore.DefaultLineEnding,
-		EncodeLevel:    zapcore.LowercaseLevelEncoder,  // 小写编码器
-		EncodeTime:     zapcore.ISO8601TimeEncoder,     // ISO8601 UTC 时间格式
-		EncodeDuration: zapcore.SecondsDurationEncoder, //
-		EncodeCaller:   zapcore.ShortCallerEncoder,     // 全路径编码器
-		EncodeName:     zapcore.FullNameEncoder,
-	}
-	return encoderConfig
-}
-func newLoggerCore(log *logConfig) zapcore.Core {
-	hook := newLogWriter(log.LogPath, log.MaxSize, log.Compress)
-
-	encoderConfig := newZapEncoder()
-
-	atomLevel := zap.NewAtomicLevelAt(getzapLevel(log.LogLevel))
-
-	var encoder zapcore.Encoder
-	if log.Format == FormatJSON {
-		encoder = zapcore.NewJSONEncoder(encoderConfig)
-	} else {
-		encoder = zapcore.NewConsoleEncoder(encoderConfig)
-	}
-
-	core := zapcore.NewCore(
-		encoder,
-		zapcore.NewMultiWriteSyncer(zapcore.AddSync(hook)),
-		atomLevel,
-	)
-	return core
-}
-
-func newLoggerOptions() []zap.Option {
-	// 开启开发模式,堆栈跟踪
-	caller := zap.AddCaller()
-	callerskip := zap.AddCallerSkip(1)
-	// 开发者
-	development := zap.Development()
-	options := []zap.Option{
-		caller,
-		callerskip,
-		development,
-	}
-	return options
-}
-
-// Option function option
-type Option func(*logConfig)
-
-// Path set logpath
-// if is zero will print,or write file
-func Path(logpath string) Option {
-	return func(logcfg *logConfig) {
-		logcfg.LogPath = logpath
-	}
-}
-
-// Compress compress log
-func Compress(compress bool) Option {
-	return func(logcfg *logConfig) {
-		logcfg.Compress = compress
-	}
-}
-
-// Level set log level default info
-func Level(level string) Option {
-	return func(logcfg *logConfig) {
-		logcfg.LogLevel = level
-	}
-}
-
-// MaxSize Log Max Size
-func MaxSize(size int) Option {
-	return func(logcfg *logConfig) {
-		logcfg.MaxSize = size
-	}
-}
-
-// MaxAge log store day
-func MaxAge(age int) Option {
-	return func(logcfg *logConfig) {
-		logcfg.MaxAge = age
-	}
-}
-
-// MaxBackups total store log
-func MaxBackups(backup int) Option {
-	return func(logcfg *logConfig) {
-		logcfg.MaxBackups = backup
-	}
-}
-
-// Format log json or text
-func Format(format string) Option {
-	return func(logcfg *logConfig) {
-		if format == FormatJSON {
-			logcfg.Format = FormatJSON
-		} else {
-			logcfg.Format = FormatText
-		}
-
-	}
-}
-
-func defaultOption() *logConfig {
-	return &logConfig{
-		LogPath:    "",
-		MaxSize:    20,
-		Compress:   true,
-		MaxAge:     7,
-		MaxBackups: 7,
-		LogLevel:   "debug",
-		Format:     FormatText,
-	}
-}
-
-// InitLog conf
-func InitLog(opts ...Option) error {
-	logcfg := defaultOption()
-	for _, opt := range opts {
-		opt(logcfg)
-	}
-	core := newLoggerCore(logcfg)
-
-	zapopts := newLoggerOptions()
-	_logger = zap.New(core, zapopts...)
-	return nil
-}
-
-// Debug output log
-func Debug(msg string, fields ...zap.Field) {
-	_logger.Debug(msg, fields...)
-}
-
-// Info output log
-func Info(msg string, fields ...zap.Field) {
-	_logger.Info(msg, fields...)
-}
-
-// Warn output log
-func Warn(msg string, fields ...zap.Field) {
-	_logger.Warn(msg, fields...)
-}
-
-// Error output log
-func Error(msg string, fields ...zap.Field) {
-	_logger.Error(msg, fields...)
-}
-
-// Panic output panic
-func Panic(msg string, fields ...zap.Field) {
-	_logger.Panic(msg, fields...)
-}
-
-// Fatal output log
-func Fatal(msg string, fields ...zap.Field) {
-	_logger.Fatal(msg, fields...)
-}

+ 0 - 53
common_utils/log/log_test.go

@@ -1,53 +0,0 @@
-package log
-
-import (
-	"errors"
-	"fmt"
-	"go.uber.org/zap"
-	"runtime/debug"
-
-	"io"
-	"os"
-	"testing"
-)
-
-func TestNewLogger(t *testing.T) {
-	logcfg := &logConfig{
-		MaxSize:    10,
-		Compress:   true,
-		LogPath:    "",
-		MaxAge:     0,
-		MaxBackups: 0,
-		LogLevel:   "info",
-	}
-	err := InitLog(
-		Path(logcfg.LogPath),
-		Level(logcfg.LogLevel),
-		Compress(logcfg.Compress),
-		MaxSize(logcfg.MaxSize),
-		MaxBackups(logcfg.MaxBackups),
-		MaxAge(logcfg.MaxAge),
-		Format("json"),
-	)
-	if err != nil {
-		fmt.Printf("InitLog failed: %v", err)
-		os.Exit(1)
-	}
-	defer func() {
-		if err := recover(); err != nil {
-			debug.PrintStack()
-		}
-	}()
-	Info("TestLog", zap.String("test", "eeyeyyeye"))
-	Debug("debug", zap.String("debug", "debug"))
-	Warn("warn", zap.String("warn", "warn"))
-	Error("error", zap.String("error", "error"))
-	Panic("panic", zap.String("panic", "panic"))
-	Fatal("fatal", zap.String("fatal", "fatal"))
-
-	err = io.EOF
-
-	err1 := fmt.Errorf("this is err: %w",err)
-	Info("111",zap.Error(err1))
-	fmt.Println(errors.Unwrap(err1),err1)
-}

+ 0 - 318
common_utils/logger.go

@@ -1,318 +0,0 @@
-package util
-
-import (
-	"fmt"
-	"log"
-	"os"
-	"runtime"
-	"strconv"
-	"sync"
-	"time"
-)
-
-const (
-	_VER string = "1.0.2"
-)
-
-type LEVEL int32
-
-var logLevel LEVEL = 1
-var maxFileSize int64
-var maxFileCount int32
-var dailyRolling bool = true
-var consoleAppender bool = true
-var RollingFile bool = false
-var logObj *_FILE
-
-const DATEFORMAT = "2006-01-02"
-
-type UNIT int64
-
-const (
-	_       = iota
-	KB UNIT = 1 << (iota * 10)
-	MB
-	GB
-	TB
-)
-
-const (
-	ALL LEVEL = iota
-	DEBUG
-	INFO
-	WARN
-	ERROR
-	FATAL
-	OFF
-)
-
-type _FILE struct {
-	dir      string
-	filename string
-	_suffix  int
-	isCover  bool
-	_date    *time.Time
-	mu       *sync.RWMutex
-	logfile  *os.File
-	lg       *log.Logger
-}
-
-func SetConsole(isConsole bool) {
-	consoleAppender = isConsole
-}
-
-func SetLevel(_level LEVEL) {
-	logLevel = _level
-}
-
-func SetRollingFile(fileDir, fileName string, maxNumber int32, maxSize int64, _unit UNIT) {
-	maxFileCount = maxNumber
-	maxFileSize = maxSize * int64(_unit)
-	RollingFile = true
-	dailyRolling = false
-	mkdirlog(fileDir)
-	logObj = &_FILE{dir: fileDir, filename: fileName, isCover: false, mu: new(sync.RWMutex)}
-	logObj.mu.Lock()
-	defer logObj.mu.Unlock()
-	for i := 1; i <= int(maxNumber); i++ {
-		if isExist(fileDir + "/" + fileName + "." + strconv.Itoa(i)) {
-			logObj._suffix = i
-		} else {
-			break
-		}
-	}
-	if !logObj.isMustRename() {
-		logObj.logfile, _ = os.OpenFile(fileDir+"/"+fileName, os.O_RDWR|os.O_APPEND|os.O_CREATE, 0666)
-		logObj.lg = log.New(logObj.logfile, "", log.Ldate|log.Ltime|log.Lshortfile)
-	} else {
-		logObj.rename()
-	}
-	go fileMonitor()
-}
-
-func SetRollingDaily(fileDir, fileName string) {
-	RollingFile = false
-	dailyRolling = true
-	t, _ := time.Parse(DATEFORMAT, time.Now().Format(DATEFORMAT))
-	mkdirlog(fileDir)
-	logObj = &_FILE{dir: fileDir, filename: fileName, _date: &t, isCover: false, mu: new(sync.RWMutex)}
-	logObj.mu.Lock()
-	defer logObj.mu.Unlock()
-
-	if !logObj.isMustRename() {
-		logObj.logfile, _ = os.OpenFile(fileDir+"/"+fileName, os.O_RDWR|os.O_APPEND|os.O_CREATE, 0666)
-		logObj.lg = log.New(logObj.logfile, "", log.Ldate|log.Ltime|log.Lshortfile)
-	} else {
-		logObj.rename()
-	}
-}
-
-func mkdirlog(dir string) (e error) {
-	_, er := os.Stat(dir)
-	b := er == nil || os.IsExist(er)
-	if !b {
-		if err := os.MkdirAll(dir, 0666); err != nil {
-			if os.IsPermission(err) {
-				fmt.Println("create dir error:", err.Error())
-				e = err
-			}
-		}
-	}
-	return
-}
-
-func console(s ...interface{}) {
-	if consoleAppender {
-		_, file, line, _ := runtime.Caller(2)
-		short := file
-		for i := len(file) - 1; i > 0; i-- {
-			if file[i] == '/' {
-				short = file[i+1:]
-				break
-			}
-		}
-		file = short
-		log.Println(file, strconv.Itoa(line), s)
-	}
-}
-
-func catchError() {
-	if err := recover(); err != nil {
-		log.Println("err", err)
-	}
-}
-
-func Debug(v ...interface{}) {
-	if dailyRolling {
-		fileCheck()
-	}
-	defer catchError()
-	if logObj != nil {
-		logObj.mu.RLock()
-		defer logObj.mu.RUnlock()
-	}
-
-	if logLevel <= DEBUG {
-		if logObj != nil {
-			logObj.lg.Output(2, fmt.Sprintln("debug", v))
-		}
-		console("debug", v)
-	}
-}
-func Info(v ...interface{}) {
-	if dailyRolling {
-		fileCheck()
-	}
-	defer catchError()
-	if logObj != nil {
-		logObj.mu.RLock()
-		defer logObj.mu.RUnlock()
-	}
-	if logLevel <= INFO {
-		if logObj != nil {
-			logObj.lg.Output(2, fmt.Sprintln("info", v))
-		}
-		console("info", v)
-	}
-}
-func Warn(v ...interface{}) {
-	if dailyRolling {
-		fileCheck()
-	}
-	defer catchError()
-	if logObj != nil {
-		logObj.mu.RLock()
-		defer logObj.mu.RUnlock()
-	}
-
-	if logLevel <= WARN {
-		if logObj != nil {
-			logObj.lg.Output(2, fmt.Sprintln("warn", v))
-		}
-		console("warn", v)
-	}
-}
-func Error(v ...interface{}) {
-	if dailyRolling {
-		fileCheck()
-	}
-	defer catchError()
-	if logObj != nil {
-		logObj.mu.RLock()
-		defer logObj.mu.RUnlock()
-	}
-	if logLevel <= ERROR {
-		if logObj != nil {
-			logObj.lg.Output(2, fmt.Sprintln("error", v))
-		}
-		console("error", v)
-	}
-}
-func Fatal(v ...interface{}) {
-	if dailyRolling {
-		fileCheck()
-	}
-	defer catchError()
-	if logObj != nil {
-		logObj.mu.RLock()
-		defer logObj.mu.RUnlock()
-	}
-	if logLevel <= FATAL {
-		if logObj != nil {
-			logObj.lg.Output(2, fmt.Sprintln("fatal", v))
-		}
-		console("fatal", v)
-	}
-}
-
-func (f *_FILE) isMustRename() bool {
-	if dailyRolling {
-		t, _ := time.Parse(DATEFORMAT, time.Now().Format(DATEFORMAT))
-		if t.After(*f._date) {
-			return true
-		}
-	} else {
-		if maxFileCount > 1 {
-			if fileSize(f.dir+"/"+f.filename) >= maxFileSize {
-				return true
-			}
-		}
-	}
-	return false
-}
-
-func (f *_FILE) rename() {
-	if dailyRolling {
-		fn := f.dir + "/" + f.filename + "." + f._date.Format(DATEFORMAT)
-		if !isExist(fn) && f.isMustRename() {
-			if f.logfile != nil {
-				f.logfile.Close()
-			}
-			err := os.Rename(f.dir+"/"+f.filename, fn)
-			if err != nil {
-				f.lg.Println("rename err", err.Error())
-			}
-			t, _ := time.Parse(DATEFORMAT, time.Now().Format(DATEFORMAT))
-			f._date = &t
-			f.logfile, _ = os.Create(f.dir + "/" + f.filename)
-			f.lg = log.New(logObj.logfile, "\n", log.Ldate|log.Ltime|log.Lshortfile)
-		}
-	} else {
-		f.coverNextOne()
-	}
-}
-
-func (f *_FILE) nextSuffix() int {
-	return int(f._suffix%int(maxFileCount) + 1)
-}
-
-func (f *_FILE) coverNextOne() {
-	f._suffix = f.nextSuffix()
-	if f.logfile != nil {
-		f.logfile.Close()
-	}
-	if isExist(f.dir + "/" + f.filename + "." + strconv.Itoa(int(f._suffix))) {
-		os.Remove(f.dir + "/" + f.filename + "." + strconv.Itoa(int(f._suffix)))
-	}
-	os.Rename(f.dir+"/"+f.filename, f.dir+"/"+f.filename+"."+strconv.Itoa(int(f._suffix)))
-	f.logfile, _ = os.Create(f.dir + "/" + f.filename)
-	f.lg = log.New(logObj.logfile, "\n", log.Ldate|log.Ltime|log.Lshortfile)
-}
-
-func fileSize(file string) int64 {
-	fmt.Println("fileSize", file)
-	f, e := os.Stat(file)
-	if e != nil {
-		fmt.Println(e.Error())
-		return 0
-	}
-	return f.Size()
-}
-
-func isExist(path string) bool {
-	_, err := os.Stat(path)
-	return err == nil || os.IsExist(err)
-}
-
-func fileMonitor() {
-	timer := time.NewTicker(1 * time.Second)
-	for {
-		select {
-		case <-timer.C:
-			fileCheck()
-		}
-	}
-}
-
-func fileCheck() {
-	defer func() {
-		if err := recover(); err != nil {
-			log.Println(err)
-		}
-	}()
-	if logObj != nil && logObj.isMustRename() {
-		logObj.mu.Lock()
-		defer logObj.mu.Unlock()
-		logObj.rename()
-	}
-}

+ 0 - 614
common_utils/mongodb/mongodb.go

@@ -1,614 +0,0 @@
-package mongodb
-
-import (
-	"context"
-	"encoding/json"
-	"fmt"
-	"go.mongodb.org/mongo-driver/bson"
-	"go.mongodb.org/mongo-driver/bson/primitive"
-	"go.mongodb.org/mongo-driver/mongo"
-	"go.mongodb.org/mongo-driver/mongo/options"
-	"log"
-	"math/big"
-	"runtime"
-	"strconv"
-	"strings"
-	"time"
-)
-
-type MgoSess struct {
-	db     string
-	coll   string
-	query  interface{}
-	sorts  []string
-	fields interface{}
-	limit  int64
-	skip   int64
-	pipe   []map[string]interface{}
-	all    interface{}
-	M      *MongodbSim
-}
-
-type MgoIter struct {
-	Cursor *mongo.Cursor
-}
-
-func NewMgo(addr, db string, size int) *MongodbSim {
-	mgo := &MongodbSim{
-		MongodbAddr: addr,
-		Size:        size,
-		DbName:      db,
-	}
-	mgo.InitPool()
-	return mgo
-}
-
-func (mt *MgoIter) Next(result interface{}) bool {
-	if mt.Cursor != nil {
-		if mt.Cursor.Next(nil) {
-			err := mt.Cursor.Decode(result)
-			if err != nil {
-				log.Println("mgo cur err", err.Error())
-				mt.Cursor.Close(nil)
-				return false
-			}
-			return true
-		} else {
-			mt.Cursor.Close(nil)
-			return false
-		}
-	} else {
-		return false
-	}
-}
-
-func (ms *MgoSess) DB(name string) *MgoSess {
-	ms.db = name
-	return ms
-}
-
-func (ms *MgoSess) C(name string) *MgoSess {
-	ms.coll = name
-	return ms
-}
-
-func (ms *MgoSess) Find(q interface{}) *MgoSess {
-	if q == nil {
-		q = map[string]interface{}{}
-	}
-	ms.query = q
-	return ms
-}
-
-func (ms *MgoSess) Select(fields interface{}) *MgoSess {
-	ms.fields = fields
-	return ms
-}
-
-func (ms *MgoSess) Limit(limit int64) *MgoSess {
-	ms.limit = limit
-	return ms
-}
-func (ms *MgoSess) Skip(skip int64) *MgoSess {
-	ms.skip = skip
-	return ms
-}
-
-func (ms *MgoSess) Sort(sorts ...string) *MgoSess {
-	ms.sorts = sorts
-	return ms
-}
-func (ms *MgoSess) Pipe(p []map[string]interface{}) *MgoSess {
-	ms.pipe = p
-	return ms
-}
-func (ms *MgoSess) All(v *[]map[string]interface{}) {
-	cur, err := ms.M.C.Database(ms.db).Collection(ms.coll).Aggregate(ms.M.Ctx, ms.pipe)
-	if err == nil && cur.Err() == nil {
-		cur.All(ms.M.Ctx, v)
-	}
-}
-func (ms *MgoSess) Iter() *MgoIter {
-	it := &MgoIter{}
-	find := options.Find()
-	if ms.skip > 0 {
-		find.SetSkip(ms.skip)
-	}
-	if ms.limit > 0 {
-		find.SetLimit(ms.limit)
-	}
-	find.SetBatchSize(100)
-	if len(ms.sorts) > 0 {
-		sort := bson.M{}
-		for _, k := range ms.sorts {
-			switch k[:1] {
-			case "-":
-				sort[k[1:]] = -1
-			case "+":
-				sort[k[1:]] = 1
-			default:
-				sort[k] = 1
-			}
-		}
-		find.SetSort(sort)
-	}
-	if ms.fields != nil {
-		find.SetProjection(ms.fields)
-	}
-	cur, err := ms.M.C.Database(ms.db).Collection(ms.coll).Find(ms.M.Ctx, ms.query, find)
-	if err != nil {
-		log.Println("mgo find err", err.Error())
-	} else {
-		it.Cursor = cur
-	}
-	return it
-}
-
-func (ms *MgoSess) Count() (int64, error) {
-	return ms.M.C.Database(ms.db).Collection(ms.coll).CountDocuments(ms.M.Ctx, ms.query)
-}
-
-type MongodbSim struct {
-	MongodbAddr string
-	Size        int
-	//	MinSize     int
-	DbName   string
-	C        *mongo.Client
-	Ctx      context.Context
-	ShortCtx context.Context
-	pool     chan bool
-	UserName string
-	Password string
-	ReplSet  string
-}
-
-func (m *MongodbSim) GetMgoConn() *MgoSess {
-	//m.Open()
-	ms := &MgoSess{}
-	ms.M = m
-	return ms
-}
-
-func (m *MongodbSim) DestoryMongoConn(ms *MgoSess) {
-	//m.Close()
-	ms.M = nil
-	ms = nil
-}
-
-func (m *MongodbSim) Destroy() {
-	//m.Close()
-	m.C.Disconnect(nil)
-	m.C = nil
-}
-
-func (m *MongodbSim) InitPool() {
-	opts := options.Client()
-	opts.SetConnectTimeout(3 * time.Second)
-	opts.SetHosts(strings.Split(m.MongodbAddr, ","))
-	//opts.ApplyURI("mongodb://" + m.MongodbAddr)
-	opts.SetMaxPoolSize(uint64(m.Size))
-	if m.UserName != "" && m.Password != "" {
-		cre := options.Credential{
-			Username: m.UserName,
-			Password: m.Password,
-		}
-		opts.SetAuth(cre)
-	}
-	//ms := strings.Split(m.MongodbAddr, ",")
-	//if m.ReplSet == "" && len(ms) > 1 {
-	//	m.ReplSet = "qfws"
-	//}
-	if m.ReplSet != "" {
-		opts.SetReplicaSet(m.ReplSet)
-		opts.SetDirect(false)
-	}
-	m.pool = make(chan bool, m.Size)
-	opts.SetMaxConnIdleTime(2 * time.Hour)
-	m.Ctx, _ = context.WithTimeout(context.Background(), 99999*time.Hour)
-	m.ShortCtx, _ = context.WithTimeout(context.Background(), 1*time.Minute)
-	client, err := mongo.Connect(m.ShortCtx, opts)
-	if err != nil {
-		log.Println("mgo init error:", err.Error())
-	} else {
-		m.C = client
-	}
-}
-
-func (m *MongodbSim) Open() {
-	m.pool <- true
-}
-func (m *MongodbSim) Close() {
-	<-m.pool
-}
-
-func (m *MongodbSim) Save(c string, doc interface{}) string {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	coll := m.C.Database(m.DbName).Collection(c)
-	obj := ObjToM(doc)
-	id := primitive.NewObjectID()
-	(*obj)["_id"] = id
-	_, err := coll.InsertOne(m.Ctx, obj)
-	if nil != err {
-		log.Println("SaveError", err)
-		return ""
-	}
-	return id.Hex()
-}
-
-//原_id不变
-func (m *MongodbSim) SaveByOriID(c string, doc interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	coll := m.C.Database(m.DbName).Collection(c)
-	_, err := coll.InsertOne(m.Ctx, ObjToM(doc))
-	if nil != err {
-		log.Println("SaveByOriIDError", err)
-		return false
-	}
-	return true
-}
-
-//批量插入
-func (m *MongodbSim) SaveBulk(c string, doc ...map[string]interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	coll := m.C.Database(m.DbName).Collection(c)
-	var writes []mongo.WriteModel
-	for _, d := range doc {
-		write := mongo.NewInsertOneModel()
-		write.SetDocument(d)
-		writes = append(writes, write)
-	}
-	br, e := coll.BulkWrite(m.Ctx, writes)
-	if e != nil {
-		b := strings.Index(e.Error(), "duplicate") > -1
-		log.Println("mgo savebulk error:", e.Error())
-		if br != nil {
-			log.Println("mgo savebulk size:", br.InsertedCount)
-		}
-		return b
-	}
-	return true
-}
-
-//批量插入
-func (m *MongodbSim) SaveBulkInterface(c string, doc ...interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	coll := m.C.Database(m.DbName).Collection(c)
-	var writes []mongo.WriteModel
-	for _, d := range doc {
-		write := mongo.NewInsertOneModel()
-		write.SetDocument(d)
-		writes = append(writes, write)
-	}
-	br, e := coll.BulkWrite(m.Ctx, writes)
-	if e != nil {
-		b := strings.Index(e.Error(), "duplicate") > -1
-		log.Println("mgo SaveBulkInterface error:", e.Error())
-		if br != nil {
-			log.Println("mgo SaveBulkInterface size:", br.InsertedCount)
-		}
-		return b
-	}
-	return true
-}
-
-//按条件统计
-func (m *MongodbSim) Count(c string, q interface{}) int {
-	r, _ := m.CountByErr(c, q)
-	return r
-}
-
-//统计
-func (m *MongodbSim) CountByErr(c string, q interface{}) (int, error) {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	res, err := m.C.Database(m.DbName).Collection(c).CountDocuments(m.Ctx, ObjToM(q))
-	if err != nil {
-		log.Println("统计错误", err.Error())
-		return 0, err
-	} else {
-		return int(res), nil
-	}
-}
-
-//按条件删除
-func (m *MongodbSim) Delete(c string, q interface{}) int64 {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	res, err := m.C.Database(m.DbName).Collection(c).DeleteMany(m.Ctx, ObjToM(q))
-	if err != nil && res == nil {
-		log.Println("删除错误", err.Error())
-	}
-	return res.DeletedCount
-}
-
-//删除对象
-func (m *MongodbSim) Del(c string, q interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	_, err := m.C.Database(m.DbName).Collection(c).DeleteMany(m.Ctx, ObjToM(q))
-	if err != nil {
-		log.Println("删除错误", err.Error())
-		return false
-	}
-	return true
-}
-
-//删除表
-func (m *MongodbSim) DelColl(c string) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	err := m.C.Database(m.DbName).Collection(c).Drop(m.Ctx)
-	if err != nil {
-		log.Println("删除错误", err.Error())
-		return false
-	}
-	return true
-}
-
-//按条件更新
-func (m *MongodbSim) Update(c string, q, u interface{}, upsert bool, multi bool) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	ct := options.Update()
-	if upsert {
-		ct.SetUpsert(true)
-	}
-	coll := m.C.Database(m.DbName).Collection(c)
-	var err error
-	if multi {
-		_, err = coll.UpdateMany(m.Ctx, ObjToM(q), ObjToM(u), ct)
-	} else {
-		_, err = coll.UpdateOne(m.Ctx, ObjToM(q), ObjToM(u), ct)
-	}
-	if err != nil {
-		log.Println("删除错误", err.Error())
-		return false
-	}
-	return true
-}
-func (m *MongodbSim) UpdateById(c string, id interface{}, set interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	q := make(map[string]interface{})
-	if sid, ok := id.(string); ok {
-		q["_id"], _ = primitive.ObjectIDFromHex(sid)
-	} else {
-		q["_id"] = id
-	}
-	_, err := m.C.Database(m.DbName).Collection(c).UpdateOne(m.Ctx, q, ObjToM(set))
-	if nil != err {
-		log.Println("UpdateByIdError", err)
-		return false
-	}
-	return true
-}
-
-//批量更新
-func (m *MongodbSim) UpdateBulkAll(db, c string, doc ...[]map[string]interface{}) bool {
-	return m.upSertBulk(db, c, false, doc...)
-}
-
-func (m *MongodbSim) UpdateBulk(c string, doc ...[]map[string]interface{}) bool {
-	return m.UpdateBulkAll(m.DbName, c, doc...)
-}
-
-//批量插入
-func (m *MongodbSim) UpSertBulk(c string, doc ...[]map[string]interface{}) bool {
-	return m.upSertBulk(m.DbName, c, true, doc...)
-}
-
-//批量插入
-func (m *MongodbSim) upSertBulk(db, c string, upsert bool, doc ...[]map[string]interface{}) bool {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	coll := m.C.Database(db).Collection(c)
-	var writes []mongo.WriteModel
-	for _, d := range doc {
-		write := mongo.NewUpdateOneModel()
-		write.SetFilter(d[0])
-		write.SetUpdate(d[1])
-		write.SetUpsert(upsert)
-		writes = append(writes, write)
-	}
-	br, e := coll.BulkWrite(m.Ctx, writes)
-	if e != nil {
-		log.Println("mgo upsert error:", e.Error())
-		return br == nil || br.UpsertedCount == 0
-	}
-	//	else {
-	//		if r.UpsertedCount != int64(len(doc)) {
-	//			log.Println("mgo upsert uncomplete:uc/dc", r.UpsertedCount, len(doc))
-	//		}
-	//		return true
-	//	}
-	return true
-}
-
-//查询单条对象
-func (m *MongodbSim) FindOne(c string, query interface{}) (*map[string]interface{}, bool) {
-	return m.FindOneByField(c, query, nil)
-}
-
-//查询单条对象
-func (m *MongodbSim) FindOneByField(c string, query interface{}, fields interface{}) (*map[string]interface{}, bool) {
-	defer catch()
-	res, ok := m.Find(c, query, nil, fields, true, -1, -1)
-	if nil != res && len(*res) > 0 {
-		return &((*res)[0]), ok
-	}
-	return nil, ok
-}
-
-//查询单条对象
-func (m *MongodbSim) FindById(c string, query string, fields interface{}) (*map[string]interface{}, bool) {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	of := options.FindOne()
-	of.SetProjection(ObjToOth(fields))
-	b := false
-	res := make(map[string]interface{})
-	_id, err := primitive.ObjectIDFromHex(query)
-	if err != nil {
-		log.Println("_id error", err)
-		return &res, b
-	}
-	sr := m.C.Database(m.DbName).Collection(c).FindOne(m.Ctx, map[string]interface{}{"_id": _id}, of)
-	if sr.Err() == nil {
-		b = true
-		sr.Decode(&res)
-	}
-	return &res, b
-}
-
-//底层查询方法
-func (m *MongodbSim) Find(c string, query interface{}, order interface{}, fields interface{}, single bool, start int, limit int) (*[]map[string]interface{}, bool) {
-	defer catch()
-	m.Open()
-	defer m.Close()
-	res := make([]map[string]interface{}, 1)
-	coll := m.C.Database(m.DbName).Collection(c)
-	if single {
-		of := options.FindOne()
-		of.SetProjection(ObjToOth(fields))
-		of.SetSort(ObjToM(order))
-		if sr := coll.FindOne(m.Ctx, ObjToM(query), of); sr.Err() == nil {
-			sr.Decode(&res[0])
-		}
-	} else {
-		of := options.Find()
-		of.SetProjection(ObjToOth(fields))
-		of.SetSort(ObjToM(order))
-		if start > -1 {
-			of.SetSkip(int64(start))
-			of.SetLimit(int64(limit))
-		}
-		cur, err := coll.Find(m.Ctx, ObjToM(query), of)
-		if err == nil && cur.Err() == nil {
-			cur.All(m.Ctx, &res)
-		}
-	}
-	return &res, true
-}
-
-func ObjToOth(query interface{}) *bson.M {
-	return ObjToMQ(query, false)
-}
-func ObjToM(query interface{}) *bson.M {
-	return ObjToMQ(query, true)
-}
-
-//obj(string,M)转M,查询用到
-func ObjToMQ(query interface{}, isQuery bool) *bson.M {
-	data := make(bson.M)
-	defer catch()
-	if s2, ok2 := query.(*map[string]interface{}); ok2 {
-		data = bson.M(*s2)
-	} else if s3, ok3 := query.(*bson.M); ok3 {
-		return s3
-	} else if s3, ok3 := query.(*primitive.M); ok3 {
-		return s3
-	} else if s, ok := query.(string); ok {
-		json.Unmarshal([]byte(strings.Replace(s, "'", "\"", -1)), &data)
-		if ss, oks := data["_id"]; oks && isQuery {
-			switch ss.(type) {
-			case string:
-				data["_id"], _ = primitive.ObjectIDFromHex(ss.(string))
-			case map[string]interface{}:
-				tmp := ss.(map[string]interface{})
-				for k, v := range tmp {
-					tmp[k], _ = primitive.ObjectIDFromHex(v.(string))
-				}
-				data["_id"] = tmp
-			}
-
-		}
-	} else if s1, ok1 := query.(map[string]interface{}); ok1 {
-		data = s1
-	} else if s4, ok4 := query.(bson.M); ok4 {
-		data = s4
-	} else if s4, ok4 := query.(primitive.M); ok4 {
-		data = s4
-	} else {
-		data = nil
-	}
-	return &data
-}
-func intAllDef(num interface{}, defaultNum int) int {
-	if i, ok := num.(int); ok {
-		return int(i)
-	} else if i0, ok0 := num.(int32); ok0 {
-		return int(i0)
-	} else if i1, ok1 := num.(float64); ok1 {
-		return int(i1)
-	} else if i2, ok2 := num.(int64); ok2 {
-		return int(i2)
-	} else if i3, ok3 := num.(float32); ok3 {
-		return int(i3)
-	} else if i4, ok4 := num.(string); ok4 {
-		in, _ := strconv.Atoi(i4)
-		return int(in)
-	} else if i5, ok5 := num.(int16); ok5 {
-		return int(i5)
-	} else if i6, ok6 := num.(int8); ok6 {
-		return int(i6)
-	} else if i7, ok7 := num.(*big.Int); ok7 {
-		in, _ := strconv.Atoi(fmt.Sprint(i7))
-		return int(in)
-	} else if i8, ok8 := num.(*big.Float); ok8 {
-		in, _ := strconv.Atoi(fmt.Sprint(i8))
-		return int(in)
-	} else {
-		return defaultNum
-	}
-}
-
-//出错拦截
-func catch() {
-	if r := recover(); r != nil {
-		log.Println(r)
-		for skip := 0; ; skip++ {
-			_, file, line, ok := runtime.Caller(skip)
-			if !ok {
-				break
-			}
-			go log.Printf("%v,%v\n", file, line)
-		}
-	}
-}
-
-//根据bsonID转string
-func BsonIdToSId(uid interface{}) string {
-	if uid == nil {
-		return ""
-	} else if u, ok := uid.(string); ok {
-		return u
-	} else if u, ok := uid.(primitive.ObjectID); ok {
-		return u.Hex()
-	} else {
-		return ""
-	}
-}
-
-func StringTOBsonId(id string) (bid primitive.ObjectID) {
-	defer catch()
-	if id != "" {
-		bid, _ = primitive.ObjectIDFromHex(id)
-	}
-	return
-}

+ 0 - 504
common_utils/mysql.go

@@ -1,504 +0,0 @@
-package util
-
-import (
-	"bytes"
-	"database/sql"
-	"fmt"
-	"log"
-	"reflect"
-	"strings"
-	"time"
-
-	_ "github.com/go-sql-driver/mysql"
-)
-
-type Mysql struct {
-	Address      string  //数据库地址:端口
-	UserName     string  //用户名
-	PassWord     string  //密码
-	DBName       string  //数据库名
-	DB           *sql.DB //数据库连接池对象
-	MaxOpenConns int     //用于设置最大打开的连接数,默认值为0表示不限制。
-	MaxIdleConns int     //用于设置闲置的连接数。
-}
-
-func (m *Mysql) Init() {
-	if m.MaxOpenConns <= 0 {
-		m.MaxOpenConns = 20
-	}
-	if m.MaxIdleConns <= 0 {
-		m.MaxIdleConns = 20
-	}
-	var err error
-	m.DB, err = sql.Open("mysql", fmt.Sprintf("%s:%s@tcp(%s)/%s?charset=utf8mb4&parseTime=true&loc=Local", m.UserName, m.PassWord, m.Address, m.DBName))
-	if err != nil {
-		log.Println(err)
-		return
-	}
-	m.DB.SetMaxOpenConns(m.MaxOpenConns)
-	m.DB.SetMaxIdleConns(m.MaxIdleConns)
-	m.DB.SetConnMaxLifetime(time.Minute * 3)
-	err = m.DB.Ping()
-	if err != nil {
-		log.Println(err)
-	}
-}
-
-//新增
-func (m *Mysql) Insert(tableName string, data map[string]interface{}) int64 {
-	return m.InsertByTx(nil, tableName, data)
-}
-
-//带有事务的新增
-func (m *Mysql) InsertByTx(tx *sql.Tx, tableName string, data map[string]interface{}) int64 {
-	fields := []string{}
-	values := []interface{}{}
-	placeholders := []string{}
-	if tableName == "dataexport_order" {
-		if _, ok := data["user_nickname"]; ok {
-			data["user_nickname"] = ""
-		}
-	}
-	for k, v := range data {
-		fields = append(fields, k)
-		values = append(values, v)
-		placeholders = append(placeholders, "?")
-	}
-	q := fmt.Sprintf("INSERT INTO %s (%s) VALUES (%s)", tableName, strings.Join(fields, ","), strings.Join(placeholders, ","))
-	//log.Println("mysql", q, values)
-	return m.InsertBySqlByTx(tx, q, values...)
-}
-
-//sql语句新增
-func (m *Mysql) InsertBySql(q string, args ...interface{}) int64 {
-	return m.InsertBySqlByTx(nil, q, args...)
-}
-
-//带有事务的sql语句新增
-func (m *Mysql) InsertBySqlByTx(tx *sql.Tx, q string, args ...interface{}) int64 {
-	result, _ := m.ExecBySqlByTx(tx, q, args...)
-	if result == nil {
-		return -1
-	}
-	id, err := result.LastInsertId()
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	return id
-}
-
-//批量新增
-func (m *Mysql) InsertIgnoreBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.InsertIgnoreBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量新增
-func (m *Mysql) InsertIgnoreBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "INSERT", "IGNORE", tableName, fields, values)
-}
-
-//批量新增
-func (m *Mysql) InsertBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.InsertBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量新增
-func (m *Mysql) InsertBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "INSERT", "", tableName, fields, values)
-}
-
-//批量更新
-func (m *Mysql) ReplaceBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.ReplaceBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量更新
-func (m *Mysql) ReplaceBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "REPLACE", "", tableName, fields, values)
-}
-
-func (m *Mysql) insertOrReplaceBatchByTx(tx *sql.Tx, tp string, afterInsert, tableName string, fields []string, values []interface{}) (int64, int64) {
-	placeholders := []string{}
-	for range fields {
-		placeholders = append(placeholders, "?")
-	}
-	placeholder := strings.Join(placeholders, ",")
-	array := []string{}
-	for i := 0; i < len(values)/len(fields); i++ {
-		array = append(array, fmt.Sprintf("(%s)", placeholder))
-	}
-	q := fmt.Sprintf("%s %s INTO %s (%s) VALUES %s", tp, afterInsert, tableName, strings.Join(fields, ","), strings.Join(array, ","))
-	result, _ := m.ExecBySqlByTx(tx, q, values...)
-	if result == nil {
-		return -1, -1
-	}
-	v1, e1 := result.RowsAffected()
-	if e1 != nil {
-		log.Println(e1)
-		return -1, -1
-	}
-	v2, e2 := result.LastInsertId()
-	if e2 != nil {
-		log.Println(e2)
-		return -1, -1
-	}
-	return v1, v2
-}
-
-//sql语句执行
-func (m *Mysql) ExecBySql(q string, args ...interface{}) (sql.Result, error) {
-	return m.ExecBySqlByTx(nil, q, args...)
-}
-
-//sql语句执行,带有事务
-func (m *Mysql) ExecBySqlByTx(tx *sql.Tx, q string, args ...interface{}) (sql.Result, error) {
-	var stmtIns *sql.Stmt
-	var err error
-	if tx == nil {
-		stmtIns, err = m.DB.Prepare(q)
-	} else {
-		stmtIns, err = tx.Prepare(q)
-	}
-	if err != nil {
-		log.Println(err)
-		return nil, err
-	}
-	defer stmtIns.Close()
-	result, err := stmtIns.Exec(args...)
-	if err != nil {
-		log.Println(args, err)
-		return nil, err
-	}
-	return result, nil
-}
-
-/*不等于 map[string]string{"ne":"1"}
- *不等于多个 map[string]string{"notin":[]interface{}{1,2}}
- *字段为空 map[string]string{"name":"$isNull"}
- *字段不为空 map[string]string{"name":"$isNotNull"}
- */
-func (m *Mysql) Find(tableName string, query map[string]interface{}, fields, order string, start, pageSize int) *[]map[string]interface{} {
-	fs := []string{}
-	vs := []interface{}{}
-	for k, v := range query {
-		rt := reflect.TypeOf(v)
-		rv := reflect.ValueOf(v)
-		if rt.Kind() == reflect.Map {
-			for _, rv_k := range rv.MapKeys() {
-				if rv_k.String() == "ne" {
-					fs = append(fs, fmt.Sprintf("%s!=?", k))
-					vs = append(vs, rv.MapIndex(rv_k).Interface())
-				}
-				if rv_k.String() == "notin" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						for _, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							fs = append(fs, fmt.Sprintf("%s!=?", k))
-							vs = append(vs, v)
-						}
-					}
-				}
-				if rv_k.String() == "in" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						_fs := fmt.Sprintf("%s in (?", k)
-						for k, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							if k > 0 {
-								_fs += ",?"
-							}
-							vs = append(vs, v)
-						}
-						_fs += ")"
-						fs = append(fs, _fs)
-					}
-				}
-			}
-		} else {
-			if v == "$isNull" {
-				fs = append(fs, fmt.Sprintf("%s is null", k))
-			} else if v == "$isNotNull" {
-				fs = append(fs, fmt.Sprintf("%s is not null", k))
-			} else {
-				fs = append(fs, fmt.Sprintf("%s=?", k))
-				vs = append(vs, v)
-			}
-		}
-	}
-	var buffer bytes.Buffer
-	buffer.WriteString("select ")
-	if fields == "" {
-		buffer.WriteString("*")
-	} else {
-		buffer.WriteString(fields)
-	}
-	buffer.WriteString(" from ")
-	buffer.WriteString(tableName)
-	if len(fs) > 0 {
-		buffer.WriteString(" where ")
-		buffer.WriteString(strings.Join(fs, " and "))
-	}
-	if order != "" {
-		buffer.WriteString(" order by ")
-		buffer.WriteString(order)
-	}
-	if start > -1 && pageSize > 0 {
-		buffer.WriteString(" limit ")
-		buffer.WriteString(fmt.Sprint(start))
-		buffer.WriteString(",")
-		buffer.WriteString(fmt.Sprint(pageSize))
-	}
-	q := buffer.String()
-	//log.Println(q, vs)
-	return m.SelectBySql(q, vs...)
-}
-
-//sql语句查询
-func (m *Mysql) SelectBySql(q string, args ...interface{}) *[]map[string]interface{} {
-	return m.SelectBySqlByTx(nil, q, args...)
-}
-func (m *Mysql) SelectBySqlByTx(tx *sql.Tx, q string, args ...interface{}) *[]map[string]interface{} {
-	return m.Select(0, nil, tx, q, args...)
-}
-func (m *Mysql) Select(bath int, f func(l *[]map[string]interface{}), tx *sql.Tx, q string, args ...interface{}) *[]map[string]interface{} {
-	var stmtOut *sql.Stmt
-	var err error
-	if tx == nil {
-		stmtOut, err = m.DB.Prepare(q)
-	} else {
-		stmtOut, err = tx.Prepare(q)
-	}
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	defer stmtOut.Close()
-	rows, err := stmtOut.Query(args...)
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	if rows != nil {
-		defer rows.Close()
-	}
-	columns, err := rows.Columns()
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	list := []map[string]interface{}{}
-	for rows.Next() {
-		scanArgs := make([]interface{}, len(columns))
-		values := make([]interface{}, len(columns))
-		ret := make(map[string]interface{})
-		for k, _ := range values {
-			scanArgs[k] = &values[k]
-		}
-		err = rows.Scan(scanArgs...)
-		if err != nil {
-			log.Println(err)
-			break
-		}
-		for i, col := range values {
-			if v, ok := col.([]uint8); ok {
-				ret[columns[i]] = string(v)
-			} else {
-				ret[columns[i]] = col
-			}
-		}
-		list = append(list, ret)
-		if bath > 0 && len(list) == bath {
-			f(&list)
-			list = []map[string]interface{}{}
-		}
-	}
-	if bath > 0 && len(list) > 0 {
-		f(&list)
-		list = []map[string]interface{}{}
-	}
-	return &list
-}
-func (m *Mysql) SelectByBath(bath int, f func(l *[]map[string]interface{}), q string, args ...interface{}) {
-	m.SelectByBathByTx(bath, f, nil, q, args...)
-}
-func (m *Mysql) SelectByBathByTx(bath int, f func(l *[]map[string]interface{}), tx *sql.Tx, q string, args ...interface{}) {
-	m.Select(bath, f, tx, q, args...)
-}
-func (m *Mysql) FindOne(tableName string, query map[string]interface{}, fields, order string) *map[string]interface{} {
-	list := m.Find(tableName, query, fields, order, 0, 1)
-	if list != nil && len(*list) == 1 {
-		temp := (*list)[0]
-		return &temp
-	}
-	return nil
-}
-
-//修改
-func (m *Mysql) Update(tableName string, query, update map[string]interface{}) bool {
-	return m.UpdateByTx(nil, tableName, query, update)
-}
-
-//带事务的修改
-func (m *Mysql) UpdateByTx(tx *sql.Tx, tableName string, query, update map[string]interface{}) bool {
-	q_fs := []string{}
-	u_fs := []string{}
-	values := []interface{}{}
-	for k, v := range update {
-		q_fs = append(q_fs, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	for k, v := range query {
-		u_fs = append(u_fs, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	q := fmt.Sprintf("update %s set %s where %s", tableName, strings.Join(q_fs, ","), strings.Join(u_fs, " and "))
-	log.Println(q, values)
-	return m.UpdateOrDeleteBySqlByTx(tx, q, values...) >= 0
-}
-
-//删除
-func (m *Mysql) Delete(tableName string, query map[string]interface{}) bool {
-	return m.DeleteByTx(nil, tableName, query)
-}
-func (m *Mysql) DeleteByTx(tx *sql.Tx, tableName string, query map[string]interface{}) bool {
-	fields := []string{}
-	values := []interface{}{}
-	for k, v := range query {
-		fields = append(fields, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	q := fmt.Sprintf("delete from %s where %s", tableName, strings.Join(fields, " and "))
-	log.Println(q, values)
-	return m.UpdateOrDeleteBySqlByTx(tx, q, values...) > 0
-}
-
-//修改或删除
-func (m *Mysql) UpdateOrDeleteBySql(q string, args ...interface{}) int64 {
-	return m.UpdateOrDeleteBySqlByTx(nil, q, args...)
-}
-
-//带事务的修改或删除
-func (m *Mysql) UpdateOrDeleteBySqlByTx(tx *sql.Tx, q string, args ...interface{}) int64 {
-	result, err := m.ExecBySqlByTx(tx, q, args...)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	count, err := result.RowsAffected()
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	return count
-}
-
-//总数
-func (m *Mysql) Count(tableName string, query map[string]interface{}) int64 {
-	fields := []string{}
-	values := []interface{}{}
-	for k, v := range query {
-		rt := reflect.TypeOf(v)
-		rv := reflect.ValueOf(v)
-		if rt.Kind() == reflect.Map {
-			for _, rv_k := range rv.MapKeys() {
-				if rv_k.String() == "ne" {
-					fields = append(fields, fmt.Sprintf("%s!=?", k))
-					values = append(values, rv.MapIndex(rv_k).Interface())
-				}
-				if rv_k.String() == "notin" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						for _, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							fields = append(fields, fmt.Sprintf("%s!=?", k))
-							values = append(values, v)
-						}
-					}
-				}
-				if rv_k.String() == "in" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						_fs := fmt.Sprintf("%s in (?", k)
-						for k, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							if k > 0 {
-								_fs += ",?"
-							}
-							values = append(values, v)
-						}
-						_fs += ")"
-						fields = append(fields, _fs)
-					}
-				}
-			}
-		} else if v == "$isNull" {
-			fields = append(fields, fmt.Sprintf("%s is null", k))
-		} else if v == "$isNotNull" {
-			fields = append(fields, fmt.Sprintf("%s is not null", k))
-		} else {
-			fields = append(fields, fmt.Sprintf("%s=?", k))
-			values = append(values, v)
-		}
-	}
-	q := fmt.Sprintf("select count(1) as count from %s", tableName)
-	if len(query) > 0 {
-		q += fmt.Sprintf(" where %s", strings.Join(fields, " and "))
-	}
-	log.Println(q, values)
-	return m.CountBySql(q, values...)
-}
-func (m *Mysql) CountBySql(q string, args ...interface{}) int64 {
-	stmtIns, err := m.DB.Prepare(q)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	defer stmtIns.Close()
-
-	rows, err := stmtIns.Query(args...)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	if rows != nil {
-		defer rows.Close()
-	}
-	var count int64 = -1
-	if rows.Next() {
-		err = rows.Scan(&count)
-		if err != nil {
-			log.Println(err)
-		}
-	}
-	return count
-}
-
-//执行事务
-func (m *Mysql) ExecTx(msg string, f func(tx *sql.Tx) bool) bool {
-	tx, err := m.DB.Begin()
-	if err != nil {
-		log.Println(msg, "获取事务错误", err)
-	} else {
-		if f(tx) {
-			if err := tx.Commit(); err != nil {
-				log.Println(msg, "提交事务错误", err)
-			} else {
-				return true
-			}
-		} else {
-			if err := tx.Rollback(); err != nil {
-				log.Println(msg, "事务回滚错误", err)
-			}
-		}
-	}
-	return false
-}
-
-/*************方法命名不规范,上面有替代方法*************/
-func (m *Mysql) Query(query string, args ...interface{}) *[]map[string]interface{} {
-	return m.SelectBySql(query, args...)
-}
-
-func (m *Mysql) QueryCount(query string, args ...interface{}) (count int) {
-	count = -1
-	if !strings.Contains(strings.ToLower(query), "count(*)") {
-		fmt.Println("QueryCount need query like < select count(*) from ..... >")
-		return
-	}
-	count = int(m.CountBySql(query, args...))
-	return
-}

+ 0 - 504
common_utils/mysqldb/mysql.go

@@ -1,504 +0,0 @@
-package mysqldb
-
-import (
-	"bytes"
-	"database/sql"
-	"fmt"
-	"log"
-	"reflect"
-	"strings"
-	"time"
-
-	_ "github.com/go-sql-driver/mysql"
-)
-
-type Mysql struct {
-	Address      string  //数据库地址:端口
-	UserName     string  //用户名
-	PassWord     string  //密码
-	DBName       string  //数据库名
-	DB           *sql.DB //数据库连接池对象
-	MaxOpenConns int     //用于设置最大打开的连接数,默认值为0表示不限制。
-	MaxIdleConns int     //用于设置闲置的连接数。
-}
-
-func (m *Mysql) Init() {
-	if m.MaxOpenConns <= 0 {
-		m.MaxOpenConns = 20
-	}
-	if m.MaxIdleConns <= 0 {
-		m.MaxIdleConns = 20
-	}
-	var err error
-	m.DB, err = sql.Open("mysql", fmt.Sprintf("%s:%s@tcp(%s)/%s?charset=utf8mb4&parseTime=true&loc=Local", m.UserName, m.PassWord, m.Address, m.DBName))
-	if err != nil {
-		log.Println(err)
-		return
-	}
-	m.DB.SetMaxOpenConns(m.MaxOpenConns)
-	m.DB.SetMaxIdleConns(m.MaxIdleConns)
-	m.DB.SetConnMaxLifetime(time.Minute * 3)
-	err = m.DB.Ping()
-	if err != nil {
-		log.Println(err)
-	}
-}
-
-//新增
-func (m *Mysql) Insert(tableName string, data map[string]interface{}) int64 {
-	return m.InsertByTx(nil, tableName, data)
-}
-
-//带有事务的新增
-func (m *Mysql) InsertByTx(tx *sql.Tx, tableName string, data map[string]interface{}) int64 {
-	fields := []string{}
-	values := []interface{}{}
-	placeholders := []string{}
-	if tableName == "dataexport_order" {
-		if _, ok := data["user_nickname"]; ok {
-			data["user_nickname"] = ""
-		}
-	}
-	for k, v := range data {
-		fields = append(fields, k)
-		values = append(values, v)
-		placeholders = append(placeholders, "?")
-	}
-	q := fmt.Sprintf("INSERT INTO %s (%s) VALUES (%s)", tableName, strings.Join(fields, ","), strings.Join(placeholders, ","))
-	//log.Println("mysql", q, values)
-	return m.InsertBySqlByTx(tx, q, values...)
-}
-
-//sql语句新增
-func (m *Mysql) InsertBySql(q string, args ...interface{}) int64 {
-	return m.InsertBySqlByTx(nil, q, args...)
-}
-
-//带有事务的sql语句新增
-func (m *Mysql) InsertBySqlByTx(tx *sql.Tx, q string, args ...interface{}) int64 {
-	result, _ := m.ExecBySqlByTx(tx, q, args...)
-	if result == nil {
-		return -1
-	}
-	id, err := result.LastInsertId()
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	return id
-}
-
-//批量新增
-func (m *Mysql) InsertIgnoreBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.InsertIgnoreBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量新增
-func (m *Mysql) InsertIgnoreBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "INSERT", "IGNORE", tableName, fields, values)
-}
-
-//批量新增
-func (m *Mysql) InsertBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.InsertBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量新增
-func (m *Mysql) InsertBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "INSERT", "", tableName, fields, values)
-}
-
-//批量更新
-func (m *Mysql) ReplaceBatch(tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.ReplaceBatchByTx(nil, tableName, fields, values)
-}
-
-//带事务的批量更新
-func (m *Mysql) ReplaceBatchByTx(tx *sql.Tx, tableName string, fields []string, values []interface{}) (int64, int64) {
-	return m.insertOrReplaceBatchByTx(tx, "REPLACE", "", tableName, fields, values)
-}
-
-func (m *Mysql) insertOrReplaceBatchByTx(tx *sql.Tx, tp string, afterInsert, tableName string, fields []string, values []interface{}) (int64, int64) {
-	placeholders := []string{}
-	for range fields {
-		placeholders = append(placeholders, "?")
-	}
-	placeholder := strings.Join(placeholders, ",")
-	array := []string{}
-	for i := 0; i < len(values)/len(fields); i++ {
-		array = append(array, fmt.Sprintf("(%s)", placeholder))
-	}
-	q := fmt.Sprintf("%s %s INTO %s (%s) VALUES %s", tp, afterInsert, tableName, strings.Join(fields, ","), strings.Join(array, ","))
-	result, _ := m.ExecBySqlByTx(tx, q, values...)
-	if result == nil {
-		return -1, -1
-	}
-	v1, e1 := result.RowsAffected()
-	if e1 != nil {
-		log.Println(e1)
-		return -1, -1
-	}
-	v2, e2 := result.LastInsertId()
-	if e2 != nil {
-		log.Println(e2)
-		return -1, -1
-	}
-	return v1, v2
-}
-
-//sql语句执行
-func (m *Mysql) ExecBySql(q string, args ...interface{}) (sql.Result, error) {
-	return m.ExecBySqlByTx(nil, q, args...)
-}
-
-//sql语句执行,带有事务
-func (m *Mysql) ExecBySqlByTx(tx *sql.Tx, q string, args ...interface{}) (sql.Result, error) {
-	var stmtIns *sql.Stmt
-	var err error
-	if tx == nil {
-		stmtIns, err = m.DB.Prepare(q)
-	} else {
-		stmtIns, err = tx.Prepare(q)
-	}
-	if err != nil {
-		log.Println(err)
-		return nil, err
-	}
-	defer stmtIns.Close()
-	result, err := stmtIns.Exec(args...)
-	if err != nil {
-		log.Println(args, err)
-		return nil, err
-	}
-	return result, nil
-}
-
-/*不等于 map[string]string{"ne":"1"}
- *不等于多个 map[string]string{"notin":[]interface{}{1,2}}
- *字段为空 map[string]string{"name":"$isNull"}
- *字段不为空 map[string]string{"name":"$isNotNull"}
- */
-func (m *Mysql) Find(tableName string, query map[string]interface{}, fields, order string, start, pageSize int) *[]map[string]interface{} {
-	fs := []string{}
-	vs := []interface{}{}
-	for k, v := range query {
-		rt := reflect.TypeOf(v)
-		rv := reflect.ValueOf(v)
-		if rt.Kind() == reflect.Map {
-			for _, rv_k := range rv.MapKeys() {
-				if rv_k.String() == "ne" {
-					fs = append(fs, fmt.Sprintf("%s!=?", k))
-					vs = append(vs, rv.MapIndex(rv_k).Interface())
-				}
-				if rv_k.String() == "notin" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						for _, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							fs = append(fs, fmt.Sprintf("%s!=?", k))
-							vs = append(vs, v)
-						}
-					}
-				}
-				if rv_k.String() == "in" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						_fs := fmt.Sprintf("%s in (?", k)
-						for k, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							if k > 0 {
-								_fs += ",?"
-							}
-							vs = append(vs, v)
-						}
-						_fs += ")"
-						fs = append(fs, _fs)
-					}
-				}
-			}
-		} else {
-			if v == "$isNull" {
-				fs = append(fs, fmt.Sprintf("%s is null", k))
-			} else if v == "$isNotNull" {
-				fs = append(fs, fmt.Sprintf("%s is not null", k))
-			} else {
-				fs = append(fs, fmt.Sprintf("%s=?", k))
-				vs = append(vs, v)
-			}
-		}
-	}
-	var buffer bytes.Buffer
-	buffer.WriteString("select ")
-	if fields == "" {
-		buffer.WriteString("*")
-	} else {
-		buffer.WriteString(fields)
-	}
-	buffer.WriteString(" from ")
-	buffer.WriteString(tableName)
-	if len(fs) > 0 {
-		buffer.WriteString(" where ")
-		buffer.WriteString(strings.Join(fs, " and "))
-	}
-	if order != "" {
-		buffer.WriteString(" order by ")
-		buffer.WriteString(order)
-	}
-	if start > -1 && pageSize > 0 {
-		buffer.WriteString(" limit ")
-		buffer.WriteString(fmt.Sprint(start))
-		buffer.WriteString(",")
-		buffer.WriteString(fmt.Sprint(pageSize))
-	}
-	q := buffer.String()
-	//log.Println(q, vs)
-	return m.SelectBySql(q, vs...)
-}
-
-//sql语句查询
-func (m *Mysql) SelectBySql(q string, args ...interface{}) *[]map[string]interface{} {
-	return m.SelectBySqlByTx(nil, q, args...)
-}
-func (m *Mysql) SelectBySqlByTx(tx *sql.Tx, q string, args ...interface{}) *[]map[string]interface{} {
-	return m.Select(0, nil, tx, q, args...)
-}
-func (m *Mysql) Select(bath int, f func(l *[]map[string]interface{}), tx *sql.Tx, q string, args ...interface{}) *[]map[string]interface{} {
-	var stmtOut *sql.Stmt
-	var err error
-	if tx == nil {
-		stmtOut, err = m.DB.Prepare(q)
-	} else {
-		stmtOut, err = tx.Prepare(q)
-	}
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	defer stmtOut.Close()
-	rows, err := stmtOut.Query(args...)
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	if rows != nil {
-		defer rows.Close()
-	}
-	columns, err := rows.Columns()
-	if err != nil {
-		log.Println(err)
-		return nil
-	}
-	list := []map[string]interface{}{}
-	for rows.Next() {
-		scanArgs := make([]interface{}, len(columns))
-		values := make([]interface{}, len(columns))
-		ret := make(map[string]interface{})
-		for k, _ := range values {
-			scanArgs[k] = &values[k]
-		}
-		err = rows.Scan(scanArgs...)
-		if err != nil {
-			log.Println(err)
-			break
-		}
-		for i, col := range values {
-			if v, ok := col.([]uint8); ok {
-				ret[columns[i]] = string(v)
-			} else {
-				ret[columns[i]] = col
-			}
-		}
-		list = append(list, ret)
-		if bath > 0 && len(list) == bath {
-			f(&list)
-			list = []map[string]interface{}{}
-		}
-	}
-	if bath > 0 && len(list) > 0 {
-		f(&list)
-		list = []map[string]interface{}{}
-	}
-	return &list
-}
-func (m *Mysql) SelectByBath(bath int, f func(l *[]map[string]interface{}), q string, args ...interface{}) {
-	m.SelectByBathByTx(bath, f, nil, q, args...)
-}
-func (m *Mysql) SelectByBathByTx(bath int, f func(l *[]map[string]interface{}), tx *sql.Tx, q string, args ...interface{}) {
-	m.Select(bath, f, tx, q, args...)
-}
-func (m *Mysql) FindOne(tableName string, query map[string]interface{}, fields, order string) *map[string]interface{} {
-	list := m.Find(tableName, query, fields, order, 0, 1)
-	if list != nil && len(*list) == 1 {
-		temp := (*list)[0]
-		return &temp
-	}
-	return nil
-}
-
-//修改
-func (m *Mysql) Update(tableName string, query, update map[string]interface{}) bool {
-	return m.UpdateByTx(nil, tableName, query, update)
-}
-
-//带事务的修改
-func (m *Mysql) UpdateByTx(tx *sql.Tx, tableName string, query, update map[string]interface{}) bool {
-	q_fs := []string{}
-	u_fs := []string{}
-	values := []interface{}{}
-	for k, v := range update {
-		q_fs = append(q_fs, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	for k, v := range query {
-		u_fs = append(u_fs, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	q := fmt.Sprintf("update %s set %s where %s", tableName, strings.Join(q_fs, ","), strings.Join(u_fs, " and "))
-	log.Println(q, values)
-	return m.UpdateOrDeleteBySqlByTx(tx, q, values...) >= 0
-}
-
-//删除
-func (m *Mysql) Delete(tableName string, query map[string]interface{}) bool {
-	return m.DeleteByTx(nil, tableName, query)
-}
-func (m *Mysql) DeleteByTx(tx *sql.Tx, tableName string, query map[string]interface{}) bool {
-	fields := []string{}
-	values := []interface{}{}
-	for k, v := range query {
-		fields = append(fields, fmt.Sprintf("%s=?", k))
-		values = append(values, v)
-	}
-	q := fmt.Sprintf("delete from %s where %s", tableName, strings.Join(fields, " and "))
-	log.Println(q, values)
-	return m.UpdateOrDeleteBySqlByTx(tx, q, values...) > 0
-}
-
-//修改或删除
-func (m *Mysql) UpdateOrDeleteBySql(q string, args ...interface{}) int64 {
-	return m.UpdateOrDeleteBySqlByTx(nil, q, args...)
-}
-
-//带事务的修改或删除
-func (m *Mysql) UpdateOrDeleteBySqlByTx(tx *sql.Tx, q string, args ...interface{}) int64 {
-	result, err := m.ExecBySqlByTx(tx, q, args...)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	count, err := result.RowsAffected()
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	return count
-}
-
-//总数
-func (m *Mysql) Count(tableName string, query map[string]interface{}) int64 {
-	fields := []string{}
-	values := []interface{}{}
-	for k, v := range query {
-		rt := reflect.TypeOf(v)
-		rv := reflect.ValueOf(v)
-		if rt.Kind() == reflect.Map {
-			for _, rv_k := range rv.MapKeys() {
-				if rv_k.String() == "ne" {
-					fields = append(fields, fmt.Sprintf("%s!=?", k))
-					values = append(values, rv.MapIndex(rv_k).Interface())
-				}
-				if rv_k.String() == "notin" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						for _, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							fields = append(fields, fmt.Sprintf("%s!=?", k))
-							values = append(values, v)
-						}
-					}
-				}
-				if rv_k.String() == "in" {
-					if len(rv.MapIndex(rv_k).Interface().([]interface{})) > 0 {
-						_fs := fmt.Sprintf("%s in (?", k)
-						for k, v := range rv.MapIndex(rv_k).Interface().([]interface{}) {
-							if k > 0 {
-								_fs += ",?"
-							}
-							values = append(values, v)
-						}
-						_fs += ")"
-						fields = append(fields, _fs)
-					}
-				}
-			}
-		} else if v == "$isNull" {
-			fields = append(fields, fmt.Sprintf("%s is null", k))
-		} else if v == "$isNotNull" {
-			fields = append(fields, fmt.Sprintf("%s is not null", k))
-		} else {
-			fields = append(fields, fmt.Sprintf("%s=?", k))
-			values = append(values, v)
-		}
-	}
-	q := fmt.Sprintf("select count(1) as count from %s", tableName)
-	if len(query) > 0 {
-		q += fmt.Sprintf(" where %s", strings.Join(fields, " and "))
-	}
-	log.Println(q, values)
-	return m.CountBySql(q, values...)
-}
-func (m *Mysql) CountBySql(q string, args ...interface{}) int64 {
-	stmtIns, err := m.DB.Prepare(q)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	defer stmtIns.Close()
-
-	rows, err := stmtIns.Query(args...)
-	if err != nil {
-		log.Println(err)
-		return -1
-	}
-	if rows != nil {
-		defer rows.Close()
-	}
-	var count int64 = -1
-	if rows.Next() {
-		err = rows.Scan(&count)
-		if err != nil {
-			log.Println(err)
-		}
-	}
-	return count
-}
-
-//执行事务
-func (m *Mysql) ExecTx(msg string, f func(tx *sql.Tx) bool) bool {
-	tx, err := m.DB.Begin()
-	if err != nil {
-		log.Println(msg, "获取事务错误", err)
-	} else {
-		if f(tx) {
-			if err := tx.Commit(); err != nil {
-				log.Println(msg, "提交事务错误", err)
-			} else {
-				return true
-			}
-		} else {
-			if err := tx.Rollback(); err != nil {
-				log.Println(msg, "事务回滚错误", err)
-			}
-		}
-	}
-	return false
-}
-
-/*************方法命名不规范,上面有替代方法*************/
-func (m *Mysql) Query(query string, args ...interface{}) *[]map[string]interface{} {
-	return m.SelectBySql(query, args...)
-}
-
-func (m *Mysql) QueryCount(query string, args ...interface{}) (count int) {
-	count = -1
-	if !strings.Contains(strings.ToLower(query), "count(*)") {
-		fmt.Println("QueryCount need query like < select count(*) from ..... >")
-		return
-	}
-	count = int(m.CountBySql(query, args...))
-	return
-}

+ 0 - 161
common_utils/protocol.go

@@ -1,161 +0,0 @@
-package util
-
-//底层网络通信协议
-import (
-	"bufio"
-	"bytes"
-	"encoding/binary"
-	"encoding/json"
-	"fmt"
-	"io"
-	"net"
-)
-
-const (
-	EMPTY_ADDR = "00000000"
-)
-
-//读取
-type Reader struct {
-	conn   net.Conn
-	reader *bufio.Reader
-	buffer [4]byte
-}
-
-//数据包,实际上就是协议定义
-type Packet struct {
-	//头开始
-	Length     int32  //4bit 包长度
-	From       string //8bit
-	To         string //8bit
-	Msgid      string //8bit
-	Event      int32  //4bit
-	SentToType int32  //4bit
-	//头结束
-	Raw []byte //数据包,头+数据
-}
-
-//返回
-func (p *Packet) GetBusinessData() []byte {
-	return p.Raw[36:]
-}
-
-//
-type RawData []byte //流数据
-
-//
-func NewReader(c net.Conn) *Reader {
-	return &Reader{
-		conn:   c,
-		reader: bufio.NewReader(c),
-	}
-}
-
-//读取头部
-func (p *Reader) readHeader() (int32, error) {
-	buf := p.buffer[:4]
-	if _, err := io.ReadFull(p.reader, buf); err != nil {
-		return 0, err
-	}
-	size := int32(binary.BigEndian.Uint32(buf))
-	if size < 32 || size > 16384000 {
-		return 0, fmt.Errorf("Incorrect frame size (%d)", size)
-	}
-	return size, nil
-}
-
-//读取完整一帧数据,防止粘包
-func (p *Reader) readFrame(size int32) (*Packet, error) {
-	var buf []byte
-	if int(size) <= len(p.buffer) {
-		buf = p.buffer[0:size]
-	} else {
-		buf = make([]byte, size)
-	}
-	_, err := io.ReadFull(p.reader, buf)
-	raw := append(Int2Byte(size), buf...)
-	if err == nil {
-		//解析包
-		packet := &Packet{
-			Length:     size,
-			From:       string(buf[:8]),
-			To:         string(buf[8:16]),
-			Msgid:      string(buf[16:24]),
-			Event:      Byte2Int(buf[24:28]),
-			SentToType: Byte2Int(buf[28:32]),
-			//Data:       buf[32:],
-			Raw: raw,
-		}
-		return packet, nil
-	}
-	return nil, err
-}
-
-//读取数据写入队列
-func forwardMessage(c net.Conn, queue chan<- *Packet) {
-	defer c.Close()
-	logReader := NewReader(c)
-	for {
-		size, err := logReader.readHeader()
-		if err != nil {
-			break
-		}
-		packet, err := logReader.readFrame(size)
-		if err != nil {
-			break
-		}
-		queue <- packet
-	}
-}
-
-//从队列中读取数据,定期处理
-func processMsg(q <-chan *Packet, parseEvent func(*Packet)) {
-	for {
-		select {
-		case msg := <-q:
-			go parseEvent(msg)
-		}
-	}
-}
-
-//封包,输出直接可以写到流中的数据包
-func Enpacket(from, to, msgid string, event, sendtotype int, obj interface{}) []byte {
-	if len(from) != 8 {
-		from = EMPTY_ADDR
-	}
-	if len(to) != 8 {
-		to = EMPTY_ADDR
-	}
-	if len(msgid) != 8 {
-		msgid = EMPTY_ADDR
-	}
-	var ret []byte
-	var bs []byte
-	if v, ok := obj.([]byte); ok {
-		bs = v
-	} else if v, ok := obj.(string); ok {
-		bs = []byte(v)
-	} else {
-		bs, _ = json.Marshal(obj)
-	}
-	ret = append(Int2Byte(int32(32 + len(bs))))
-	ret = append(ret, []byte(from+to+msgid)...)
-	ret = append(ret, Int2Byte(int32(event))...)
-	ret = append(ret, Int2Byte(int32(sendtotype))...)
-	ret = append(ret, bs...)
-	return ret
-}
-
-//
-func Byte2Int(src []byte) int32 {
-	var ret int32
-	binary.Read(bytes.NewReader(src), binary.BigEndian, &ret)
-	return ret
-}
-
-//
-func Int2Byte(src int32) []byte {
-	buf := bytes.NewBuffer([]byte{})
-	binary.Write(buf, binary.BigEndian, src)
-	return buf.Bytes()
-}

+ 0 - 70
common_utils/redis/redisloginutil.go

@@ -1,70 +0,0 @@
-package redis
-
-import (
-	"log"
-	"strings"
-	"time"
-
-	redisLogin "github.com/gomodule/redigo/redis"
-)
-
-var RedisLoginPool *redisLogin.Pool
-
-func InitRedisLogin(addrs string) {
-	addr := strings.Split(addrs, ",")
-	for _, v := range addr {
-		saddr := strings.Split(v, "=")
-		if saddr[0] == "login" {
-			RedisLoginPool = &redisLogin.Pool{MaxActive: 10, MaxIdle: 5,
-				IdleTimeout: time.Duration(10) * time.Second, Dial: func() (redisLogin.Conn, error) {
-					c, err := redisLogin.Dial("tcp", saddr[1])
-					if err != nil {
-						return nil, err
-					}
-					return c, nil
-				}}
-		}
-	}
-
-}
-
-//
-func SetLoginVal(key, value string) {
-	conn := RedisLoginPool.Get()
-	defer conn.Close()
-	conn.Do("PUBLISH", key, value)
-}
-
-//
-func GetLoginVal(key string, wxFunc func(wxParams []string) bool) {
-	for {
-		defer catch()
-	L:
-		for {
-			conn := RedisLoginPool.Get()
-			defer conn.Close()
-			if conn.Err() == nil {
-				psc := redisLogin.PubSubConn{Conn: conn}
-				if err := psc.Subscribe(redisLogin.Args{}.AddFlat(key)...); err != nil {
-					log.Println(err)
-				}
-				for {
-					msg := psc.Receive()
-					//					go func(msg interface{}) {
-					switch n := msg.(type) {
-					case error:
-						log.Println("wxlogin err", msg)
-						break L
-					case redisLogin.Message:
-						res := string(n.Data)
-						param := strings.Split(res, ",")
-						go wxFunc(param)
-					}
-					//					}(msg)
-				}
-			}
-			time.Sleep(2 * time.Second)
-		}
-		time.Sleep(1 * time.Second)
-	}
-}

+ 0 - 517
common_utils/redis/redisutil.go

@@ -1,517 +0,0 @@
-package redis
-
-import (
-	"encoding/json"
-	"errors"
-	redigo "github.com/gomodule/redigo/redis"
-	"log"
-	"runtime"
-	"strings"
-	"time"
-)
-
-var RedisPool map[string]*redigo.Pool
-
-//初始化redis 1为多个连接池,2为共用一个连接池
-func InitRedis(addrs string) {
-	InitRedisBySize(addrs, 300, 30, 240)
-}
-
-func InitRedisBySize(addrs string, maxSize, maxIdle, timeout int) {
-	RedisPool = map[string]*redigo.Pool{}
-	addr := strings.Split(addrs, ",")
-	for _, v := range addr {
-		saddr := strings.Split(v, "=")
-		RedisPool[saddr[0]] = &redigo.Pool{MaxActive: maxSize, MaxIdle: maxIdle,
-			IdleTimeout: time.Duration(timeout) * time.Second, Dial: func() (redigo.Conn, error) {
-				c, err := redigo.Dial("tcp", saddr[1])
-				if err != nil {
-					return nil, err
-				}
-				return c, nil
-			}}
-	}
-}
-
-//分流redis`
-//并存入字符串缓存
-func PutKV(key string, obj interface{}) bool {
-	return Put("other", key, obj, -1)
-}
-func PutCKV(code, key string, obj interface{}) bool {
-	return Put(code, key, obj, -1)
-}
-func Put(code, key string, obj interface{}, timeout int) bool {
-	b := false
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	var err error
-	_obj, _err := json.Marshal(obj)
-	if _err != nil {
-		log.Println("redisutil-SET-序列化出错Error", _err)
-		return b
-	}
-	if timeout < 1 {
-		_, err = conn.Do("SET", key, _obj)
-	} else {
-		_, err = conn.Do("SET", key, _obj, "EX", timeout)
-	}
-	if nil != err {
-		log.Println("redisutil-SETError-put", err)
-	} else {
-		b = true
-	}
-	return b
-}
-
-func BulkPut(code string, timeout int, obj ...interface{}) bool {
-	b := false
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	var err error
-	for _, _tmp := range obj {
-		tmp, ok := _tmp.([]interface{})
-		if ok && len(tmp) == 2 {
-			key, kok := tmp[0].(string)
-			if kok && key != "" {
-				_obj, _err := json.Marshal(tmp[1])
-				if _err != nil {
-					log.Println("redisutil-SET-序列化出错Error", _err)
-					return b
-				}
-				if timeout < 1 {
-					_, err = conn.Do("SET", key, _obj)
-				} else {
-					_, err = conn.Do("SET", key, _obj, "EX", timeout)
-				}
-			}
-		}
-	}
-	if nil != err {
-		b = false
-		log.Println("redisutil-SETError-put", err)
-	} else {
-		b = b && true
-	}
-	return b
-}
-
-//直接存字节流
-func PutBytes(code, key string, data *[]byte, timeout int) (err error) {
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-
-	if timeout < 1 {
-		_, err = conn.Do("SET", key, *data)
-	} else {
-		_, err = conn.Do("SET", key, *data, "EX", timeout)
-	}
-	if nil != err {
-		log.Println("redisutil-SETError", err)
-	}
-	return
-}
-
-//设置超时时间,单位秒
-func SetExpire(code, key string, expire int) error {
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	_, err := conn.Do("expire", key, expire)
-	return err
-}
-
-//判断一个key是否存在
-func Exists(code, key string) (bool, error) {
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	repl, err := conn.Do("exists", key)
-	ret, _ := redigo.Int(repl, err)
-	return ret == 1, err
-}
-
-//获取string
-func GetStr(code, key string) string {
-	res := Get(code, key)
-	str, _ := res.(string)
-	return str
-}
-
-//获取int
-func GetInt(code, key string) int {
-	result, _ := GetNewInt(code, key)
-	return result
-}
-
-func GetNewInt(code, key string) (int, error) {
-	var res interface{}
-	err := GetNewInterface(code, key, &res)
-	var result int
-	if str, ok := res.(float64); ok {
-		result = int(str)
-	}
-	return result, err
-}
-
-//取得字符串,支持变参,2个 (key,code),返回后自己断言
-func Get(code, key string) (result interface{}) {
-	GetInterface(code, key, &result)
-	return
-}
-
-func GetInterface(code, key string, result interface{}) {
-	GetNewInterface(code, key, result)
-}
-
-func GetNewInterface(code, key string, result interface{}) error {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("GET", key)
-	if nil != err {
-		log.Println("redisutil-GetError", err)
-	} else {
-		var ok bool
-		var res []byte
-		if res, ok = ret.([]byte); ok {
-			err = json.Unmarshal(res, result)
-			if err != nil {
-				log.Println("Get ERROR:", err.Error())
-			}
-		}
-	}
-	return err
-}
-
-//直接返回字节流
-func GetBytes(code, key string) (ret *[]byte, err error) {
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	var r interface{}
-	r, err = conn.Do("GET", key)
-	if err != nil {
-		log.Println("redisutil-GetBytesError", err)
-	} else {
-		if tmp, ok := r.([]byte); ok {
-			ret = &tmp
-		} else {
-			err = errors.New("redis返回数据格式不对")
-		}
-	}
-	return
-}
-func GetNewBytes(code, key string) (ret *[]byte, err error) {
-	defer catch()
-	redisPool := RedisPool[code]
-	if redisPool == nil {
-		err = errors.New("redis code " + code + " is nil")
-		log.Println("redisutil-GetNewBytesError", err)
-		return
-	}
-	conn := redisPool.Get()
-	defer conn.Close()
-	var r interface{}
-	r, err = conn.Do("GET", key)
-	if err != nil {
-		log.Println("redisutil-GetNewBytesError", err)
-	} else if r != nil {
-		if tmp, ok := r.([]byte); ok {
-			ret = &tmp
-		}
-	}
-	return
-}
-
-//删所有key
-func FlushDB(code string) bool {
-	b := false
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-
-	var err error
-	_, err = conn.Do("FLUSHDB")
-	if nil != err {
-		log.Println("redisutil-FLUSHDBError", err)
-	} else {
-		b = true
-	}
-	return b
-}
-
-//支持删除多个key
-func Del(code string, key ...interface{}) bool {
-	defer catch()
-	b := false
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-
-	var err error
-	_, err = conn.Do("DEL", key...)
-	if nil != err {
-		log.Println("redisutil-DELError", err)
-	} else {
-		b = true
-	}
-	return b
-}
-
-/**
-func DelKey(key ...interface{}) {
-	defer func() {
-		if r := recover(); r != nil {
-			log.Println("[E]", r)
-			for skip := 1; ; skip++ {
-				_, file, line, ok := runtime.Caller(skip)
-				if !ok {
-					break
-				}
-				go log.Printf("%v,%v\n", file, line)
-			}
-		}
-	}()
-	for i := 0; i < len(RedisPool); i++ {
-		delByNum(i, key...)
-	}
-
-}
-**/
-
-/**
-func delByNum(n int, key ...interface{}) {
-	defer func() {
-		if r := recover(); r != nil {
-			log.Println("[E]", r)
-			for skip := 1; ; skip++ {
-				_, file, line, ok := runtime.Caller(skip)
-				if !ok {
-					break
-				}
-				go log.Printf("%v,%v\n", file, line)
-			}
-		}
-	}()
-	i := 0
-	for _, v := range RedisPool {
-		if i == n {
-			conn := v.Get()
-			defer conn.Close()
-			conn.Do("DEL", key...)
-			break
-		}
-		i++
-	}
-}
-**/
-
-//根据代码和前辍key删除多个
-func DelByCodePattern(code, key string) {
-	defer catch()
-
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("KEYS", key)
-	var result []interface{}
-	if nil != err {
-		log.Println("redisutil-GetError", err)
-	} else {
-		result = ret.([]interface{})
-		for k := 0; k < len(result); k++ {
-			conn.Do("DEL", string(result[k].([]uint8)))
-		}
-	}
-}
-
-/**
-func DelByPattern(key string) {
-	defer func() {
-		if r := recover(); r != nil {
-			log.Println("[E]", r)
-			for skip := 1; ; skip++ {
-				_, file, line, ok := runtime.Caller(skip)
-				if !ok {
-					break
-				}
-				go log.Printf("%v,%v\n", file, line)
-			}
-		}
-	}()
-	i := 0
-	for _, v := range RedisPool {
-		conn := v.Get()
-		defer conn.Close()
-		ret, err := conn.Do("KEYS", key)
-		var result []interface{}
-		if nil != err {
-			log.Println("redisutil-GetError", err)
-		} else {
-			result = ret.([]interface{})
-			for k := 0; k < len(result); k++ {
-				delByNum(i, string(result[k].([]uint8)))
-			}
-		}
-		i++
-	}
-
-}
-**/
-//自增计数器
-func Incr(code, key string) int64 {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("INCR", key)
-	if nil != err {
-		log.Println("redisutil-INCR-Error", err)
-	} else {
-		if res, ok := ret.(int64); ok {
-			return res
-		} else {
-			return 0
-		}
-	}
-	return 0
-}
-
-//自减
-func Decrby(code, key string, val int) int64 {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("DECRBY", key, val)
-	if nil != err {
-		log.Println("redisutil-DECR-Error", err)
-	} else {
-		if res, ok := ret.(int64); ok {
-			return res
-		} else {
-			return 0
-		}
-	}
-	return 0
-}
-
-//根据正则去取
-func GetKeysByPattern(code, key string) []interface{} {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("KEYS", key)
-	if nil != err {
-		log.Println("redisutil-GetKeysError", err)
-		return nil
-	} else {
-		res, _ := ret.([]interface{})
-		return res
-	}
-}
-
-//批量取多个key
-func Mget(code string, key []string) []interface{} {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	interfaceKeys := make([]interface{}, len(key))
-	for n, k := range key {
-		interfaceKeys[n] = k
-	}
-	ret, err := conn.Do("MGET", interfaceKeys...)
-	if nil != err {
-		log.Println("redisutil-MgetError", err)
-		return nil
-	} else {
-		res, _ := ret.([]interface{})
-		return res
-	}
-}
-
-//取出并删除Key
-func Pop(code string, key string) (result interface{}) {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("GET", key)
-	if nil != err {
-		log.Println("redisutil-PopError", err)
-	} else {
-		var ok bool
-		var res []byte
-		if res, ok = ret.([]byte); ok {
-			err = json.Unmarshal(res, &result)
-			if err != nil {
-				log.Println("Poperr", err)
-			}
-		}
-		conn.Do("DEL", key)
-	}
-	return
-}
-
-//list操作
-func LPOP(code, list string) (result interface{}) {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("LPOP", list)
-	if nil != err {
-		log.Println("redisutil-LPopError", err)
-	} else {
-		if res, ok := ret.([]byte); ok {
-			err = json.Unmarshal(res, &result)
-			log.Println(err)
-		}
-	}
-	return
-}
-
-func RPUSH(code, list string, val interface{}) bool {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	_obj, _ := json.Marshal(val)
-	_, err := conn.Do("RPUSH", list, _obj)
-	if nil != err {
-		log.Println("redisutil-RPUSHError", err)
-		return false
-	}
-	return true
-}
-
-func LLEN(code, list string) int64 {
-	defer catch()
-	conn := RedisPool[code].Get()
-	defer conn.Close()
-	ret, err := conn.Do("LLEN", list)
-	if nil != err {
-		log.Println("redisutil-LLENError", err)
-		return 0
-	}
-	if res, ok := ret.(int64); ok {
-		return res
-	} else {
-		return 0
-	}
-}
-
-func catch() {
-	if r := recover(); r != nil {
-		log.Println(r)
-		for skip := 0; ; skip++ {
-			_, file, line, ok := runtime.Caller(skip)
-			if !ok {
-				break
-			}
-			go log.Printf("%v,%v\n", file, line)
-		}
-	}
-}

+ 0 - 86
common_utils/redis/redisutil_test.go

@@ -1,86 +0,0 @@
-package redis
-
-import (
-	"fmt"
-	"log"
-	"testing"
-	"time"
-)
-
-func Test_redis(t *testing.T) {
-	InitRedis("192.168.3.142:6379,192.168.3.142:7379")
-
-	log.Println(PutKV("key-BBB", "v-oooo"))
-	log.Println(GetStr("", "key-BBB"))
-
-	log.Println(PutCKV("code-K", "key-BBB2", 123))
-	log.Println(GetInt("code-K", "key-BBB2"))
-
-	log.Println(Put("codeA", "BBB", "oooo", 0))
-	//log.Println(Del("codeA", "AAA"))
-	log.Println(GetStr("codeA", "AAA"))
-
-	log.Println(Put("code", "Key", &map[string]string{"name": "张三"}, 0))
-	log.Println(Get("code", "Key"))
-}
-
-func Test_redisMorePut(t *testing.T) {
-	//by := []byte("dddddddddddd555d")
-
-	//InitRedis("enterprise=192.168.3.14:1379,service=192.168.3.14:2379,other=192.168.3.14:3379")
-	InitRedis("sso=192.168.3.14:1379")
-	//PutBytes("enterprise", "A", &by, 0)
-	//Put("sso", "new_1070776706", "obEpLuMMDUYUM-zlzCbQ0MbuQOzc", 180)
-	Put("sso", "1903540616", "oJULtwzXo6EFV1Ah-XeyRBimXGM8", 180)
-	//log.Println(Get("enterprise", "A"))
-	//GetMoreKey("ent*")
-}
-
-func Test_other(t *testing.T) {
-	//s := `[{"S_remark":"kokopkopkop","s_pic":"/upload/2015/10/16/2015101611194101018681.jpg","o_extend":{"k1":"ioio","k7":"000"}}]`
-	//mo := []map[string]interface{}{}
-	//json.Unmarshal([]byte(s), &mo)
-	//log.Println(mo)
-
-	pools := make(chan bool, 1)
-	pool := make(chan bool, 2)
-	for i := 0; i < 1000; i++ {
-		go func(i int) {
-			pool <- true
-			defer func() {
-				<-pool
-			}()
-			log.Println("--", i)
-			time.Sleep(5 * time.Millisecond)
-
-		}(i)
-	}
-	<-pools
-}
-
-func TestIncr(t *testing.T) {
-	InitRedis("other=192.168.3.14:1379")
-	//log.Println(GetBytes("sso", "p_share_3200000006"))
-	Put("other", "test", "12212212", 50000)
-}
-
-func Test_Pop(t *testing.T) {
-	InitRedis("sso=192.168.3.207:1601")
-	m := "aaaa"
-	Put("sso", "aaa", m, 1000)
-	log.Println(Pop("sso", "aaa"))
-}
-
-func Test_MGET(t *testing.T) {
-	InitRedis("sso=192.168.3.207:3378")
-	InitRedis("sso=192.168.3.207:1711")
-	n := 0
-	for {
-		n++
-		Put("sso", fmt.Sprintf("%d_1", n), n, 3600)
-		time.Sleep(8 * time.Second)
-
-	}
-	res := Mget("sso", []string{"pn_金业街(西自由街-虎泉路)道路建设工程"})
-	log.Println(res)
-}

+ 0 - 135
common_utils/simple_encrypt.go

@@ -1,135 +0,0 @@
-package util
-
-import (
-	"bytes"
-	"encoding/base64"
-	"encoding/hex"
-)
-
-/**
-加解密
-	数据结构
-	密文+sha32校验
-*/
-//
-type SimpleEncrypt struct {
-	Key string //加解密用到的key(加密key索引)+
-}
-
-//计算检验和
-func (s *SimpleEncrypt) calaCheckCode(src []byte) []byte {
-	check := 0
-	for i := 0; i < len(src); i++ {
-		check += int(src[i])
-	}
-	return []byte{byte((check >> 8) & 0xff), byte(check & 0xff)}
-}
-
-//验证数据有效性
-func (s *SimpleEncrypt) verify(src []byte) bool {
-	v := s.calaCheckCode(src[:len(src)-2])
-	return bytes.Equal(v, src[len(src)-2:])
-}
-
-//加密String
-func (s *SimpleEncrypt) EncodeString(str string) string {
-	data := []byte(str)
-	s.doEncode(data)
-	return base64.StdEncoding.EncodeToString(data)
-}
-
-//加密String,ByCheck
-func (s *SimpleEncrypt) EncodeStringByCheck(str string) string {
-	data := []byte(str)
-	s.doEncode(data)
-	v := s.calaCheckCode(data)
-	data = append(data, v...)
-	return base64.StdEncoding.EncodeToString(data)
-}
-
-//
-func (s *SimpleEncrypt) Encode2Hex(str string) string {
-	data := []byte(str)
-	s.doEncode(data)
-	return hex.EncodeToString(data)
-}
-func (s *SimpleEncrypt) Encode2HexByCheck(str string) string {
-	data := []byte(str)
-	s.doEncode(data)
-	v := s.calaCheckCode(data)
-	data = append(data, v...)
-	return hex.EncodeToString(data)
-}
-
-//解密String
-func (s *SimpleEncrypt) DecodeString(str string) string {
-	data, _ := base64.StdEncoding.DecodeString(str)
-	s.doEncode(data)
-	return string(data)
-}
-
-//解密String,ByCheck
-func (s *SimpleEncrypt) DecodeStringByCheck(str string) string {
-	data, _ := base64.StdEncoding.DecodeString(str)
-	if len(data) < 2 || !s.verify(data) {
-		return ""
-	}
-	data = data[:len(data)-2]
-	s.doEncode(data)
-	return string(data)
-}
-
-//
-func (s *SimpleEncrypt) Decode4Hex(str string) string {
-	data, _ := hex.DecodeString(str)
-	s.doEncode(data)
-	return string(data)
-}
-func (s *SimpleEncrypt) Decode4HexByCheck(str string) string {
-	data, _ := hex.DecodeString(str)
-	if len(data) < 2 || !s.verify(data) {
-		return ""
-	}
-	data = data[:len(data)-2]
-	s.doEncode(data)
-	return string(data)
-}
-
-//加密
-func (s *SimpleEncrypt) Encode(data []byte) {
-	s.doEncode(data)
-
-}
-
-func (s *SimpleEncrypt) EncodeByCheck(data []byte) {
-	s.doEncode(data)
-	v := s.calaCheckCode(data)
-	data = append(data, v...)
-}
-
-//解密
-func (s *SimpleEncrypt) Decode(data []byte) {
-	s.doEncode(data)
-}
-
-//解密
-func (s *SimpleEncrypt) DecodeByCheck(data []byte) {
-	if len(data) < 2 || !s.verify(data) {
-		data = []byte{}
-		return
-	}
-	s.doEncode(data)
-}
-
-func (s *SimpleEncrypt) doEncode(bs []byte) {
-	tmp := []byte(s.Key)
-THEFOR:
-	for i := 0; i < len(bs); {
-		for j := 0; j < len(tmp); j, i = j+1, i+1 {
-			if i >= len(bs) {
-				break THEFOR
-			}
-			bs[i] = bs[i] ^ tmp[j]
-		}
-	}
-}

+ 0 - 78
common_utils/udp.go

@@ -1,78 +0,0 @@
-package util
-
-import (
-	"bytes"
-	"net"
-	"time"
-)
-
-//
-type UdpClient struct {
-	Local   string
-	Connect *net.UDPConn
-	BufSize int
-}
-
-//指令
-const (
-	OP_NOOP = byte(iota)
-	OP_JOIN
-	OP_BYE
-	OP_SAY_ONLINE
-	OP_TYPE_DATA
-	OP_GET_DOWNLOADERCODE     //上报下载器代码
-	OP_WILLCHANGEIP           //将要切换IP
-	OP_PUSH_DOWNLOADERCODES   //
-	OP_DELETE_DOWNLOADERCODES //需要删除
-	OP_SEND_EMAIL             //发送邮件
-)
-
-//
-func (c *UdpClient) Listen(fn func(byte, []byte, *net.UDPAddr)) {
-	listenAddr, _ := net.ResolveUDPAddr("udp4", c.Local)
-	c.Connect, _ = net.ListenUDP("udp4", listenAddr)
-	go c.readUdp(fn)
-}
-
-//写
-func (c *UdpClient) WriteUdp(data []byte /*写入数据*/, act byte /*动作*/, toaddr *net.UDPAddr /*目标端地址*/) error {
-	bs := make([]byte, 1)
-	bs[0] = act
-	sizebs := Int2Byte(int32(len(data)))
-	bs = append(bs, sizebs...)
-	bs = append(bs, data...)
-	if len(bs) > c.BufSize {
-		bs = bs[:c.BufSize]
-	} else if len(bs) < c.BufSize {
-		bs = append(bs, bytes.Repeat([]byte{0}, c.BufSize-len(bs))...)
-	}
-	for i := 0; i < 5; i++ { //尝试5次
-		_, err := c.Connect.WriteToUDP(bs, toaddr)
-		if err == nil {
-			break
-		}
-		time.Sleep(1 * time.Second)
-	}
-	return nil
-}
-
-//读
-func (c *UdpClient) readUdp(fn func(byte, []byte, *net.UDPAddr)) {
-	for {
-		head := make([]byte, c.BufSize)
-		n, ra, err := c.Connect.ReadFromUDP(head)
-		if err != nil || n == 0 { //取不到数据
-			time.Sleep(1 * time.Second)
-			continue
-		}
-		size := int(Byte2Int(head[1:5]))
-		if size < 1 { //无数据,仅仅是控制指令
-			go fn(head[0], []byte{}, ra)
-		} else {
-			if size > c.BufSize-5 {
-				size = c.BufSize - 5
-			}
-			go fn(head[0], head[5:5+size], ra)
-		}
-	}
-}

+ 0 - 64
common_utils/validator/converter.go

@@ -1,64 +0,0 @@
-package govalidator
-
-import (
-	"encoding/json"
-	"fmt"
-	"reflect"
-	"strconv"
-)
-
-// ToString convert the input to a string.
-func ToString(obj interface{}) string {
-	res := fmt.Sprintf("%v", obj)
-	return res
-}
-
-// ToJSON convert the input to a valid JSON string
-func ToJSON(obj interface{}) (string, error) {
-	res, err := json.Marshal(obj)
-	if err != nil {
-		res = []byte("")
-	}
-	return string(res), err
-}
-
-// ToFloat convert the input string to a float, or 0.0 if the input is not a float.
-func ToFloat(str string) (float64, error) {
-	res, err := strconv.ParseFloat(str, 64)
-	if err != nil {
-		res = 0.0
-	}
-	return res, err
-}
-
-// ToInt convert the input string or any int type to an integer type 64, or 0 if the input is not an integer.
-func ToInt(value interface{}) (res int64, err error) {
-	val := reflect.ValueOf(value)
-
-	switch value.(type) {
-	case int, int8, int16, int32, int64:
-		res = val.Int()
-	case uint, uint8, uint16, uint32, uint64:
-		res = int64(val.Uint())
-	case string:
-		if IsInt(val.String()) {
-			res, err = strconv.ParseInt(val.String(), 0, 64)
-			if err != nil {
-				res = 0
-			}
-		} else {
-			err = fmt.Errorf("ToInt: invalid numeric format %g", value)
-			res = 0
-		}
-	default:
-		err = fmt.Errorf("ToInt: unknown interface type %T", value)
-		res = 0
-	}
-
-	return
-}
-
-// ToBoolean convert the input string to a boolean.
-func ToBoolean(str string) (bool, error) {
-	return strconv.ParseBool(str)
-}

+ 0 - 47
common_utils/validator/error.go

@@ -1,47 +0,0 @@
-package govalidator
-
-import (
-	"sort"
-	"strings"
-)
-
-// Errors is an array of multiple errors and conforms to the error interface.
-type Errors []error
-
-// Errors returns itself.
-func (es Errors) Errors() []error {
-	return es
-}
-
-func (es Errors) Error() string {
-	var errs []string
-	for _, e := range es {
-		errs = append(errs, e.Error())
-	}
-	sort.Strings(errs)
-	return strings.Join(errs, ";")
-}
-
-// Error encapsulates a name, an error and whether there's a custom error message or not.
-type Error struct {
-	Name                     string
-	Err                      error
-	CustomErrorMessageExists bool
-
-	// Validator indicates the name of the validator that failed
-	Validator string
-	Path      []string
-}
-
-func (e Error) Error() string {
-	if e.CustomErrorMessageExists {
-		return e.Err.Error()
-	}
-
-	errName := e.Name
-	if len(e.Path) > 0 {
-		errName = strings.Join(append(e.Path, e.Name), ".")
-	}
-
-	return errName + ": " + e.Err.Error()
-}

+ 0 - 96
common_utils/validator/numerics.go

@@ -1,96 +0,0 @@
-package govalidator
-
-import (
-	"math"
-)
-
-// Abs returns absolute value of number
-func Abs(value float64) float64 {
-	return math.Abs(value)
-}
-
-// Sign returns signum of number: 1 in case of value > 0, -1 in case of value < 0, 0 otherwise
-func Sign(value float64) float64 {
-	if value > 0 {
-		return 1
-	} else if value < 0 {
-		return -1
-	} else {
-		return 0
-	}
-}
-
-// IsNegative returns true if value < 0
-func IsNegative(value float64) bool {
-	return value < 0
-}
-
-// IsPositive returns true if value > 0
-func IsPositive(value float64) bool {
-	return value > 0
-}
-
-// IsNonNegative returns true if value >= 0
-func IsNonNegative(value float64) bool {
-	return value >= 0
-}
-
-// IsNonPositive returns true if value <= 0
-func IsNonPositive(value float64) bool {
-	return value <= 0
-}
-
-// InRangeInt returns true if value lies between left and right border
-func InRangeInt(value, left, right interface{}) bool {
-	value64, _ := ToInt(value)
-	left64, _ := ToInt(left)
-	right64, _ := ToInt(right)
-	if left64 > right64 {
-		left64, right64 = right64, left64
-	}
-	return value64 >= left64 && value64 <= right64
-}
-
-// InRangeFloat32 returns true if value lies between left and right border
-func InRangeFloat32(value, left, right float32) bool {
-	if left > right {
-		left, right = right, left
-	}
-	return value >= left && value <= right
-}
-
-// InRangeFloat64 returns true if value lies between left and right border
-func InRangeFloat64(value, left, right float64) bool {
-	if left > right {
-		left, right = right, left
-	}
-	return value >= left && value <= right
-}
-
-// InRange returns true if value lies between left and right border, generic type to handle int, float32, float64 and string.
-// All types must the same type.
-// False if value doesn't lie in range or if it incompatible or not comparable
-func InRange(value interface{}, left interface{}, right interface{}) bool {
-	switch value.(type) {
-	case int:
-		return InRangeInt(value.(int), left.(int), right.(int))
-	case float32:
-		return InRangeFloat32(value.(float32), left.(float32), right.(float32))
-	case float64:
-		return InRangeFloat64(value.(float64), left.(float64), right.(float64))
-	case string:
-		return value.(string) >= left.(string) && value.(string) <= right.(string)
-	default:
-		return false
-	}
-}
-
-// IsWhole returns true if value is whole number
-func IsWhole(value float64) bool {
-	return math.Remainder(value, 1) == 0
-}
-
-// IsNatural returns true if value is natural number (positive and whole)
-func IsNatural(value float64) bool {
-	return IsWhole(value) && IsPositive(value)
-}

+ 0 - 107
common_utils/validator/patterns.go

@@ -1,107 +0,0 @@
-package govalidator
-
-import "regexp"
-
-// Basic regular expressions for validating strings
-const (
-	Email             string = "^(((([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+(\\.([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+)*)|((\\x22)((((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(([\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f]|\\x21|[\\x23-\\x5b]|[\\x5d-\\x7e]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(\\([\\x01-\\x09\\x0b\\x0c\\x0d-\\x7f]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}]))))*(((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(\\x22)))@((([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|\\.|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.)+(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.?$"
-	CreditCard        string = "^(?:4[0-9]{12}(?:[0-9]{3})?|5[1-5][0-9]{14}|(222[1-9]|22[3-9][0-9]|2[3-6][0-9]{2}|27[01][0-9]|2720)[0-9]{12}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11}|6[27][0-9]{14})$"
-	ISBN10            string = "^(?:[0-9]{9}X|[0-9]{10})$"
-	ISBN13            string = "^(?:[0-9]{13})$"
-	UUID3             string = "^[0-9a-f]{8}-[0-9a-f]{4}-3[0-9a-f]{3}-[0-9a-f]{4}-[0-9a-f]{12}$"
-	UUID4             string = "^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$"
-	UUID5             string = "^[0-9a-f]{8}-[0-9a-f]{4}-5[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$"
-	UUID              string = "^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$"
-	Alpha             string = "^[a-zA-Z]+$"
-	Alphanumeric      string = "^[a-zA-Z0-9]+$"
-	Numeric           string = "^[0-9]+$"
-	Int               string = "^(?:[-+]?(?:0|[1-9][0-9]*))$"
-	Float             string = "^(?:[-+]?(?:[0-9]+))?(?:\\.[0-9]*)?(?:[eE][\\+\\-]?(?:[0-9]+))?$"
-	Hexadecimal       string = "^[0-9a-fA-F]+$"
-	Hexcolor          string = "^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$"
-	RGBcolor          string = "^rgb\\(\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*\\)$"
-	ASCII             string = "^[\x00-\x7F]+$"
-	Multibyte         string = "[^\x00-\x7F]"
-	FullWidth         string = "[^\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]"
-	HalfWidth         string = "[\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]"
-	Base64            string = "^(?:[A-Za-z0-9+\\/]{4})*(?:[A-Za-z0-9+\\/]{2}==|[A-Za-z0-9+\\/]{3}=|[A-Za-z0-9+\\/]{4})$"
-	PrintableASCII    string = "^[\x20-\x7E]+$"
-	DataURI           string = "^data:.+\\/(.+);base64$"
-	MagnetURI         string = "^magnet:\\?xt=urn:[a-zA-Z0-9]+:[a-zA-Z0-9]{32,40}&dn=.+&tr=.+$"
-	Latitude          string = "^[-+]?([1-8]?\\d(\\.\\d+)?|90(\\.0+)?)$"
-	Longitude         string = "^[-+]?(180(\\.0+)?|((1[0-7]\\d)|([1-9]?\\d))(\\.\\d+)?)$"
-	DNSName           string = `^([a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62}){1}(\.[a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62})*[\._]?$`
-	IP                string = `(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:)|fe80:(:[0-9a-fA-F]{0,4}){0,4}%[0-9a-zA-Z]{1,}|::(ffff(:0{1,4}){0,1}:){0,1}((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])|([0-9a-fA-F]{1,4}:){1,4}:((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]))`
-	URLSchema         string = `((ftp|tcp|udp|wss?|https?):\/\/)`
-	URLUsername       string = `(\S+(:\S*)?@)`
-	URLPath           string = `((\/|\?|#)[^\s]*)`
-	URLPort           string = `(:(\d{1,5}))`
-	URLIP             string = `([1-9]\d?|1\d\d|2[01]\d|22[0-3]|24\d|25[0-5])(\.(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])){2}(?:\.([0-9]\d?|1\d\d|2[0-4]\d|25[0-5]))`
-	URLSubdomain      string = `((www\.)|([a-zA-Z0-9]+([-_\.]?[a-zA-Z0-9])*[a-zA-Z0-9]\.[a-zA-Z0-9]+))`
-	URL                      = `^` + URLSchema + `?` + URLUsername + `?` + `((` + URLIP + `|(\[` + IP + `\])|(([a-zA-Z0-9]([a-zA-Z0-9-_]+)?[a-zA-Z0-9]([-\.][a-zA-Z0-9]+)*)|(` + URLSubdomain + `?))?(([a-zA-Z\x{00a1}-\x{ffff}0-9]+-?-?)*[a-zA-Z\x{00a1}-\x{ffff}0-9]+)(?:\.([a-zA-Z\x{00a1}-\x{ffff}]{1,}))?))\.?` + URLPort + `?` + URLPath + `?$`
-	SSN               string = `^\d{3}[- ]?\d{2}[- ]?\d{4}$`
-	WinPath           string = `^[a-zA-Z]:\\(?:[^\\/:*?"<>|\r\n]+\\)*[^\\/:*?"<>|\r\n]*$`
-	UnixPath          string = `^(/[^/\x00]*)+/?$`
-	Semver            string = "^v?(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)(-(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*)(\\.(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*))*)?(\\+[0-9a-zA-Z-]+(\\.[0-9a-zA-Z-]+)*)?$"
-	tagName           string = "valid"
-	hasLowerCase      string = ".*[[:lower:]]"
-	hasUpperCase      string = ".*[[:upper:]]"
-	hasWhitespace     string = ".*[[:space:]]"
-	hasWhitespaceOnly string = "^[[:space:]]+$"
-	IMEI              string = "^[0-9a-f]{14}$|^\\d{15}$|^\\d{18}$"
-	IMSI              string = "^\\d{14,15}$"
-)
-
-// Used by IsFilePath func
-const (
-	// Unknown is unresolved OS type
-	Unknown = iota
-	// Win is Windows type
-	Win
-	// Unix is *nix OS types
-	Unix
-)
-
-var (
-	userRegexp          = regexp.MustCompile("^[a-zA-Z0-9!#$%&'*+/=?^_`{|}~.-]+$")
-	hostRegexp          = regexp.MustCompile("^[^\\s]+\\.[^\\s]+$")
-	userDotRegexp       = regexp.MustCompile("(^[.]{1})|([.]{1}$)|([.]{2,})")
-	rxEmail             = regexp.MustCompile(Email)
-	rxCreditCard        = regexp.MustCompile(CreditCard)
-	rxISBN10            = regexp.MustCompile(ISBN10)
-	rxISBN13            = regexp.MustCompile(ISBN13)
-	rxUUID3             = regexp.MustCompile(UUID3)
-	rxUUID4             = regexp.MustCompile(UUID4)
-	rxUUID5             = regexp.MustCompile(UUID5)
-	rxUUID              = regexp.MustCompile(UUID)
-	rxAlpha             = regexp.MustCompile(Alpha)
-	rxAlphanumeric      = regexp.MustCompile(Alphanumeric)
-	rxNumeric           = regexp.MustCompile(Numeric)
-	rxInt               = regexp.MustCompile(Int)
-	rxFloat             = regexp.MustCompile(Float)
-	rxHexadecimal       = regexp.MustCompile(Hexadecimal)
-	rxHexcolor          = regexp.MustCompile(Hexcolor)
-	rxRGBcolor          = regexp.MustCompile(RGBcolor)
-	rxASCII             = regexp.MustCompile(ASCII)
-	rxPrintableASCII    = regexp.MustCompile(PrintableASCII)
-	rxMultibyte         = regexp.MustCompile(Multibyte)
-	rxFullWidth         = regexp.MustCompile(FullWidth)
-	rxHalfWidth         = regexp.MustCompile(HalfWidth)
-	rxBase64            = regexp.MustCompile(Base64)
-	rxDataURI           = regexp.MustCompile(DataURI)
-	rxMagnetURI         = regexp.MustCompile(MagnetURI)
-	rxLatitude          = regexp.MustCompile(Latitude)
-	rxLongitude         = regexp.MustCompile(Longitude)
-	rxDNSName           = regexp.MustCompile(DNSName)
-	rxURL               = regexp.MustCompile(URL)
-	rxSSN               = regexp.MustCompile(SSN)
-	rxWinPath           = regexp.MustCompile(WinPath)
-	rxUnixPath          = regexp.MustCompile(UnixPath)
-	rxSemver            = regexp.MustCompile(Semver)
-	rxHasLowerCase      = regexp.MustCompile(hasLowerCase)
-	rxHasUpperCase      = regexp.MustCompile(hasUpperCase)
-	rxHasWhitespace     = regexp.MustCompile(hasWhitespace)
-	rxHasWhitespaceOnly = regexp.MustCompile(hasWhitespaceOnly)
-	rxIMEI              = regexp.MustCompile(IMEI)
-	rxIMSI              = regexp.MustCompile(IMSI)
-)

+ 0 - 655
common_utils/validator/types.go

@@ -1,655 +0,0 @@
-package govalidator
-
-import (
-	"reflect"
-	"regexp"
-	"sort"
-	"sync"
-)
-
-// Validator is a wrapper for a validator function that returns bool and accepts string.
-type Validator func(str string) bool
-
-// CustomTypeValidator is a wrapper for validator functions that returns bool and accepts any type.
-// The second parameter should be the context (in the case of validating a struct: the whole object being validated).
-type CustomTypeValidator func(i interface{}, o interface{}) bool
-
-// ParamValidator is a wrapper for validator functions that accept additional parameters.
-type ParamValidator func(str string, params ...string) bool
-
-// InterfaceParamValidator is a wrapper for functions that accept variants parameters for an interface value
-type InterfaceParamValidator func(in interface{}, params ...string) bool
-type tagOptionsMap map[string]tagOption
-
-func (t tagOptionsMap) orderedKeys() []string {
-	var keys []string
-	for k := range t {
-		keys = append(keys, k)
-	}
-
-	sort.Slice(keys, func(a, b int) bool {
-		return t[keys[a]].order < t[keys[b]].order
-	})
-
-	return keys
-}
-
-type tagOption struct {
-	name               string
-	customErrorMessage string
-	order              int
-}
-
-// UnsupportedTypeError is a wrapper for reflect.Type
-type UnsupportedTypeError struct {
-	Type reflect.Type
-}
-
-// stringValues is a slice of reflect.Value holding *reflect.StringValue.
-// It implements the methods to sort by string.
-type stringValues []reflect.Value
-
-// InterfaceParamTagMap is a map of functions accept variants parameters for an interface value
-var InterfaceParamTagMap = map[string]InterfaceParamValidator{
-	"type": IsType,
-}
-
-// InterfaceParamTagRegexMap maps interface param tags to their respective regexes.
-var InterfaceParamTagRegexMap = map[string]*regexp.Regexp{
-	"type": regexp.MustCompile(`^type\((.*)\)$`),
-}
-
-// ParamTagMap is a map of functions accept variants parameters
-var ParamTagMap = map[string]ParamValidator{
-	"length":          ByteLength,
-	"range":           Range,
-	"runelength":      RuneLength,
-	"stringlength":    StringLength,
-	"matches":         StringMatches,
-	"in":              IsInRaw,
-	"rsapub":          IsRsaPub,
-	"minstringlength": MinStringLength,
-	"maxstringlength": MaxStringLength,
-}
-
-// ParamTagRegexMap maps param tags to their respective regexes.
-var ParamTagRegexMap = map[string]*regexp.Regexp{
-	"range":           regexp.MustCompile("^range\\((\\d+)\\|(\\d+)\\)$"),
-	"length":          regexp.MustCompile("^length\\((\\d+)\\|(\\d+)\\)$"),
-	"runelength":      regexp.MustCompile("^runelength\\((\\d+)\\|(\\d+)\\)$"),
-	"stringlength":    regexp.MustCompile("^stringlength\\((\\d+)\\|(\\d+)\\)$"),
-	"in":              regexp.MustCompile(`^in\((.*)\)`),
-	"matches":         regexp.MustCompile(`^matches\((.+)\)$`),
-	"rsapub":          regexp.MustCompile("^rsapub\\((\\d+)\\)$"),
-	"minstringlength": regexp.MustCompile("^minstringlength\\((\\d+)\\)$"),
-	"maxstringlength": regexp.MustCompile("^maxstringlength\\((\\d+)\\)$"),
-}
-
-type customTypeTagMap struct {
-	validators map[string]CustomTypeValidator
-
-	sync.RWMutex
-}
-
-func (tm *customTypeTagMap) Get(name string) (CustomTypeValidator, bool) {
-	tm.RLock()
-	defer tm.RUnlock()
-	v, ok := tm.validators[name]
-	return v, ok
-}
-
-func (tm *customTypeTagMap) Set(name string, ctv CustomTypeValidator) {
-	tm.Lock()
-	defer tm.Unlock()
-	tm.validators[name] = ctv
-}
-
-// CustomTypeTagMap is a map of functions that can be used as tags for ValidateStruct function.
-// Use this to validate compound or custom types that need to be handled as a whole, e.g.
-// `type UUID [16]byte` (this would be handled as an array of bytes).
-var CustomTypeTagMap = &customTypeTagMap{validators: make(map[string]CustomTypeValidator)}
-
-// TagMap is a map of functions, that can be used as tags for ValidateStruct function.
-var TagMap = map[string]Validator{
-	"email":              IsEmail,
-	"url":                IsURL,
-	"dialstring":         IsDialString,
-	"requrl":             IsRequestURL,
-	"requri":             IsRequestURI,
-	"alpha":              IsAlpha,
-	"utfletter":          IsUTFLetter,
-	"alphanum":           IsAlphanumeric,
-	"utfletternum":       IsUTFLetterNumeric,
-	"numeric":            IsNumeric,
-	"utfnumeric":         IsUTFNumeric,
-	"utfdigit":           IsUTFDigit,
-	"hexadecimal":        IsHexadecimal,
-	"hexcolor":           IsHexcolor,
-	"rgbcolor":           IsRGBcolor,
-	"lowercase":          IsLowerCase,
-	"uppercase":          IsUpperCase,
-	"int":                IsInt,
-	"float":              IsFloat,
-	"null":               IsNull,
-	"notnull":            IsNotNull,
-	"uuid":               IsUUID,
-	"uuidv3":             IsUUIDv3,
-	"uuidv4":             IsUUIDv4,
-	"uuidv5":             IsUUIDv5,
-	"creditcard":         IsCreditCard,
-	"isbn10":             IsISBN10,
-	"isbn13":             IsISBN13,
-	"json":               IsJSON,
-	"multibyte":          IsMultibyte,
-	"ascii":              IsASCII,
-	"printableascii":     IsPrintableASCII,
-	"fullwidth":          IsFullWidth,
-	"halfwidth":          IsHalfWidth,
-	"variablewidth":      IsVariableWidth,
-	"base64":             IsBase64,
-	"datauri":            IsDataURI,
-	"ip":                 IsIP,
-	"port":               IsPort,
-	"ipv4":               IsIPv4,
-	"ipv6":               IsIPv6,
-	"dns":                IsDNSName,
-	"host":               IsHost,
-	"mac":                IsMAC,
-	"latitude":           IsLatitude,
-	"longitude":          IsLongitude,
-	"ssn":                IsSSN,
-	"semver":             IsSemver,
-	"rfc3339":            IsRFC3339,
-	"rfc3339WithoutZone": IsRFC3339WithoutZone,
-	"ISO3166Alpha2":      IsISO3166Alpha2,
-	"ISO3166Alpha3":      IsISO3166Alpha3,
-	"ISO4217":            IsISO4217,
-	"IMEI":               IsIMEI,
-}
-
-// ISO3166Entry stores country codes
-type ISO3166Entry struct {
-	EnglishShortName string
-	FrenchShortName  string
-	Alpha2Code       string
-	Alpha3Code       string
-	Numeric          string
-}
-
-//ISO3166List based on https://www.iso.org/obp/ui/#search/code/ Code Type "Officially Assigned Codes"
-var ISO3166List = []ISO3166Entry{
-	{"Afghanistan", "Afghanistan (l')", "AF", "AFG", "004"},
-	{"Albania", "Albanie (l')", "AL", "ALB", "008"},
-	{"Antarctica", "Antarctique (l')", "AQ", "ATA", "010"},
-	{"Algeria", "Algérie (l')", "DZ", "DZA", "012"},
-	{"American Samoa", "Samoa américaines (les)", "AS", "ASM", "016"},
-	{"Andorra", "Andorre (l')", "AD", "AND", "020"},
-	{"Angola", "Angola (l')", "AO", "AGO", "024"},
-	{"Antigua and Barbuda", "Antigua-et-Barbuda", "AG", "ATG", "028"},
-	{"Azerbaijan", "Azerbaïdjan (l')", "AZ", "AZE", "031"},
-	{"Argentina", "Argentine (l')", "AR", "ARG", "032"},
-	{"Australia", "Australie (l')", "AU", "AUS", "036"},
-	{"Austria", "Autriche (l')", "AT", "AUT", "040"},
-	{"Bahamas (the)", "Bahamas (les)", "BS", "BHS", "044"},
-	{"Bahrain", "Bahreïn", "BH", "BHR", "048"},
-	{"Bangladesh", "Bangladesh (le)", "BD", "BGD", "050"},
-	{"Armenia", "Arménie (l')", "AM", "ARM", "051"},
-	{"Barbados", "Barbade (la)", "BB", "BRB", "052"},
-	{"Belgium", "Belgique (la)", "BE", "BEL", "056"},
-	{"Bermuda", "Bermudes (les)", "BM", "BMU", "060"},
-	{"Bhutan", "Bhoutan (le)", "BT", "BTN", "064"},
-	{"Bolivia (Plurinational State of)", "Bolivie (État plurinational de)", "BO", "BOL", "068"},
-	{"Bosnia and Herzegovina", "Bosnie-Herzégovine (la)", "BA", "BIH", "070"},
-	{"Botswana", "Botswana (le)", "BW", "BWA", "072"},
-	{"Bouvet Island", "Bouvet (l'Île)", "BV", "BVT", "074"},
-	{"Brazil", "Brésil (le)", "BR", "BRA", "076"},
-	{"Belize", "Belize (le)", "BZ", "BLZ", "084"},
-	{"British Indian Ocean Territory (the)", "Indien (le Territoire britannique de l'océan)", "IO", "IOT", "086"},
-	{"Solomon Islands", "Salomon (Îles)", "SB", "SLB", "090"},
-	{"Virgin Islands (British)", "Vierges britanniques (les Îles)", "VG", "VGB", "092"},
-	{"Brunei Darussalam", "Brunéi Darussalam (le)", "BN", "BRN", "096"},
-	{"Bulgaria", "Bulgarie (la)", "BG", "BGR", "100"},
-	{"Myanmar", "Myanmar (le)", "MM", "MMR", "104"},
-	{"Burundi", "Burundi (le)", "BI", "BDI", "108"},
-	{"Belarus", "Bélarus (le)", "BY", "BLR", "112"},
-	{"Cambodia", "Cambodge (le)", "KH", "KHM", "116"},
-	{"Cameroon", "Cameroun (le)", "CM", "CMR", "120"},
-	{"Canada", "Canada (le)", "CA", "CAN", "124"},
-	{"Cabo Verde", "Cabo Verde", "CV", "CPV", "132"},
-	{"Cayman Islands (the)", "Caïmans (les Îles)", "KY", "CYM", "136"},
-	{"Central African Republic (the)", "République centrafricaine (la)", "CF", "CAF", "140"},
-	{"Sri Lanka", "Sri Lanka", "LK", "LKA", "144"},
-	{"Chad", "Tchad (le)", "TD", "TCD", "148"},
-	{"Chile", "Chili (le)", "CL", "CHL", "152"},
-	{"China", "Chine (la)", "CN", "CHN", "156"},
-	{"Taiwan (Province of China)", "Taïwan (Province de Chine)", "TW", "TWN", "158"},
-	{"Christmas Island", "Christmas (l'Île)", "CX", "CXR", "162"},
-	{"Cocos (Keeling) Islands (the)", "Cocos (les Îles)/ Keeling (les Îles)", "CC", "CCK", "166"},
-	{"Colombia", "Colombie (la)", "CO", "COL", "170"},
-	{"Comoros (the)", "Comores (les)", "KM", "COM", "174"},
-	{"Mayotte", "Mayotte", "YT", "MYT", "175"},
-	{"Congo (the)", "Congo (le)", "CG", "COG", "178"},
-	{"Congo (the Democratic Republic of the)", "Congo (la République démocratique du)", "CD", "COD", "180"},
-	{"Cook Islands (the)", "Cook (les Îles)", "CK", "COK", "184"},
-	{"Costa Rica", "Costa Rica (le)", "CR", "CRI", "188"},
-	{"Croatia", "Croatie (la)", "HR", "HRV", "191"},
-	{"Cuba", "Cuba", "CU", "CUB", "192"},
-	{"Cyprus", "Chypre", "CY", "CYP", "196"},
-	{"Czech Republic (the)", "tchèque (la République)", "CZ", "CZE", "203"},
-	{"Benin", "Bénin (le)", "BJ", "BEN", "204"},
-	{"Denmark", "Danemark (le)", "DK", "DNK", "208"},
-	{"Dominica", "Dominique (la)", "DM", "DMA", "212"},
-	{"Dominican Republic (the)", "dominicaine (la République)", "DO", "DOM", "214"},
-	{"Ecuador", "Équateur (l')", "EC", "ECU", "218"},
-	{"El Salvador", "El Salvador", "SV", "SLV", "222"},
-	{"Equatorial Guinea", "Guinée équatoriale (la)", "GQ", "GNQ", "226"},
-	{"Ethiopia", "Éthiopie (l')", "ET", "ETH", "231"},
-	{"Eritrea", "Érythrée (l')", "ER", "ERI", "232"},
-	{"Estonia", "Estonie (l')", "EE", "EST", "233"},
-	{"Faroe Islands (the)", "Féroé (les Îles)", "FO", "FRO", "234"},
-	{"Falkland Islands (the) [Malvinas]", "Falkland (les Îles)/Malouines (les Îles)", "FK", "FLK", "238"},
-	{"South Georgia and the South Sandwich Islands", "Géorgie du Sud-et-les Îles Sandwich du Sud (la)", "GS", "SGS", "239"},
-	{"Fiji", "Fidji (les)", "FJ", "FJI", "242"},
-	{"Finland", "Finlande (la)", "FI", "FIN", "246"},
-	{"Åland Islands", "Åland(les Îles)", "AX", "ALA", "248"},
-	{"France", "France (la)", "FR", "FRA", "250"},
-	{"French Guiana", "Guyane française (la )", "GF", "GUF", "254"},
-	{"French Polynesia", "Polynésie française (la)", "PF", "PYF", "258"},
-	{"French Southern Territories (the)", "Terres australes françaises (les)", "TF", "ATF", "260"},
-	{"Djibouti", "Djibouti", "DJ", "DJI", "262"},
-	{"Gabon", "Gabon (le)", "GA", "GAB", "266"},
-	{"Georgia", "Géorgie (la)", "GE", "GEO", "268"},
-	{"Gambia (the)", "Gambie (la)", "GM", "GMB", "270"},
-	{"Palestine, State of", "Palestine, État de", "PS", "PSE", "275"},
-	{"Germany", "Allemagne (l')", "DE", "DEU", "276"},
-	{"Ghana", "Ghana (le)", "GH", "GHA", "288"},
-	{"Gibraltar", "Gibraltar", "GI", "GIB", "292"},
-	{"Kiribati", "Kiribati", "KI", "KIR", "296"},
-	{"Greece", "Grèce (la)", "GR", "GRC", "300"},
-	{"Greenland", "Groenland (le)", "GL", "GRL", "304"},
-	{"Grenada", "Grenade (la)", "GD", "GRD", "308"},
-	{"Guadeloupe", "Guadeloupe (la)", "GP", "GLP", "312"},
-	{"Guam", "Guam", "GU", "GUM", "316"},
-	{"Guatemala", "Guatemala (le)", "GT", "GTM", "320"},
-	{"Guinea", "Guinée (la)", "GN", "GIN", "324"},
-	{"Guyana", "Guyana (le)", "GY", "GUY", "328"},
-	{"Haiti", "Haïti", "HT", "HTI", "332"},
-	{"Heard Island and McDonald Islands", "Heard-et-Îles MacDonald (l'Île)", "HM", "HMD", "334"},
-	{"Holy See (the)", "Saint-Siège (le)", "VA", "VAT", "336"},
-	{"Honduras", "Honduras (le)", "HN", "HND", "340"},
-	{"Hong Kong", "Hong Kong", "HK", "HKG", "344"},
-	{"Hungary", "Hongrie (la)", "HU", "HUN", "348"},
-	{"Iceland", "Islande (l')", "IS", "ISL", "352"},
-	{"India", "Inde (l')", "IN", "IND", "356"},
-	{"Indonesia", "Indonésie (l')", "ID", "IDN", "360"},
-	{"Iran (Islamic Republic of)", "Iran (République Islamique d')", "IR", "IRN", "364"},
-	{"Iraq", "Iraq (l')", "IQ", "IRQ", "368"},
-	{"Ireland", "Irlande (l')", "IE", "IRL", "372"},
-	{"Israel", "Israël", "IL", "ISR", "376"},
-	{"Italy", "Italie (l')", "IT", "ITA", "380"},
-	{"Côte d'Ivoire", "Côte d'Ivoire (la)", "CI", "CIV", "384"},
-	{"Jamaica", "Jamaïque (la)", "JM", "JAM", "388"},
-	{"Japan", "Japon (le)", "JP", "JPN", "392"},
-	{"Kazakhstan", "Kazakhstan (le)", "KZ", "KAZ", "398"},
-	{"Jordan", "Jordanie (la)", "JO", "JOR", "400"},
-	{"Kenya", "Kenya (le)", "KE", "KEN", "404"},
-	{"Korea (the Democratic People's Republic of)", "Corée (la République populaire démocratique de)", "KP", "PRK", "408"},
-	{"Korea (the Republic of)", "Corée (la République de)", "KR", "KOR", "410"},
-	{"Kuwait", "Koweït (le)", "KW", "KWT", "414"},
-	{"Kyrgyzstan", "Kirghizistan (le)", "KG", "KGZ", "417"},
-	{"Lao People's Democratic Republic (the)", "Lao, République démocratique populaire", "LA", "LAO", "418"},
-	{"Lebanon", "Liban (le)", "LB", "LBN", "422"},
-	{"Lesotho", "Lesotho (le)", "LS", "LSO", "426"},
-	{"Latvia", "Lettonie (la)", "LV", "LVA", "428"},
-	{"Liberia", "Libéria (le)", "LR", "LBR", "430"},
-	{"Libya", "Libye (la)", "LY", "LBY", "434"},
-	{"Liechtenstein", "Liechtenstein (le)", "LI", "LIE", "438"},
-	{"Lithuania", "Lituanie (la)", "LT", "LTU", "440"},
-	{"Luxembourg", "Luxembourg (le)", "LU", "LUX", "442"},
-	{"Macao", "Macao", "MO", "MAC", "446"},
-	{"Madagascar", "Madagascar", "MG", "MDG", "450"},
-	{"Malawi", "Malawi (le)", "MW", "MWI", "454"},
-	{"Malaysia", "Malaisie (la)", "MY", "MYS", "458"},
-	{"Maldives", "Maldives (les)", "MV", "MDV", "462"},
-	{"Mali", "Mali (le)", "ML", "MLI", "466"},
-	{"Malta", "Malte", "MT", "MLT", "470"},
-	{"Martinique", "Martinique (la)", "MQ", "MTQ", "474"},
-	{"Mauritania", "Mauritanie (la)", "MR", "MRT", "478"},
-	{"Mauritius", "Maurice", "MU", "MUS", "480"},
-	{"Mexico", "Mexique (le)", "MX", "MEX", "484"},
-	{"Monaco", "Monaco", "MC", "MCO", "492"},
-	{"Mongolia", "Mongolie (la)", "MN", "MNG", "496"},
-	{"Moldova (the Republic of)", "Moldova , République de", "MD", "MDA", "498"},
-	{"Montenegro", "Monténégro (le)", "ME", "MNE", "499"},
-	{"Montserrat", "Montserrat", "MS", "MSR", "500"},
-	{"Morocco", "Maroc (le)", "MA", "MAR", "504"},
-	{"Mozambique", "Mozambique (le)", "MZ", "MOZ", "508"},
-	{"Oman", "Oman", "OM", "OMN", "512"},
-	{"Namibia", "Namibie (la)", "NA", "NAM", "516"},
-	{"Nauru", "Nauru", "NR", "NRU", "520"},
-	{"Nepal", "Népal (le)", "NP", "NPL", "524"},
-	{"Netherlands (the)", "Pays-Bas (les)", "NL", "NLD", "528"},
-	{"Curaçao", "Curaçao", "CW", "CUW", "531"},
-	{"Aruba", "Aruba", "AW", "ABW", "533"},
-	{"Sint Maarten (Dutch part)", "Saint-Martin (partie néerlandaise)", "SX", "SXM", "534"},
-	{"Bonaire, Sint Eustatius and Saba", "Bonaire, Saint-Eustache et Saba", "BQ", "BES", "535"},
-	{"New Caledonia", "Nouvelle-Calédonie (la)", "NC", "NCL", "540"},
-	{"Vanuatu", "Vanuatu (le)", "VU", "VUT", "548"},
-	{"New Zealand", "Nouvelle-Zélande (la)", "NZ", "NZL", "554"},
-	{"Nicaragua", "Nicaragua (le)", "NI", "NIC", "558"},
-	{"Niger (the)", "Niger (le)", "NE", "NER", "562"},
-	{"Nigeria", "Nigéria (le)", "NG", "NGA", "566"},
-	{"Niue", "Niue", "NU", "NIU", "570"},
-	{"Norfolk Island", "Norfolk (l'Île)", "NF", "NFK", "574"},
-	{"Norway", "Norvège (la)", "NO", "NOR", "578"},
-	{"Northern Mariana Islands (the)", "Mariannes du Nord (les Îles)", "MP", "MNP", "580"},
-	{"United States Minor Outlying Islands (the)", "Îles mineures éloignées des États-Unis (les)", "UM", "UMI", "581"},
-	{"Micronesia (Federated States of)", "Micronésie (États fédérés de)", "FM", "FSM", "583"},
-	{"Marshall Islands (the)", "Marshall (Îles)", "MH", "MHL", "584"},
-	{"Palau", "Palaos (les)", "PW", "PLW", "585"},
-	{"Pakistan", "Pakistan (le)", "PK", "PAK", "586"},
-	{"Panama", "Panama (le)", "PA", "PAN", "591"},
-	{"Papua New Guinea", "Papouasie-Nouvelle-Guinée (la)", "PG", "PNG", "598"},
-	{"Paraguay", "Paraguay (le)", "PY", "PRY", "600"},
-	{"Peru", "Pérou (le)", "PE", "PER", "604"},
-	{"Philippines (the)", "Philippines (les)", "PH", "PHL", "608"},
-	{"Pitcairn", "Pitcairn", "PN", "PCN", "612"},
-	{"Poland", "Pologne (la)", "PL", "POL", "616"},
-	{"Portugal", "Portugal (le)", "PT", "PRT", "620"},
-	{"Guinea-Bissau", "Guinée-Bissau (la)", "GW", "GNB", "624"},
-	{"Timor-Leste", "Timor-Leste (le)", "TL", "TLS", "626"},
-	{"Puerto Rico", "Porto Rico", "PR", "PRI", "630"},
-	{"Qatar", "Qatar (le)", "QA", "QAT", "634"},
-	{"Réunion", "Réunion (La)", "RE", "REU", "638"},
-	{"Romania", "Roumanie (la)", "RO", "ROU", "642"},
-	{"Russian Federation (the)", "Russie (la Fédération de)", "RU", "RUS", "643"},
-	{"Rwanda", "Rwanda (le)", "RW", "RWA", "646"},
-	{"Saint Barthélemy", "Saint-Barthélemy", "BL", "BLM", "652"},
-	{"Saint Helena, Ascension and Tristan da Cunha", "Sainte-Hélène, Ascension et Tristan da Cunha", "SH", "SHN", "654"},
-	{"Saint Kitts and Nevis", "Saint-Kitts-et-Nevis", "KN", "KNA", "659"},
-	{"Anguilla", "Anguilla", "AI", "AIA", "660"},
-	{"Saint Lucia", "Sainte-Lucie", "LC", "LCA", "662"},
-	{"Saint Martin (French part)", "Saint-Martin (partie française)", "MF", "MAF", "663"},
-	{"Saint Pierre and Miquelon", "Saint-Pierre-et-Miquelon", "PM", "SPM", "666"},
-	{"Saint Vincent and the Grenadines", "Saint-Vincent-et-les Grenadines", "VC", "VCT", "670"},
-	{"San Marino", "Saint-Marin", "SM", "SMR", "674"},
-	{"Sao Tome and Principe", "Sao Tomé-et-Principe", "ST", "STP", "678"},
-	{"Saudi Arabia", "Arabie saoudite (l')", "SA", "SAU", "682"},
-	{"Senegal", "Sénégal (le)", "SN", "SEN", "686"},
-	{"Serbia", "Serbie (la)", "RS", "SRB", "688"},
-	{"Seychelles", "Seychelles (les)", "SC", "SYC", "690"},
-	{"Sierra Leone", "Sierra Leone (la)", "SL", "SLE", "694"},
-	{"Singapore", "Singapour", "SG", "SGP", "702"},
-	{"Slovakia", "Slovaquie (la)", "SK", "SVK", "703"},
-	{"Viet Nam", "Viet Nam (le)", "VN", "VNM", "704"},
-	{"Slovenia", "Slovénie (la)", "SI", "SVN", "705"},
-	{"Somalia", "Somalie (la)", "SO", "SOM", "706"},
-	{"South Africa", "Afrique du Sud (l')", "ZA", "ZAF", "710"},
-	{"Zimbabwe", "Zimbabwe (le)", "ZW", "ZWE", "716"},
-	{"Spain", "Espagne (l')", "ES", "ESP", "724"},
-	{"South Sudan", "Soudan du Sud (le)", "SS", "SSD", "728"},
-	{"Sudan (the)", "Soudan (le)", "SD", "SDN", "729"},
-	{"Western Sahara*", "Sahara occidental (le)*", "EH", "ESH", "732"},
-	{"Suriname", "Suriname (le)", "SR", "SUR", "740"},
-	{"Svalbard and Jan Mayen", "Svalbard et l'Île Jan Mayen (le)", "SJ", "SJM", "744"},
-	{"Swaziland", "Swaziland (le)", "SZ", "SWZ", "748"},
-	{"Sweden", "Suède (la)", "SE", "SWE", "752"},
-	{"Switzerland", "Suisse (la)", "CH", "CHE", "756"},
-	{"Syrian Arab Republic", "République arabe syrienne (la)", "SY", "SYR", "760"},
-	{"Tajikistan", "Tadjikistan (le)", "TJ", "TJK", "762"},
-	{"Thailand", "Thaïlande (la)", "TH", "THA", "764"},
-	{"Togo", "Togo (le)", "TG", "TGO", "768"},
-	{"Tokelau", "Tokelau (les)", "TK", "TKL", "772"},
-	{"Tonga", "Tonga (les)", "TO", "TON", "776"},
-	{"Trinidad and Tobago", "Trinité-et-Tobago (la)", "TT", "TTO", "780"},
-	{"United Arab Emirates (the)", "Émirats arabes unis (les)", "AE", "ARE", "784"},
-	{"Tunisia", "Tunisie (la)", "TN", "TUN", "788"},
-	{"Turkey", "Turquie (la)", "TR", "TUR", "792"},
-	{"Turkmenistan", "Turkménistan (le)", "TM", "TKM", "795"},
-	{"Turks and Caicos Islands (the)", "Turks-et-Caïcos (les Îles)", "TC", "TCA", "796"},
-	{"Tuvalu", "Tuvalu (les)", "TV", "TUV", "798"},
-	{"Uganda", "Ouganda (l')", "UG", "UGA", "800"},
-	{"Ukraine", "Ukraine (l')", "UA", "UKR", "804"},
-	{"Macedonia (the former Yugoslav Republic of)", "Macédoine (l'ex‑République yougoslave de)", "MK", "MKD", "807"},
-	{"Egypt", "Égypte (l')", "EG", "EGY", "818"},
-	{"United Kingdom of Great Britain and Northern Ireland (the)", "Royaume-Uni de Grande-Bretagne et d'Irlande du Nord (le)", "GB", "GBR", "826"},
-	{"Guernsey", "Guernesey", "GG", "GGY", "831"},
-	{"Jersey", "Jersey", "JE", "JEY", "832"},
-	{"Isle of Man", "Île de Man", "IM", "IMN", "833"},
-	{"Tanzania, United Republic of", "Tanzanie, République-Unie de", "TZ", "TZA", "834"},
-	{"United States of America (the)", "États-Unis d'Amérique (les)", "US", "USA", "840"},
-	{"Virgin Islands (U.S.)", "Vierges des États-Unis (les Îles)", "VI", "VIR", "850"},
-	{"Burkina Faso", "Burkina Faso (le)", "BF", "BFA", "854"},
-	{"Uruguay", "Uruguay (l')", "UY", "URY", "858"},
-	{"Uzbekistan", "Ouzbékistan (l')", "UZ", "UZB", "860"},
-	{"Venezuela (Bolivarian Republic of)", "Venezuela (République bolivarienne du)", "VE", "VEN", "862"},
-	{"Wallis and Futuna", "Wallis-et-Futuna", "WF", "WLF", "876"},
-	{"Samoa", "Samoa (le)", "WS", "WSM", "882"},
-	{"Yemen", "Yémen (le)", "YE", "YEM", "887"},
-	{"Zambia", "Zambie (la)", "ZM", "ZMB", "894"},
-}
-
-// ISO4217List is the list of ISO currency codes
-var ISO4217List = []string{
-	"AED", "AFN", "ALL", "AMD", "ANG", "AOA", "ARS", "AUD", "AWG", "AZN",
-	"BAM", "BBD", "BDT", "BGN", "BHD", "BIF", "BMD", "BND", "BOB", "BOV", "BRL", "BSD", "BTN", "BWP", "BYN", "BZD",
-	"CAD", "CDF", "CHE", "CHF", "CHW", "CLF", "CLP", "CNY", "COP", "COU", "CRC", "CUC", "CUP", "CVE", "CZK",
-	"DJF", "DKK", "DOP", "DZD",
-	"EGP", "ERN", "ETB", "EUR",
-	"FJD", "FKP",
-	"GBP", "GEL", "GHS", "GIP", "GMD", "GNF", "GTQ", "GYD",
-	"HKD", "HNL", "HRK", "HTG", "HUF",
-	"IDR", "ILS", "INR", "IQD", "IRR", "ISK",
-	"JMD", "JOD", "JPY",
-	"KES", "KGS", "KHR", "KMF", "KPW", "KRW", "KWD", "KYD", "KZT",
-	"LAK", "LBP", "LKR", "LRD", "LSL", "LYD",
-	"MAD", "MDL", "MGA", "MKD", "MMK", "MNT", "MOP", "MRO", "MUR", "MVR", "MWK", "MXN", "MXV", "MYR", "MZN",
-	"NAD", "NGN", "NIO", "NOK", "NPR", "NZD",
-	"OMR",
-	"PAB", "PEN", "PGK", "PHP", "PKR", "PLN", "PYG",
-	"QAR",
-	"RON", "RSD", "RUB", "RWF",
-	"SAR", "SBD", "SCR", "SDG", "SEK", "SGD", "SHP", "SLL", "SOS", "SRD", "SSP", "STD", "STN", "SVC", "SYP", "SZL",
-	"THB", "TJS", "TMT", "TND", "TOP", "TRY", "TTD", "TWD", "TZS",
-	"UAH", "UGX", "USD", "USN", "UYI", "UYU", "UYW", "UZS",
-	"VEF", "VES", "VND", "VUV",
-	"WST",
-	"XAF", "XAG", "XAU", "XBA", "XBB", "XBC", "XBD", "XCD", "XDR", "XOF", "XPD", "XPF", "XPT", "XSU", "XTS", "XUA", "XXX",
-	"YER",
-	"ZAR", "ZMW", "ZWL",
-}
-
-// ISO693Entry stores ISO language codes
-type ISO693Entry struct {
-	Alpha3bCode string
-	Alpha2Code  string
-	English     string
-}
-
-//ISO693List based on http://data.okfn.org/data/core/language-codes/r/language-codes-3b2.json
-var ISO693List = []ISO693Entry{
-	{Alpha3bCode: "aar", Alpha2Code: "aa", English: "Afar"},
-	{Alpha3bCode: "abk", Alpha2Code: "ab", English: "Abkhazian"},
-	{Alpha3bCode: "afr", Alpha2Code: "af", English: "Afrikaans"},
-	{Alpha3bCode: "aka", Alpha2Code: "ak", English: "Akan"},
-	{Alpha3bCode: "alb", Alpha2Code: "sq", English: "Albanian"},
-	{Alpha3bCode: "amh", Alpha2Code: "am", English: "Amharic"},
-	{Alpha3bCode: "ara", Alpha2Code: "ar", English: "Arabic"},
-	{Alpha3bCode: "arg", Alpha2Code: "an", English: "Aragonese"},
-	{Alpha3bCode: "arm", Alpha2Code: "hy", English: "Armenian"},
-	{Alpha3bCode: "asm", Alpha2Code: "as", English: "Assamese"},
-	{Alpha3bCode: "ava", Alpha2Code: "av", English: "Avaric"},
-	{Alpha3bCode: "ave", Alpha2Code: "ae", English: "Avestan"},
-	{Alpha3bCode: "aym", Alpha2Code: "ay", English: "Aymara"},
-	{Alpha3bCode: "aze", Alpha2Code: "az", English: "Azerbaijani"},
-	{Alpha3bCode: "bak", Alpha2Code: "ba", English: "Bashkir"},
-	{Alpha3bCode: "bam", Alpha2Code: "bm", English: "Bambara"},
-	{Alpha3bCode: "baq", Alpha2Code: "eu", English: "Basque"},
-	{Alpha3bCode: "bel", Alpha2Code: "be", English: "Belarusian"},
-	{Alpha3bCode: "ben", Alpha2Code: "bn", English: "Bengali"},
-	{Alpha3bCode: "bih", Alpha2Code: "bh", English: "Bihari languages"},
-	{Alpha3bCode: "bis", Alpha2Code: "bi", English: "Bislama"},
-	{Alpha3bCode: "bos", Alpha2Code: "bs", English: "Bosnian"},
-	{Alpha3bCode: "bre", Alpha2Code: "br", English: "Breton"},
-	{Alpha3bCode: "bul", Alpha2Code: "bg", English: "Bulgarian"},
-	{Alpha3bCode: "bur", Alpha2Code: "my", English: "Burmese"},
-	{Alpha3bCode: "cat", Alpha2Code: "ca", English: "Catalan; Valencian"},
-	{Alpha3bCode: "cha", Alpha2Code: "ch", English: "Chamorro"},
-	{Alpha3bCode: "che", Alpha2Code: "ce", English: "Chechen"},
-	{Alpha3bCode: "chi", Alpha2Code: "zh", English: "Chinese"},
-	{Alpha3bCode: "chu", Alpha2Code: "cu", English: "Church Slavic; Old Slavonic; Church Slavonic; Old Bulgarian; Old Church Slavonic"},
-	{Alpha3bCode: "chv", Alpha2Code: "cv", English: "Chuvash"},
-	{Alpha3bCode: "cor", Alpha2Code: "kw", English: "Cornish"},
-	{Alpha3bCode: "cos", Alpha2Code: "co", English: "Corsican"},
-	{Alpha3bCode: "cre", Alpha2Code: "cr", English: "Cree"},
-	{Alpha3bCode: "cze", Alpha2Code: "cs", English: "Czech"},
-	{Alpha3bCode: "dan", Alpha2Code: "da", English: "Danish"},
-	{Alpha3bCode: "div", Alpha2Code: "dv", English: "Divehi; Dhivehi; Maldivian"},
-	{Alpha3bCode: "dut", Alpha2Code: "nl", English: "Dutch; Flemish"},
-	{Alpha3bCode: "dzo", Alpha2Code: "dz", English: "Dzongkha"},
-	{Alpha3bCode: "eng", Alpha2Code: "en", English: "English"},
-	{Alpha3bCode: "epo", Alpha2Code: "eo", English: "Esperanto"},
-	{Alpha3bCode: "est", Alpha2Code: "et", English: "Estonian"},
-	{Alpha3bCode: "ewe", Alpha2Code: "ee", English: "Ewe"},
-	{Alpha3bCode: "fao", Alpha2Code: "fo", English: "Faroese"},
-	{Alpha3bCode: "fij", Alpha2Code: "fj", English: "Fijian"},
-	{Alpha3bCode: "fin", Alpha2Code: "fi", English: "Finnish"},
-	{Alpha3bCode: "fre", Alpha2Code: "fr", English: "French"},
-	{Alpha3bCode: "fry", Alpha2Code: "fy", English: "Western Frisian"},
-	{Alpha3bCode: "ful", Alpha2Code: "ff", English: "Fulah"},
-	{Alpha3bCode: "geo", Alpha2Code: "ka", English: "Georgian"},
-	{Alpha3bCode: "ger", Alpha2Code: "de", English: "German"},
-	{Alpha3bCode: "gla", Alpha2Code: "gd", English: "Gaelic; Scottish Gaelic"},
-	{Alpha3bCode: "gle", Alpha2Code: "ga", English: "Irish"},
-	{Alpha3bCode: "glg", Alpha2Code: "gl", English: "Galician"},
-	{Alpha3bCode: "glv", Alpha2Code: "gv", English: "Manx"},
-	{Alpha3bCode: "gre", Alpha2Code: "el", English: "Greek, Modern (1453-)"},
-	{Alpha3bCode: "grn", Alpha2Code: "gn", English: "Guarani"},
-	{Alpha3bCode: "guj", Alpha2Code: "gu", English: "Gujarati"},
-	{Alpha3bCode: "hat", Alpha2Code: "ht", English: "Haitian; Haitian Creole"},
-	{Alpha3bCode: "hau", Alpha2Code: "ha", English: "Hausa"},
-	{Alpha3bCode: "heb", Alpha2Code: "he", English: "Hebrew"},
-	{Alpha3bCode: "her", Alpha2Code: "hz", English: "Herero"},
-	{Alpha3bCode: "hin", Alpha2Code: "hi", English: "Hindi"},
-	{Alpha3bCode: "hmo", Alpha2Code: "ho", English: "Hiri Motu"},
-	{Alpha3bCode: "hrv", Alpha2Code: "hr", English: "Croatian"},
-	{Alpha3bCode: "hun", Alpha2Code: "hu", English: "Hungarian"},
-	{Alpha3bCode: "ibo", Alpha2Code: "ig", English: "Igbo"},
-	{Alpha3bCode: "ice", Alpha2Code: "is", English: "Icelandic"},
-	{Alpha3bCode: "ido", Alpha2Code: "io", English: "Ido"},
-	{Alpha3bCode: "iii", Alpha2Code: "ii", English: "Sichuan Yi; Nuosu"},
-	{Alpha3bCode: "iku", Alpha2Code: "iu", English: "Inuktitut"},
-	{Alpha3bCode: "ile", Alpha2Code: "ie", English: "Interlingue; Occidental"},
-	{Alpha3bCode: "ina", Alpha2Code: "ia", English: "Interlingua (International Auxiliary Language Association)"},
-	{Alpha3bCode: "ind", Alpha2Code: "id", English: "Indonesian"},
-	{Alpha3bCode: "ipk", Alpha2Code: "ik", English: "Inupiaq"},
-	{Alpha3bCode: "ita", Alpha2Code: "it", English: "Italian"},
-	{Alpha3bCode: "jav", Alpha2Code: "jv", English: "Javanese"},
-	{Alpha3bCode: "jpn", Alpha2Code: "ja", English: "Japanese"},
-	{Alpha3bCode: "kal", Alpha2Code: "kl", English: "Kalaallisut; Greenlandic"},
-	{Alpha3bCode: "kan", Alpha2Code: "kn", English: "Kannada"},
-	{Alpha3bCode: "kas", Alpha2Code: "ks", English: "Kashmiri"},
-	{Alpha3bCode: "kau", Alpha2Code: "kr", English: "Kanuri"},
-	{Alpha3bCode: "kaz", Alpha2Code: "kk", English: "Kazakh"},
-	{Alpha3bCode: "khm", Alpha2Code: "km", English: "Central Khmer"},
-	{Alpha3bCode: "kik", Alpha2Code: "ki", English: "Kikuyu; Gikuyu"},
-	{Alpha3bCode: "kin", Alpha2Code: "rw", English: "Kinyarwanda"},
-	{Alpha3bCode: "kir", Alpha2Code: "ky", English: "Kirghiz; Kyrgyz"},
-	{Alpha3bCode: "kom", Alpha2Code: "kv", English: "Komi"},
-	{Alpha3bCode: "kon", Alpha2Code: "kg", English: "Kongo"},
-	{Alpha3bCode: "kor", Alpha2Code: "ko", English: "Korean"},
-	{Alpha3bCode: "kua", Alpha2Code: "kj", English: "Kuanyama; Kwanyama"},
-	{Alpha3bCode: "kur", Alpha2Code: "ku", English: "Kurdish"},
-	{Alpha3bCode: "lao", Alpha2Code: "lo", English: "Lao"},
-	{Alpha3bCode: "lat", Alpha2Code: "la", English: "Latin"},
-	{Alpha3bCode: "lav", Alpha2Code: "lv", English: "Latvian"},
-	{Alpha3bCode: "lim", Alpha2Code: "li", English: "Limburgan; Limburger; Limburgish"},
-	{Alpha3bCode: "lin", Alpha2Code: "ln", English: "Lingala"},
-	{Alpha3bCode: "lit", Alpha2Code: "lt", English: "Lithuanian"},
-	{Alpha3bCode: "ltz", Alpha2Code: "lb", English: "Luxembourgish; Letzeburgesch"},
-	{Alpha3bCode: "lub", Alpha2Code: "lu", English: "Luba-Katanga"},
-	{Alpha3bCode: "lug", Alpha2Code: "lg", English: "Ganda"},
-	{Alpha3bCode: "mac", Alpha2Code: "mk", English: "Macedonian"},
-	{Alpha3bCode: "mah", Alpha2Code: "mh", English: "Marshallese"},
-	{Alpha3bCode: "mal", Alpha2Code: "ml", English: "Malayalam"},
-	{Alpha3bCode: "mao", Alpha2Code: "mi", English: "Maori"},
-	{Alpha3bCode: "mar", Alpha2Code: "mr", English: "Marathi"},
-	{Alpha3bCode: "may", Alpha2Code: "ms", English: "Malay"},
-	{Alpha3bCode: "mlg", Alpha2Code: "mg", English: "Malagasy"},
-	{Alpha3bCode: "mlt", Alpha2Code: "mt", English: "Maltese"},
-	{Alpha3bCode: "mon", Alpha2Code: "mn", English: "Mongolian"},
-	{Alpha3bCode: "nau", Alpha2Code: "na", English: "Nauru"},
-	{Alpha3bCode: "nav", Alpha2Code: "nv", English: "Navajo; Navaho"},
-	{Alpha3bCode: "nbl", Alpha2Code: "nr", English: "Ndebele, South; South Ndebele"},
-	{Alpha3bCode: "nde", Alpha2Code: "nd", English: "Ndebele, North; North Ndebele"},
-	{Alpha3bCode: "ndo", Alpha2Code: "ng", English: "Ndonga"},
-	{Alpha3bCode: "nep", Alpha2Code: "ne", English: "Nepali"},
-	{Alpha3bCode: "nno", Alpha2Code: "nn", English: "Norwegian Nynorsk; Nynorsk, Norwegian"},
-	{Alpha3bCode: "nob", Alpha2Code: "nb", English: "Bokmål, Norwegian; Norwegian Bokmål"},
-	{Alpha3bCode: "nor", Alpha2Code: "no", English: "Norwegian"},
-	{Alpha3bCode: "nya", Alpha2Code: "ny", English: "Chichewa; Chewa; Nyanja"},
-	{Alpha3bCode: "oci", Alpha2Code: "oc", English: "Occitan (post 1500); Provençal"},
-	{Alpha3bCode: "oji", Alpha2Code: "oj", English: "Ojibwa"},
-	{Alpha3bCode: "ori", Alpha2Code: "or", English: "Oriya"},
-	{Alpha3bCode: "orm", Alpha2Code: "om", English: "Oromo"},
-	{Alpha3bCode: "oss", Alpha2Code: "os", English: "Ossetian; Ossetic"},
-	{Alpha3bCode: "pan", Alpha2Code: "pa", English: "Panjabi; Punjabi"},
-	{Alpha3bCode: "per", Alpha2Code: "fa", English: "Persian"},
-	{Alpha3bCode: "pli", Alpha2Code: "pi", English: "Pali"},
-	{Alpha3bCode: "pol", Alpha2Code: "pl", English: "Polish"},
-	{Alpha3bCode: "por", Alpha2Code: "pt", English: "Portuguese"},
-	{Alpha3bCode: "pus", Alpha2Code: "ps", English: "Pushto; Pashto"},
-	{Alpha3bCode: "que", Alpha2Code: "qu", English: "Quechua"},
-	{Alpha3bCode: "roh", Alpha2Code: "rm", English: "Romansh"},
-	{Alpha3bCode: "rum", Alpha2Code: "ro", English: "Romanian; Moldavian; Moldovan"},
-	{Alpha3bCode: "run", Alpha2Code: "rn", English: "Rundi"},
-	{Alpha3bCode: "rus", Alpha2Code: "ru", English: "Russian"},
-	{Alpha3bCode: "sag", Alpha2Code: "sg", English: "Sango"},
-	{Alpha3bCode: "san", Alpha2Code: "sa", English: "Sanskrit"},
-	{Alpha3bCode: "sin", Alpha2Code: "si", English: "Sinhala; Sinhalese"},
-	{Alpha3bCode: "slo", Alpha2Code: "sk", English: "Slovak"},
-	{Alpha3bCode: "slv", Alpha2Code: "sl", English: "Slovenian"},
-	{Alpha3bCode: "sme", Alpha2Code: "se", English: "Northern Sami"},
-	{Alpha3bCode: "smo", Alpha2Code: "sm", English: "Samoan"},
-	{Alpha3bCode: "sna", Alpha2Code: "sn", English: "Shona"},
-	{Alpha3bCode: "snd", Alpha2Code: "sd", English: "Sindhi"},
-	{Alpha3bCode: "som", Alpha2Code: "so", English: "Somali"},
-	{Alpha3bCode: "sot", Alpha2Code: "st", English: "Sotho, Southern"},
-	{Alpha3bCode: "spa", Alpha2Code: "es", English: "Spanish; Castilian"},
-	{Alpha3bCode: "srd", Alpha2Code: "sc", English: "Sardinian"},
-	{Alpha3bCode: "srp", Alpha2Code: "sr", English: "Serbian"},
-	{Alpha3bCode: "ssw", Alpha2Code: "ss", English: "Swati"},
-	{Alpha3bCode: "sun", Alpha2Code: "su", English: "Sundanese"},
-	{Alpha3bCode: "swa", Alpha2Code: "sw", English: "Swahili"},
-	{Alpha3bCode: "swe", Alpha2Code: "sv", English: "Swedish"},
-	{Alpha3bCode: "tah", Alpha2Code: "ty", English: "Tahitian"},
-	{Alpha3bCode: "tam", Alpha2Code: "ta", English: "Tamil"},
-	{Alpha3bCode: "tat", Alpha2Code: "tt", English: "Tatar"},
-	{Alpha3bCode: "tel", Alpha2Code: "te", English: "Telugu"},
-	{Alpha3bCode: "tgk", Alpha2Code: "tg", English: "Tajik"},
-	{Alpha3bCode: "tgl", Alpha2Code: "tl", English: "Tagalog"},
-	{Alpha3bCode: "tha", Alpha2Code: "th", English: "Thai"},
-	{Alpha3bCode: "tib", Alpha2Code: "bo", English: "Tibetan"},
-	{Alpha3bCode: "tir", Alpha2Code: "ti", English: "Tigrinya"},
-	{Alpha3bCode: "ton", Alpha2Code: "to", English: "Tonga (Tonga Islands)"},
-	{Alpha3bCode: "tsn", Alpha2Code: "tn", English: "Tswana"},
-	{Alpha3bCode: "tso", Alpha2Code: "ts", English: "Tsonga"},
-	{Alpha3bCode: "tuk", Alpha2Code: "tk", English: "Turkmen"},
-	{Alpha3bCode: "tur", Alpha2Code: "tr", English: "Turkish"},
-	{Alpha3bCode: "twi", Alpha2Code: "tw", English: "Twi"},
-	{Alpha3bCode: "uig", Alpha2Code: "ug", English: "Uighur; Uyghur"},
-	{Alpha3bCode: "ukr", Alpha2Code: "uk", English: "Ukrainian"},
-	{Alpha3bCode: "urd", Alpha2Code: "ur", English: "Urdu"},
-	{Alpha3bCode: "uzb", Alpha2Code: "uz", English: "Uzbek"},
-	{Alpha3bCode: "ven", Alpha2Code: "ve", English: "Venda"},
-	{Alpha3bCode: "vie", Alpha2Code: "vi", English: "Vietnamese"},
-	{Alpha3bCode: "vol", Alpha2Code: "vo", English: "Volapük"},
-	{Alpha3bCode: "wel", Alpha2Code: "cy", English: "Welsh"},
-	{Alpha3bCode: "wln", Alpha2Code: "wa", English: "Walloon"},
-	{Alpha3bCode: "wol", Alpha2Code: "wo", English: "Wolof"},
-	{Alpha3bCode: "xho", Alpha2Code: "xh", English: "Xhosa"},
-	{Alpha3bCode: "yid", Alpha2Code: "yi", English: "Yiddish"},
-	{Alpha3bCode: "yor", Alpha2Code: "yo", English: "Yoruba"},
-	{Alpha3bCode: "zha", Alpha2Code: "za", English: "Zhuang; Chuang"},
-	{Alpha3bCode: "zul", Alpha2Code: "zu", English: "Zulu"},
-}

+ 0 - 270
common_utils/validator/utils.go

@@ -1,270 +0,0 @@
-package govalidator
-
-import (
-	"errors"
-	"fmt"
-	"html"
-	"math"
-	"path"
-	"regexp"
-	"strings"
-	"unicode"
-	"unicode/utf8"
-)
-
-// Contains checks if the string contains the substring.
-func Contains(str, substring string) bool {
-	return strings.Contains(str, substring)
-}
-
-// Matches checks if string matches the pattern (pattern is regular expression)
-// In case of error return false
-func Matches(str, pattern string) bool {
-	match, _ := regexp.MatchString(pattern, str)
-	return match
-}
-
-// LeftTrim trims characters from the left side of the input.
-// If second argument is empty, it will remove leading spaces.
-func LeftTrim(str, chars string) string {
-	if chars == "" {
-		return strings.TrimLeftFunc(str, unicode.IsSpace)
-	}
-	r, _ := regexp.Compile("^[" + chars + "]+")
-	return r.ReplaceAllString(str, "")
-}
-
-// RightTrim trims characters from the right side of the input.
-// If second argument is empty, it will remove trailing spaces.
-func RightTrim(str, chars string) string {
-	if chars == "" {
-		return strings.TrimRightFunc(str, unicode.IsSpace)
-	}
-	r, _ := regexp.Compile("[" + chars + "]+$")
-	return r.ReplaceAllString(str, "")
-}
-
-// Trim trims characters from both sides of the input.
-// If second argument is empty, it will remove spaces.
-func Trim(str, chars string) string {
-	return LeftTrim(RightTrim(str, chars), chars)
-}
-
-// WhiteList removes characters that do not appear in the whitelist.
-func WhiteList(str, chars string) string {
-	pattern := "[^" + chars + "]+"
-	r, _ := regexp.Compile(pattern)
-	return r.ReplaceAllString(str, "")
-}
-
-// BlackList removes characters that appear in the blacklist.
-func BlackList(str, chars string) string {
-	pattern := "[" + chars + "]+"
-	r, _ := regexp.Compile(pattern)
-	return r.ReplaceAllString(str, "")
-}
-
-// StripLow removes characters with a numerical value < 32 and 127, mostly control characters.
-// If keep_new_lines is true, newline characters are preserved (\n and \r, hex 0xA and 0xD).
-func StripLow(str string, keepNewLines bool) string {
-	chars := ""
-	if keepNewLines {
-		chars = "\x00-\x09\x0B\x0C\x0E-\x1F\x7F"
-	} else {
-		chars = "\x00-\x1F\x7F"
-	}
-	return BlackList(str, chars)
-}
-
-// ReplacePattern replaces regular expression pattern in string
-func ReplacePattern(str, pattern, replace string) string {
-	r, _ := regexp.Compile(pattern)
-	return r.ReplaceAllString(str, replace)
-}
-
-// Escape replaces <, >, & and " with HTML entities.
-var Escape = html.EscapeString
-
-func addSegment(inrune, segment []rune) []rune {
-	if len(segment) == 0 {
-		return inrune
-	}
-	if len(inrune) != 0 {
-		inrune = append(inrune, '_')
-	}
-	inrune = append(inrune, segment...)
-	return inrune
-}
-
-// UnderscoreToCamelCase converts from underscore separated form to camel case form.
-// Ex.: my_func => MyFunc
-func UnderscoreToCamelCase(s string) string {
-	return strings.Replace(strings.Title(strings.Replace(strings.ToLower(s), "_", " ", -1)), " ", "", -1)
-}
-
-// CamelCaseToUnderscore converts from camel case form to underscore separated form.
-// Ex.: MyFunc => my_func
-func CamelCaseToUnderscore(str string) string {
-	var output []rune
-	var segment []rune
-	for _, r := range str {
-
-		// not treat number as separate segment
-		if !unicode.IsLower(r) && string(r) != "_" && !unicode.IsNumber(r) {
-			output = addSegment(output, segment)
-			segment = nil
-		}
-		segment = append(segment, unicode.ToLower(r))
-	}
-	output = addSegment(output, segment)
-	return string(output)
-}
-
-// Reverse returns reversed string
-func Reverse(s string) string {
-	r := []rune(s)
-	for i, j := 0, len(r)-1; i < j; i, j = i+1, j-1 {
-		r[i], r[j] = r[j], r[i]
-	}
-	return string(r)
-}
-
-// GetLines splits string by "\n" and return array of lines
-func GetLines(s string) []string {
-	return strings.Split(s, "\n")
-}
-
-// GetLine returns specified line of multiline string
-func GetLine(s string, index int) (string, error) {
-	lines := GetLines(s)
-	if index < 0 || index >= len(lines) {
-		return "", errors.New("line index out of bounds")
-	}
-	return lines[index], nil
-}
-
-// RemoveTags removes all tags from HTML string
-func RemoveTags(s string) string {
-	return ReplacePattern(s, "<[^>]*>", "")
-}
-
-// SafeFileName returns safe string that can be used in file names
-func SafeFileName(str string) string {
-	name := strings.ToLower(str)
-	name = path.Clean(path.Base(name))
-	name = strings.Trim(name, " ")
-	separators, err := regexp.Compile(`[ &_=+:]`)
-	if err == nil {
-		name = separators.ReplaceAllString(name, "-")
-	}
-	legal, err := regexp.Compile(`[^[:alnum:]-.]`)
-	if err == nil {
-		name = legal.ReplaceAllString(name, "")
-	}
-	for strings.Contains(name, "--") {
-		name = strings.Replace(name, "--", "-", -1)
-	}
-	return name
-}
-
-// NormalizeEmail canonicalize an email address.
-// The local part of the email address is lowercased for all domains; the hostname is always lowercased and
-// the local part of the email address is always lowercased for hosts that are known to be case-insensitive (currently only GMail).
-// Normalization follows special rules for known providers: currently, GMail addresses have dots removed in the local part and
-// are stripped of tags (e.g. some.one+tag@gmail.com becomes someone@gmail.com) and all @googlemail.com addresses are
-// normalized to @gmail.com.
-func NormalizeEmail(str string) (string, error) {
-	if !IsEmail(str) {
-		return "", fmt.Errorf("%s is not an email", str)
-	}
-	parts := strings.Split(str, "@")
-	parts[0] = strings.ToLower(parts[0])
-	parts[1] = strings.ToLower(parts[1])
-	if parts[1] == "gmail.com" || parts[1] == "googlemail.com" {
-		parts[1] = "gmail.com"
-		parts[0] = strings.Split(ReplacePattern(parts[0], `\.`, ""), "+")[0]
-	}
-	return strings.Join(parts, "@"), nil
-}
-
-// Truncate a string to the closest length without breaking words.
-func Truncate(str string, length int, ending string) string {
-	var aftstr, befstr string
-	if len(str) > length {
-		words := strings.Fields(str)
-		before, present := 0, 0
-		for i := range words {
-			befstr = aftstr
-			before = present
-			aftstr = aftstr + words[i] + " "
-			present = len(aftstr)
-			if present > length && i != 0 {
-				if (length - before) < (present - length) {
-					return Trim(befstr, " /\\.,\"'#!?&@+-") + ending
-				}
-				return Trim(aftstr, " /\\.,\"'#!?&@+-") + ending
-			}
-		}
-	}
-
-	return str
-}
-
-// PadLeft pads left side of a string if size of string is less then indicated pad length
-func PadLeft(str string, padStr string, padLen int) string {
-	return buildPadStr(str, padStr, padLen, true, false)
-}
-
-// PadRight pads right side of a string if size of string is less then indicated pad length
-func PadRight(str string, padStr string, padLen int) string {
-	return buildPadStr(str, padStr, padLen, false, true)
-}
-
-// PadBoth pads both sides of a string if size of string is less then indicated pad length
-func PadBoth(str string, padStr string, padLen int) string {
-	return buildPadStr(str, padStr, padLen, true, true)
-}
-
-// PadString either left, right or both sides.
-// Note that padding string can be unicode and more then one character
-func buildPadStr(str string, padStr string, padLen int, padLeft bool, padRight bool) string {
-
-	// When padded length is less then the current string size
-	if padLen < utf8.RuneCountInString(str) {
-		return str
-	}
-
-	padLen -= utf8.RuneCountInString(str)
-
-	targetLen := padLen
-
-	targetLenLeft := targetLen
-	targetLenRight := targetLen
-	if padLeft && padRight {
-		targetLenLeft = padLen / 2
-		targetLenRight = padLen - targetLenLeft
-	}
-
-	strToRepeatLen := utf8.RuneCountInString(padStr)
-
-	repeatTimes := int(math.Ceil(float64(targetLen) / float64(strToRepeatLen)))
-	repeatedString := strings.Repeat(padStr, repeatTimes)
-
-	leftSide := ""
-	if padLeft {
-		leftSide = repeatedString[0:targetLenLeft]
-	}
-
-	rightSide := ""
-	if padRight {
-		rightSide = repeatedString[0:targetLenRight]
-	}
-
-	return leftSide + str + rightSide
-}
-
-// TruncatingErrorf removes extra args from fmt.Errorf if not formatted in the str object
-func TruncatingErrorf(str string, args ...interface{}) error {
-	n := strings.Count(str, "%s")
-	return fmt.Errorf(str, args[:n]...)
-}

+ 0 - 1622
common_utils/validator/validator.go

@@ -1,1622 +0,0 @@
-// Package govalidator is package of validators and sanitizers for strings, structs and collections.
-package govalidator
-
-import (
-	"bytes"
-	"crypto/rsa"
-	"crypto/x509"
-	"encoding/base64"
-	"encoding/json"
-	"encoding/pem"
-	"fmt"
-	"io/ioutil"
-	"net"
-	"net/url"
-	"reflect"
-	"regexp"
-	"sort"
-	"strconv"
-	"strings"
-	"time"
-	"unicode"
-	"unicode/utf8"
-)
-
-var (
-	fieldsRequiredByDefault bool
-	nilPtrAllowedByRequired = false
-	notNumberRegexp         = regexp.MustCompile("[^0-9]+")
-	whiteSpacesAndMinus     = regexp.MustCompile(`[\s-]+`)
-	paramsRegexp            = regexp.MustCompile(`\(.*\)$`)
-)
-
-const maxURLRuneCount = 2083
-const minURLRuneCount = 3
-const rfc3339WithoutZone = "2006-01-02T15:04:05"
-
-// SetFieldsRequiredByDefault causes validation to fail when struct fields
-// do not include validations or are not explicitly marked as exempt (using `valid:"-"` or `valid:"email,optional"`).
-// This struct definition will fail govalidator.ValidateStruct() (and the field values do not matter):
-//     type exampleStruct struct {
-//         Name  string ``
-//         Email string `valid:"email"`
-// This, however, will only fail when Email is empty or an invalid email address:
-//     type exampleStruct2 struct {
-//         Name  string `valid:"-"`
-//         Email string `valid:"email"`
-// Lastly, this will only fail when Email is an invalid email address but not when it's empty:
-//     type exampleStruct2 struct {
-//         Name  string `valid:"-"`
-//         Email string `valid:"email,optional"`
-func SetFieldsRequiredByDefault(value bool) {
-	fieldsRequiredByDefault = value
-}
-
-// SetNilPtrAllowedByRequired causes validation to pass for nil ptrs when a field is set to required.
-// The validation will still reject ptr fields in their zero value state. Example with this enabled:
-//     type exampleStruct struct {
-//         Name  *string `valid:"required"`
-// With `Name` set to "", this will be considered invalid input and will cause a validation error.
-// With `Name` set to nil, this will be considered valid by validation.
-// By default this is disabled.
-func SetNilPtrAllowedByRequired(value bool) {
-	nilPtrAllowedByRequired = value
-}
-
-// IsEmail checks if the string is an email.
-func IsEmail(str string) bool {
-	// TODO uppercase letters are not supported
-	return rxEmail.MatchString(str)
-}
-
-// IsExistingEmail checks if the string is an email of existing domain
-func IsExistingEmail(email string) bool {
-
-	if len(email) < 6 || len(email) > 254 {
-		return false
-	}
-	at := strings.LastIndex(email, "@")
-	if at <= 0 || at > len(email)-3 {
-		return false
-	}
-	user := email[:at]
-	host := email[at+1:]
-	if len(user) > 64 {
-		return false
-	}
-	switch host {
-	case "localhost", "example.com":
-		return true
-	}
-	if userDotRegexp.MatchString(user) || !userRegexp.MatchString(user) || !hostRegexp.MatchString(host) {
-		return false
-	}
-	if _, err := net.LookupMX(host); err != nil {
-		if _, err := net.LookupIP(host); err != nil {
-			return false
-		}
-	}
-
-	return true
-}
-
-// IsURL checks if the string is an URL.
-func IsURL(str string) bool {
-	if str == "" || utf8.RuneCountInString(str) >= maxURLRuneCount || len(str) <= minURLRuneCount || strings.HasPrefix(str, ".") {
-		return false
-	}
-	strTemp := str
-	if strings.Contains(str, ":") && !strings.Contains(str, "://") {
-		// support no indicated urlscheme but with colon for port number
-		// http:// is appended so url.Parse will succeed, strTemp used so it does not impact rxURL.MatchString
-		strTemp = "http://" + str
-	}
-	u, err := url.Parse(strTemp)
-	if err != nil {
-		return false
-	}
-	if strings.HasPrefix(u.Host, ".") {
-		return false
-	}
-	if u.Host == "" && (u.Path != "" && !strings.Contains(u.Path, ".")) {
-		return false
-	}
-	return rxURL.MatchString(str)
-}
-
-// IsRequestURL checks if the string rawurl, assuming
-// it was received in an HTTP request, is a valid
-// URL confirm to RFC 3986
-func IsRequestURL(rawurl string) bool {
-	url, err := url.ParseRequestURI(rawurl)
-	if err != nil {
-		return false //Couldn't even parse the rawurl
-	}
-	if len(url.Scheme) == 0 {
-		return false //No Scheme found
-	}
-	return true
-}
-
-// IsRequestURI checks if the string rawurl, assuming
-// it was received in an HTTP request, is an
-// absolute URI or an absolute path.
-func IsRequestURI(rawurl string) bool {
-	_, err := url.ParseRequestURI(rawurl)
-	return err == nil
-}
-
-// IsAlpha checks if the string contains only letters (a-zA-Z). Empty string is valid.
-func IsAlpha(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxAlpha.MatchString(str)
-}
-
-//IsUTFLetter checks if the string contains only unicode letter characters.
-//Similar to IsAlpha but for all languages. Empty string is valid.
-func IsUTFLetter(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-
-	for _, c := range str {
-		if !unicode.IsLetter(c) {
-			return false
-		}
-	}
-	return true
-
-}
-
-// IsAlphanumeric checks if the string contains only letters and numbers. Empty string is valid.
-func IsAlphanumeric(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxAlphanumeric.MatchString(str)
-}
-
-// IsUTFLetterNumeric checks if the string contains only unicode letters and numbers. Empty string is valid.
-func IsUTFLetterNumeric(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	for _, c := range str {
-		if !unicode.IsLetter(c) && !unicode.IsNumber(c) { //letters && numbers are ok
-			return false
-		}
-	}
-	return true
-
-}
-
-// IsNumeric checks if the string contains only numbers. Empty string is valid.
-func IsNumeric(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxNumeric.MatchString(str)
-}
-
-// IsUTFNumeric checks if the string contains only unicode numbers of any kind.
-// Numbers can be 0-9 but also Fractions ¾,Roman Ⅸ and Hangzhou 〩. Empty string is valid.
-func IsUTFNumeric(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	if strings.IndexAny(str, "+-") > 0 {
-		return false
-	}
-	if len(str) > 1 {
-		str = strings.TrimPrefix(str, "-")
-		str = strings.TrimPrefix(str, "+")
-	}
-	for _, c := range str {
-		if !unicode.IsNumber(c) { //numbers && minus sign are ok
-			return false
-		}
-	}
-	return true
-
-}
-
-// IsUTFDigit checks if the string contains only unicode radix-10 decimal digits. Empty string is valid.
-func IsUTFDigit(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	if strings.IndexAny(str, "+-") > 0 {
-		return false
-	}
-	if len(str) > 1 {
-		str = strings.TrimPrefix(str, "-")
-		str = strings.TrimPrefix(str, "+")
-	}
-	for _, c := range str {
-		if !unicode.IsDigit(c) { //digits && minus sign are ok
-			return false
-		}
-	}
-	return true
-
-}
-
-// IsHexadecimal checks if the string is a hexadecimal number.
-func IsHexadecimal(str string) bool {
-	return rxHexadecimal.MatchString(str)
-}
-
-// IsHexcolor checks if the string is a hexadecimal color.
-func IsHexcolor(str string) bool {
-	return rxHexcolor.MatchString(str)
-}
-
-// IsRGBcolor checks if the string is a valid RGB color in form rgb(RRR, GGG, BBB).
-func IsRGBcolor(str string) bool {
-	return rxRGBcolor.MatchString(str)
-}
-
-// IsLowerCase checks if the string is lowercase. Empty string is valid.
-func IsLowerCase(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return str == strings.ToLower(str)
-}
-
-// IsUpperCase checks if the string is uppercase. Empty string is valid.
-func IsUpperCase(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return str == strings.ToUpper(str)
-}
-
-// HasLowerCase checks if the string contains at least 1 lowercase. Empty string is valid.
-func HasLowerCase(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxHasLowerCase.MatchString(str)
-}
-
-// HasUpperCase checks if the string contains as least 1 uppercase. Empty string is valid.
-func HasUpperCase(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxHasUpperCase.MatchString(str)
-}
-
-// IsInt checks if the string is an integer. Empty string is valid.
-func IsInt(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxInt.MatchString(str)
-}
-
-// IsFloat checks if the string is a float.
-func IsFloat(str string) bool {
-	return str != "" && rxFloat.MatchString(str)
-}
-
-// IsDivisibleBy checks if the string is a number that's divisible by another.
-// If second argument is not valid integer or zero, it's return false.
-// Otherwise, if first argument is not valid integer or zero, it's return true (Invalid string converts to zero).
-func IsDivisibleBy(str, num string) bool {
-	f, _ := ToFloat(str)
-	p := int64(f)
-	q, _ := ToInt(num)
-	if q == 0 {
-		return false
-	}
-	return (p == 0) || (p%q == 0)
-}
-
-// IsNull checks if the string is null.
-func IsNull(str string) bool {
-	return len(str) == 0
-}
-
-// IsNotNull checks if the string is not null.
-func IsNotNull(str string) bool {
-	return !IsNull(str)
-}
-
-// HasWhitespaceOnly checks the string only contains whitespace
-func HasWhitespaceOnly(str string) bool {
-	return len(str) > 0 && rxHasWhitespaceOnly.MatchString(str)
-}
-
-// HasWhitespace checks if the string contains any whitespace
-func HasWhitespace(str string) bool {
-	return len(str) > 0 && rxHasWhitespace.MatchString(str)
-}
-
-// IsByteLength checks if the string's length (in bytes) falls in a range.
-func IsByteLength(str string, min, max int) bool {
-	return len(str) >= min && len(str) <= max
-}
-
-// IsUUIDv3 checks if the string is a UUID version 3.
-func IsUUIDv3(str string) bool {
-	return rxUUID3.MatchString(str)
-}
-
-// IsUUIDv4 checks if the string is a UUID version 4.
-func IsUUIDv4(str string) bool {
-	return rxUUID4.MatchString(str)
-}
-
-// IsUUIDv5 checks if the string is a UUID version 5.
-func IsUUIDv5(str string) bool {
-	return rxUUID5.MatchString(str)
-}
-
-// IsUUID checks if the string is a UUID (version 3, 4 or 5).
-func IsUUID(str string) bool {
-	return rxUUID.MatchString(str)
-}
-
-// IsCreditCard checks if the string is a credit card.
-func IsCreditCard(str string) bool {
-	sanitized := notNumberRegexp.ReplaceAllString(str, "")
-	if !rxCreditCard.MatchString(sanitized) {
-		return false
-	}
-	var sum int64
-	var digit string
-	var tmpNum int64
-	var shouldDouble bool
-	for i := len(sanitized) - 1; i >= 0; i-- {
-		digit = sanitized[i:(i + 1)]
-		tmpNum, _ = ToInt(digit)
-		if shouldDouble {
-			tmpNum *= 2
-			if tmpNum >= 10 {
-				sum += (tmpNum % 10) + 1
-			} else {
-				sum += tmpNum
-			}
-		} else {
-			sum += tmpNum
-		}
-		shouldDouble = !shouldDouble
-	}
-
-	return sum%10 == 0
-}
-
-// IsISBN10 checks if the string is an ISBN version 10.
-func IsISBN10(str string) bool {
-	return IsISBN(str, 10)
-}
-
-// IsISBN13 checks if the string is an ISBN version 13.
-func IsISBN13(str string) bool {
-	return IsISBN(str, 13)
-}
-
-// IsISBN checks if the string is an ISBN (version 10 or 13).
-// If version value is not equal to 10 or 13, it will be checks both variants.
-func IsISBN(str string, version int) bool {
-	sanitized := whiteSpacesAndMinus.ReplaceAllString(str, "")
-	var checksum int32
-	var i int32
-	if version == 10 {
-		if !rxISBN10.MatchString(sanitized) {
-			return false
-		}
-		for i = 0; i < 9; i++ {
-			checksum += (i + 1) * int32(sanitized[i]-'0')
-		}
-		if sanitized[9] == 'X' {
-			checksum += 10 * 10
-		} else {
-			checksum += 10 * int32(sanitized[9]-'0')
-		}
-		if checksum%11 == 0 {
-			return true
-		}
-		return false
-	} else if version == 13 {
-		if !rxISBN13.MatchString(sanitized) {
-			return false
-		}
-		factor := []int32{1, 3}
-		for i = 0; i < 12; i++ {
-			checksum += factor[i%2] * int32(sanitized[i]-'0')
-		}
-		return (int32(sanitized[12]-'0'))-((10-(checksum%10))%10) == 0
-	}
-	return IsISBN(str, 10) || IsISBN(str, 13)
-}
-
-// IsJSON checks if the string is valid JSON (note: uses json.Unmarshal).
-func IsJSON(str string) bool {
-	var js json.RawMessage
-	return json.Unmarshal([]byte(str), &js) == nil
-}
-
-// IsMultibyte checks if the string contains one or more multibyte chars. Empty string is valid.
-func IsMultibyte(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxMultibyte.MatchString(str)
-}
-
-// IsASCII checks if the string contains ASCII chars only. Empty string is valid.
-func IsASCII(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxASCII.MatchString(str)
-}
-
-// IsPrintableASCII checks if the string contains printable ASCII chars only. Empty string is valid.
-func IsPrintableASCII(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxPrintableASCII.MatchString(str)
-}
-
-// IsFullWidth checks if the string contains any full-width chars. Empty string is valid.
-func IsFullWidth(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxFullWidth.MatchString(str)
-}
-
-// IsHalfWidth checks if the string contains any half-width chars. Empty string is valid.
-func IsHalfWidth(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxHalfWidth.MatchString(str)
-}
-
-// IsVariableWidth checks if the string contains a mixture of full and half-width chars. Empty string is valid.
-func IsVariableWidth(str string) bool {
-	if IsNull(str) {
-		return true
-	}
-	return rxHalfWidth.MatchString(str) && rxFullWidth.MatchString(str)
-}
-
-// IsBase64 checks if a string is base64 encoded.
-func IsBase64(str string) bool {
-	return rxBase64.MatchString(str)
-}
-
-// IsFilePath checks is a string is Win or Unix file path and returns it's type.
-func IsFilePath(str string) (bool, int) {
-	if rxWinPath.MatchString(str) {
-		//check windows path limit see:
-		//  http://msdn.microsoft.com/en-us/library/aa365247(VS.85).aspx#maxpath
-		if len(str[3:]) > 32767 {
-			return false, Win
-		}
-		return true, Win
-	} else if rxUnixPath.MatchString(str) {
-		return true, Unix
-	}
-	return false, Unknown
-}
-
-// IsDataURI checks if a string is base64 encoded data URI such as an image
-func IsDataURI(str string) bool {
-	dataURI := strings.Split(str, ",")
-	if !rxDataURI.MatchString(dataURI[0]) {
-		return false
-	}
-	return IsBase64(dataURI[1])
-}
-
-// IsMagnetURI checks if a string is valid magnet URI
-func IsMagnetURI(str string) bool {
-	return rxMagnetURI.MatchString(str)
-}
-
-// IsISO3166Alpha2 checks if a string is valid two-letter country code
-func IsISO3166Alpha2(str string) bool {
-	for _, entry := range ISO3166List {
-		if str == entry.Alpha2Code {
-			return true
-		}
-	}
-	return false
-}
-
-// IsISO3166Alpha3 checks if a string is valid three-letter country code
-func IsISO3166Alpha3(str string) bool {
-	for _, entry := range ISO3166List {
-		if str == entry.Alpha3Code {
-			return true
-		}
-	}
-	return false
-}
-
-// IsISO693Alpha2 checks if a string is valid two-letter language code
-func IsISO693Alpha2(str string) bool {
-	for _, entry := range ISO693List {
-		if str == entry.Alpha2Code {
-			return true
-		}
-	}
-	return false
-}
-
-// IsISO693Alpha3b checks if a string is valid three-letter language code
-func IsISO693Alpha3b(str string) bool {
-	for _, entry := range ISO693List {
-		if str == entry.Alpha3bCode {
-			return true
-		}
-	}
-	return false
-}
-
-// IsDNSName will validate the given string as a DNS name
-func IsDNSName(str string) bool {
-	if str == "" || len(strings.Replace(str, ".", "", -1)) > 255 {
-		// constraints already violated
-		return false
-	}
-	return !IsIP(str) && rxDNSName.MatchString(str)
-}
-
-// IsHash checks if a string is a hash of type algorithm.
-// Algorithm is one of ['md4', 'md5', 'sha1', 'sha256', 'sha384', 'sha512', 'ripemd128', 'ripemd160', 'tiger128', 'tiger160', 'tiger192', 'crc32', 'crc32b']
-func IsHash(str string, algorithm string) bool {
-	var len string
-	algo := strings.ToLower(algorithm)
-
-	if algo == "crc32" || algo == "crc32b" {
-		len = "8"
-	} else if algo == "md5" || algo == "md4" || algo == "ripemd128" || algo == "tiger128" {
-		len = "32"
-	} else if algo == "sha1" || algo == "ripemd160" || algo == "tiger160" {
-		len = "40"
-	} else if algo == "tiger192" {
-		len = "48"
-	} else if algo == "sha256" {
-		len = "64"
-	} else if algo == "sha384" {
-		len = "96"
-	} else if algo == "sha512" {
-		len = "128"
-	} else {
-		return false
-	}
-
-	return Matches(str, "^[a-f0-9]{"+len+"}$")
-}
-
-// IsSHA512 checks is a string is a SHA512 hash. Alias for `IsHash(str, "sha512")`
-func IsSHA512(str string) bool {
-	return IsHash(str, "sha512")
-}
-
-// IsSHA384 checks is a string is a SHA384 hash. Alias for `IsHash(str, "sha384")`
-func IsSHA384(str string) bool {
-	return IsHash(str, "sha384")
-}
-
-// IsSHA256 checks is a string is a SHA256 hash. Alias for `IsHash(str, "sha256")`
-func IsSHA256(str string) bool {
-	return IsHash(str, "sha256")
-}
-
-// IsTiger192 checks is a string is a Tiger192 hash. Alias for `IsHash(str, "tiger192")`
-func IsTiger192(str string) bool {
-	return IsHash(str, "tiger192")
-}
-
-// IsTiger160 checks is a string is a Tiger160 hash. Alias for `IsHash(str, "tiger160")`
-func IsTiger160(str string) bool {
-	return IsHash(str, "tiger160")
-}
-
-// IsRipeMD160 checks is a string is a RipeMD160 hash. Alias for `IsHash(str, "ripemd160")`
-func IsRipeMD160(str string) bool {
-	return IsHash(str, "ripemd160")
-}
-
-// IsSHA1 checks is a string is a SHA-1 hash. Alias for `IsHash(str, "sha1")`
-func IsSHA1(str string) bool {
-	return IsHash(str, "sha1")
-}
-
-// IsTiger128 checks is a string is a Tiger128 hash. Alias for `IsHash(str, "tiger128")`
-func IsTiger128(str string) bool {
-	return IsHash(str, "tiger128")
-}
-
-// IsRipeMD128 checks is a string is a RipeMD128 hash. Alias for `IsHash(str, "ripemd128")`
-func IsRipeMD128(str string) bool {
-	return IsHash(str, "ripemd128")
-}
-
-// IsCRC32 checks is a string is a CRC32 hash. Alias for `IsHash(str, "crc32")`
-func IsCRC32(str string) bool {
-	return IsHash(str, "crc32")
-}
-
-// IsCRC32b checks is a string is a CRC32b hash. Alias for `IsHash(str, "crc32b")`
-func IsCRC32b(str string) bool {
-	return IsHash(str, "crc32b")
-}
-
-// IsMD5 checks is a string is a MD5 hash. Alias for `IsHash(str, "md5")`
-func IsMD5(str string) bool {
-	return IsHash(str, "md5")
-}
-
-// IsMD4 checks is a string is a MD4 hash. Alias for `IsHash(str, "md4")`
-func IsMD4(str string) bool {
-	return IsHash(str, "md4")
-}
-
-// IsDialString validates the given string for usage with the various Dial() functions
-func IsDialString(str string) bool {
-	if h, p, err := net.SplitHostPort(str); err == nil && h != "" && p != "" && (IsDNSName(h) || IsIP(h)) && IsPort(p) {
-		return true
-	}
-
-	return false
-}
-
-// IsIP checks if a string is either IP version 4 or 6. Alias for `net.ParseIP`
-func IsIP(str string) bool {
-	return net.ParseIP(str) != nil
-}
-
-// IsPort checks if a string represents a valid port
-func IsPort(str string) bool {
-	if i, err := strconv.Atoi(str); err == nil && i > 0 && i < 65536 {
-		return true
-	}
-	return false
-}
-
-// IsIPv4 checks if the string is an IP version 4.
-func IsIPv4(str string) bool {
-	ip := net.ParseIP(str)
-	return ip != nil && strings.Contains(str, ".")
-}
-
-// IsIPv6 checks if the string is an IP version 6.
-func IsIPv6(str string) bool {
-	ip := net.ParseIP(str)
-	return ip != nil && strings.Contains(str, ":")
-}
-
-// IsCIDR checks if the string is an valid CIDR notiation (IPV4 & IPV6)
-func IsCIDR(str string) bool {
-	_, _, err := net.ParseCIDR(str)
-	return err == nil
-}
-
-// IsMAC checks if a string is valid MAC address.
-// Possible MAC formats:
-// 01:23:45:67:89:ab
-// 01:23:45:67:89:ab:cd:ef
-// 01-23-45-67-89-ab
-// 01-23-45-67-89-ab-cd-ef
-// 0123.4567.89ab
-// 0123.4567.89ab.cdef
-func IsMAC(str string) bool {
-	_, err := net.ParseMAC(str)
-	return err == nil
-}
-
-// IsHost checks if the string is a valid IP (both v4 and v6) or a valid DNS name
-func IsHost(str string) bool {
-	return IsIP(str) || IsDNSName(str)
-}
-
-// IsMongoID checks if the string is a valid hex-encoded representation of a MongoDB ObjectId.
-func IsMongoID(str string) bool {
-	return rxHexadecimal.MatchString(str) && (len(str) == 24)
-}
-
-// IsLatitude checks if a string is valid latitude.
-func IsLatitude(str string) bool {
-	return rxLatitude.MatchString(str)
-}
-
-// IsLongitude checks if a string is valid longitude.
-func IsLongitude(str string) bool {
-	return rxLongitude.MatchString(str)
-}
-
-// IsIMEI checks if a string is valid IMEI
-func IsIMEI(str string) bool {
-	return rxIMEI.MatchString(str)
-}
-
-// IsIMSI checks if a string is valid IMSI
-func IsIMSI(str string) bool {
-	if !rxIMSI.MatchString(str) {
-		return false
-	}
-
-	mcc, err := strconv.ParseInt(str[0:3], 10, 32)
-	if err != nil {
-		return false
-	}
-
-	switch mcc {
-	case 202, 204, 206, 208, 212, 213, 214, 216, 218, 219:
-	case 220, 221, 222, 226, 228, 230, 231, 232, 234, 235:
-	case 238, 240, 242, 244, 246, 247, 248, 250, 255, 257:
-	case 259, 260, 262, 266, 268, 270, 272, 274, 276, 278:
-	case 280, 282, 283, 284, 286, 288, 289, 290, 292, 293:
-	case 294, 295, 297, 302, 308, 310, 311, 312, 313, 314:
-	case 315, 316, 330, 332, 334, 338, 340, 342, 344, 346:
-	case 348, 350, 352, 354, 356, 358, 360, 362, 363, 364:
-	case 365, 366, 368, 370, 372, 374, 376, 400, 401, 402:
-	case 404, 405, 406, 410, 412, 413, 414, 415, 416, 417:
-	case 418, 419, 420, 421, 422, 424, 425, 426, 427, 428:
-	case 429, 430, 431, 432, 434, 436, 437, 438, 440, 441:
-	case 450, 452, 454, 455, 456, 457, 460, 461, 466, 467:
-	case 470, 472, 502, 505, 510, 514, 515, 520, 525, 528:
-	case 530, 536, 537, 539, 540, 541, 542, 543, 544, 545:
-	case 546, 547, 548, 549, 550, 551, 552, 553, 554, 555:
-	case 602, 603, 604, 605, 606, 607, 608, 609, 610, 611:
-	case 612, 613, 614, 615, 616, 617, 618, 619, 620, 621:
-	case 622, 623, 624, 625, 626, 627, 628, 629, 630, 631:
-	case 632, 633, 634, 635, 636, 637, 638, 639, 640, 641:
-	case 642, 643, 645, 646, 647, 648, 649, 650, 651, 652:
-	case 653, 654, 655, 657, 658, 659, 702, 704, 706, 708:
-	case 710, 712, 714, 716, 722, 724, 730, 732, 734, 736:
-	case 738, 740, 742, 744, 746, 748, 750, 995:
-		return true
-	default:
-		return false
-	}
-	return true
-}
-
-// IsRsaPublicKey checks if a string is valid public key with provided length
-func IsRsaPublicKey(str string, keylen int) bool {
-	bb := bytes.NewBufferString(str)
-	pemBytes, err := ioutil.ReadAll(bb)
-	if err != nil {
-		return false
-	}
-	block, _ := pem.Decode(pemBytes)
-	if block != nil && block.Type != "PUBLIC KEY" {
-		return false
-	}
-	var der []byte
-
-	if block != nil {
-		der = block.Bytes
-	} else {
-		der, err = base64.StdEncoding.DecodeString(str)
-		if err != nil {
-			return false
-		}
-	}
-
-	key, err := x509.ParsePKIXPublicKey(der)
-	if err != nil {
-		return false
-	}
-	pubkey, ok := key.(*rsa.PublicKey)
-	if !ok {
-		return false
-	}
-	bitlen := len(pubkey.N.Bytes()) * 8
-	return bitlen == int(keylen)
-}
-
-func toJSONName(tag string) string {
-	if tag == "" {
-		return ""
-	}
-
-	// JSON name always comes first. If there's no options then split[0] is
-	// JSON name, if JSON name is not set, then split[0] is an empty string.
-	split := strings.SplitN(tag, ",", 2)
-
-	name := split[0]
-
-	// However it is possible that the field is skipped when
-	// (de-)serializing from/to JSON, in which case assume that there is no
-	// tag name to use
-	if name == "-" {
-		return ""
-	}
-	return name
-}
-
-func prependPathToErrors(err error, path string) error {
-	switch err2 := err.(type) {
-	case Error:
-		err2.Path = append([]string{path}, err2.Path...)
-		return err2
-	case Errors:
-		errors := err2.Errors()
-		for i, err3 := range errors {
-			errors[i] = prependPathToErrors(err3, path)
-		}
-		return err2
-	}
-	return err
-}
-
-// ValidateMap use validation map for fields.
-// result will be equal to `false` if there are any errors.
-// s is the map containing the data to be validated.
-// m is the validation map in the form:
-//   map[string]interface{}{"name":"required,alpha","address":map[string]interface{}{"line1":"required,alphanum"}}
-func ValidateMap(s map[string]interface{}, m map[string]interface{}) (bool, error) {
-	if s == nil {
-		return true, nil
-	}
-	result := true
-	var err error
-	var errs Errors
-	var index int
-	val := reflect.ValueOf(s)
-	for key, value := range s {
-		presentResult := true
-		validator, ok := m[key]
-		if !ok {
-			presentResult = false
-			var err error
-			err = fmt.Errorf("all map keys has to be present in the validation map; got %s", key)
-			err = prependPathToErrors(err, key)
-			errs = append(errs, err)
-		}
-		valueField := reflect.ValueOf(value)
-		mapResult := true
-		typeResult := true
-		structResult := true
-		resultField := true
-		switch subValidator := validator.(type) {
-		case map[string]interface{}:
-			var err error
-			if v, ok := value.(map[string]interface{}); !ok {
-				mapResult = false
-				err = fmt.Errorf("map validator has to be for the map type only; got %s", valueField.Type().String())
-				err = prependPathToErrors(err, key)
-				errs = append(errs, err)
-			} else {
-				mapResult, err = ValidateMap(v, subValidator)
-				if err != nil {
-					mapResult = false
-					err = prependPathToErrors(err, key)
-					errs = append(errs, err)
-				}
-			}
-		case string:
-			if (valueField.Kind() == reflect.Struct ||
-				(valueField.Kind() == reflect.Ptr && valueField.Elem().Kind() == reflect.Struct)) &&
-				subValidator != "-" {
-				var err error
-				structResult, err = ValidateStruct(valueField.Interface())
-				if err != nil {
-					err = prependPathToErrors(err, key)
-					errs = append(errs, err)
-				}
-			}
-			resultField, err = typeCheck(valueField, reflect.StructField{
-				Name:      key,
-				PkgPath:   "",
-				Type:      val.Type(),
-				Tag:       reflect.StructTag(fmt.Sprintf("%s:%q", tagName, subValidator)),
-				Offset:    0,
-				Index:     []int{index},
-				Anonymous: false,
-			}, val, nil)
-			if err != nil {
-				errs = append(errs, err)
-			}
-		case nil:
-			// already handlerd when checked before
-		default:
-			typeResult = false
-			err = fmt.Errorf("map validator has to be either map[string]interface{} or string; got %s", valueField.Type().String())
-			err = prependPathToErrors(err, key)
-			errs = append(errs, err)
-		}
-		result = result && presentResult && typeResult && resultField && structResult && mapResult
-		index++
-	}
-	// checks required keys
-	requiredResult := true
-	for key, value := range m {
-		if schema, ok := value.(string); ok {
-			tags := parseTagIntoMap(schema)
-			if required, ok := tags["required"]; ok {
-				if _, ok := s[key]; !ok {
-					requiredResult = false
-					if required.customErrorMessage != "" {
-						err = Error{key, fmt.Errorf(required.customErrorMessage), true, "required", []string{}}
-					} else {
-						err = Error{key, fmt.Errorf("required field missing"), false, "required", []string{}}
-					}
-					errs = append(errs, err)
-				}
-			}
-		}
-	}
-
-	if len(errs) > 0 {
-		err = errs
-	}
-	return result && requiredResult, err
-}
-
-// ValidateStruct use tags for fields.
-// result will be equal to `false` if there are any errors.
-// todo currently there is no guarantee that errors will be returned in predictable order (tests may to fail)
-func ValidateStruct(s interface{}) (bool, error) {
-	if s == nil {
-		return true, nil
-	}
-	result := true
-	var err error
-	val := reflect.ValueOf(s)
-	if val.Kind() == reflect.Interface || val.Kind() == reflect.Ptr {
-		val = val.Elem()
-	}
-	// we only accept structs
-	if val.Kind() != reflect.Struct {
-		return false, fmt.Errorf("function only accepts structs; got %s", val.Kind())
-	}
-	var errs Errors
-	for i := 0; i < val.NumField(); i++ {
-		valueField := val.Field(i)
-		typeField := val.Type().Field(i)
-		if typeField.PkgPath != "" {
-			continue // Private field
-		}
-		structResult := true
-		if valueField.Kind() == reflect.Interface {
-			valueField = valueField.Elem()
-		}
-		if (valueField.Kind() == reflect.Struct ||
-			(valueField.Kind() == reflect.Ptr && valueField.Elem().Kind() == reflect.Struct)) &&
-			typeField.Tag.Get(tagName) != "-" {
-			var err error
-			structResult, err = ValidateStruct(valueField.Interface())
-			if err != nil {
-				err = prependPathToErrors(err, typeField.Name)
-				errs = append(errs, err)
-			}
-		}
-		resultField, err2 := typeCheck(valueField, typeField, val, nil)
-		if err2 != nil {
-
-			// Replace structure name with JSON name if there is a tag on the variable
-			jsonTag := toJSONName(typeField.Tag.Get("json"))
-			if jsonTag != "" {
-				switch jsonError := err2.(type) {
-				case Error:
-					jsonError.Name = jsonTag
-					err2 = jsonError
-				case Errors:
-					for i2, err3 := range jsonError {
-						switch customErr := err3.(type) {
-						case Error:
-							customErr.Name = jsonTag
-							jsonError[i2] = customErr
-						}
-					}
-
-					err2 = jsonError
-				}
-			}
-
-			errs = append(errs, err2)
-		}
-		result = result && resultField && structResult
-	}
-	if len(errs) > 0 {
-		err = errs
-	}
-	return result, err
-}
-
-// ValidateStructAsync performs async validation of the struct and returns results through the channels
-func ValidateStructAsync(s interface{}) (<-chan bool, <-chan error) {
-	res := make(chan bool)
-	errors := make(chan error)
-
-	go func() {
-		defer close(res)
-		defer close(errors)
-
-		isValid, isFailed := ValidateStruct(s)
-
-		res <- isValid
-		errors <- isFailed
-	}()
-
-	return res, errors
-}
-
-// ValidateMapAsync performs async validation of the map and returns results through the channels
-func ValidateMapAsync(s map[string]interface{}, m map[string]interface{}) (<-chan bool, <-chan error) {
-	res := make(chan bool)
-	errors := make(chan error)
-
-	go func() {
-		defer close(res)
-		defer close(errors)
-
-		isValid, isFailed := ValidateMap(s, m)
-
-		res <- isValid
-		errors <- isFailed
-	}()
-
-	return res, errors
-}
-
-// parseTagIntoMap parses a struct tag `valid:required~Some error message,length(2|3)` into map[string]string{"required": "Some error message", "length(2|3)": ""}
-func parseTagIntoMap(tag string) tagOptionsMap {
-	optionsMap := make(tagOptionsMap)
-	options := strings.Split(tag, ",")
-
-	for i, option := range options {
-		option = strings.TrimSpace(option)
-
-		validationOptions := strings.Split(option, "~")
-		if !isValidTag(validationOptions[0]) {
-			continue
-		}
-		if len(validationOptions) == 2 {
-			optionsMap[validationOptions[0]] = tagOption{validationOptions[0], validationOptions[1], i}
-		} else {
-			optionsMap[validationOptions[0]] = tagOption{validationOptions[0], "", i}
-		}
-	}
-	return optionsMap
-}
-
-func isValidTag(s string) bool {
-	if s == "" {
-		return false
-	}
-	for _, c := range s {
-		switch {
-		case strings.ContainsRune("\\'\"!#$%&()*+-./:<=>?@[]^_{|}~ ", c):
-			// Backslash and quote chars are reserved, but
-			// otherwise any punctuation chars are allowed
-			// in a tag name.
-		default:
-			if !unicode.IsLetter(c) && !unicode.IsDigit(c) {
-				return false
-			}
-		}
-	}
-	return true
-}
-
-// IsSSN will validate the given string as a U.S. Social Security Number
-func IsSSN(str string) bool {
-	if str == "" || len(str) != 11 {
-		return false
-	}
-	return rxSSN.MatchString(str)
-}
-
-// IsSemver checks if string is valid semantic version
-func IsSemver(str string) bool {
-	return rxSemver.MatchString(str)
-}
-
-// IsType checks if interface is of some type
-func IsType(v interface{}, params ...string) bool {
-	if len(params) == 1 {
-		typ := params[0]
-		return strings.Replace(reflect.TypeOf(v).String(), " ", "", -1) == strings.Replace(typ, " ", "", -1)
-	}
-	return false
-}
-
-// IsTime checks if string is valid according to given format
-func IsTime(str string, format string) bool {
-	_, err := time.Parse(format, str)
-	return err == nil
-}
-
-// IsUnixTime checks if string is valid unix timestamp value
-func IsUnixTime(str string) bool {
-	if _, err := strconv.Atoi(str); err == nil {
-		return true
-	}
-	return false
-}
-
-// IsRFC3339 checks if string is valid timestamp value according to RFC3339
-func IsRFC3339(str string) bool {
-	return IsTime(str, time.RFC3339)
-}
-
-// IsRFC3339WithoutZone checks if string is valid timestamp value according to RFC3339 which excludes the timezone.
-func IsRFC3339WithoutZone(str string) bool {
-	return IsTime(str, rfc3339WithoutZone)
-}
-
-// IsISO4217 checks if string is valid ISO currency code
-func IsISO4217(str string) bool {
-	for _, currency := range ISO4217List {
-		if str == currency {
-			return true
-		}
-	}
-
-	return false
-}
-
-// ByteLength checks string's length
-func ByteLength(str string, params ...string) bool {
-	if len(params) == 2 {
-		min, _ := ToInt(params[0])
-		max, _ := ToInt(params[1])
-		return len(str) >= int(min) && len(str) <= int(max)
-	}
-
-	return false
-}
-
-// RuneLength checks string's length
-// Alias for StringLength
-func RuneLength(str string, params ...string) bool {
-	return StringLength(str, params...)
-}
-
-// IsRsaPub checks whether string is valid RSA key
-// Alias for IsRsaPublicKey
-func IsRsaPub(str string, params ...string) bool {
-	if len(params) == 1 {
-		len, _ := ToInt(params[0])
-		return IsRsaPublicKey(str, int(len))
-	}
-
-	return false
-}
-
-// StringMatches checks if a string matches a given pattern.
-func StringMatches(s string, params ...string) bool {
-	if len(params) == 1 {
-		pattern := params[0]
-		return Matches(s, pattern)
-	}
-	return false
-}
-
-// StringLength checks string's length (including multi byte strings)
-func StringLength(str string, params ...string) bool {
-
-	if len(params) == 2 {
-		strLength := utf8.RuneCountInString(str)
-		min, _ := ToInt(params[0])
-		max, _ := ToInt(params[1])
-		return strLength >= int(min) && strLength <= int(max)
-	}
-
-	return false
-}
-
-// MinStringLength checks string's minimum length (including multi byte strings)
-func MinStringLength(str string, params ...string) bool {
-
-	if len(params) == 1 {
-		strLength := utf8.RuneCountInString(str)
-		min, _ := ToInt(params[0])
-		return strLength >= int(min)
-	}
-
-	return false
-}
-
-// MaxStringLength checks string's maximum length (including multi byte strings)
-func MaxStringLength(str string, params ...string) bool {
-
-	if len(params) == 1 {
-		strLength := utf8.RuneCountInString(str)
-		max, _ := ToInt(params[0])
-		return strLength <= int(max)
-	}
-
-	return false
-}
-
-// Range checks string's length
-func Range(str string, params ...string) bool {
-	if len(params) == 2 {
-		value, _ := ToFloat(str)
-		min, _ := ToFloat(params[0])
-		max, _ := ToFloat(params[1])
-		return InRange(value, min, max)
-	}
-
-	return false
-}
-
-// IsInRaw checks if string is in list of allowed values
-func IsInRaw(str string, params ...string) bool {
-	if len(params) == 1 {
-		rawParams := params[0]
-
-		parsedParams := strings.Split(rawParams, "|")
-
-		return IsIn(str, parsedParams...)
-	}
-
-	return false
-}
-
-// IsIn checks if string str is a member of the set of strings params
-func IsIn(str string, params ...string) bool {
-	for _, param := range params {
-		if str == param {
-			return true
-		}
-	}
-
-	return false
-}
-
-func checkRequired(v reflect.Value, t reflect.StructField, options tagOptionsMap) (bool, error) {
-	if nilPtrAllowedByRequired {
-		k := v.Kind()
-		if (k == reflect.Ptr || k == reflect.Interface) && v.IsNil() {
-			return true, nil
-		}
-	}
-
-	if requiredOption, isRequired := options["required"]; isRequired {
-		if len(requiredOption.customErrorMessage) > 0 {
-			return false, Error{t.Name, fmt.Errorf(requiredOption.customErrorMessage), true, "required", []string{}}
-		}
-		return false, Error{t.Name, fmt.Errorf("non zero value required"), false, "required", []string{}}
-	} else if _, isOptional := options["optional"]; fieldsRequiredByDefault && !isOptional {
-		return false, Error{t.Name, fmt.Errorf("Missing required field"), false, "required", []string{}}
-	}
-	// not required and empty is valid
-	return true, nil
-}
-
-func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options tagOptionsMap) (isValid bool, resultErr error) {
-	if !v.IsValid() {
-		return false, nil
-	}
-
-	tag := t.Tag.Get(tagName)
-
-	// checks if the field should be ignored
-	switch tag {
-	case "":
-		if v.Kind() != reflect.Slice && v.Kind() != reflect.Map {
-			if !fieldsRequiredByDefault {
-				return true, nil
-			}
-			return false, Error{t.Name, fmt.Errorf("All fields are required to at least have one validation defined"), false, "required", []string{}}
-		}
-	case "-":
-		return true, nil
-	}
-
-	isRootType := false
-	if options == nil {
-		isRootType = true
-		options = parseTagIntoMap(tag)
-	}
-
-	if isEmptyValue(v) {
-		// an empty value is not validated, checks only required
-		isValid, resultErr = checkRequired(v, t, options)
-		for key := range options {
-			delete(options, key)
-		}
-		return isValid, resultErr
-	}
-
-	var customTypeErrors Errors
-	optionsOrder := options.orderedKeys()
-	for _, validatorName := range optionsOrder {
-		validatorStruct := options[validatorName]
-		if validatefunc, ok := CustomTypeTagMap.Get(validatorName); ok {
-			delete(options, validatorName)
-
-			if result := validatefunc(v.Interface(), o.Interface()); !result {
-				if len(validatorStruct.customErrorMessage) > 0 {
-					customTypeErrors = append(customTypeErrors, Error{Name: t.Name, Err: TruncatingErrorf(validatorStruct.customErrorMessage, fmt.Sprint(v), validatorName), CustomErrorMessageExists: true, Validator: stripParams(validatorName)})
-					continue
-				}
-				customTypeErrors = append(customTypeErrors, Error{Name: t.Name, Err: fmt.Errorf("%s does not validate as %s", fmt.Sprint(v), validatorName), CustomErrorMessageExists: false, Validator: stripParams(validatorName)})
-			}
-		}
-	}
-
-	if len(customTypeErrors.Errors()) > 0 {
-		return false, customTypeErrors
-	}
-
-	if isRootType {
-		// Ensure that we've checked the value by all specified validators before report that the value is valid
-		defer func() {
-			delete(options, "optional")
-			delete(options, "required")
-
-			if isValid && resultErr == nil && len(options) != 0 {
-				optionsOrder := options.orderedKeys()
-				for _, validator := range optionsOrder {
-					isValid = false
-					resultErr = Error{t.Name, fmt.Errorf(
-						"The following validator is invalid or can't be applied to the field: %q", validator), false, stripParams(validator), []string{}}
-					return
-				}
-			}
-		}()
-	}
-
-	for _, validatorSpec := range optionsOrder {
-		validatorStruct := options[validatorSpec]
-		var negate bool
-		validator := validatorSpec
-		customMsgExists := len(validatorStruct.customErrorMessage) > 0
-
-		// checks whether the tag looks like '!something' or 'something'
-		if validator[0] == '!' {
-			validator = validator[1:]
-			negate = true
-		}
-
-		// checks for interface param validators
-		for key, value := range InterfaceParamTagRegexMap {
-			ps := value.FindStringSubmatch(validator)
-			if len(ps) == 0 {
-				continue
-			}
-
-			validatefunc, ok := InterfaceParamTagMap[key]
-			if !ok {
-				continue
-			}
-
-			delete(options, validatorSpec)
-
-			field := fmt.Sprint(v)
-			if result := validatefunc(v.Interface(), ps[1:]...); (!result && !negate) || (result && negate) {
-				if customMsgExists {
-					return false, Error{t.Name, TruncatingErrorf(validatorStruct.customErrorMessage, field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-				}
-				if negate {
-					return false, Error{t.Name, fmt.Errorf("%s does validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-				}
-				return false, Error{t.Name, fmt.Errorf("%s does not validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-			}
-		}
-	}
-
-	switch v.Kind() {
-	case reflect.Bool,
-		reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
-		reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr,
-		reflect.Float32, reflect.Float64,
-		reflect.String:
-		// for each tag option checks the map of validator functions
-		for _, validatorSpec := range optionsOrder {
-			validatorStruct := options[validatorSpec]
-			var negate bool
-			validator := validatorSpec
-			customMsgExists := len(validatorStruct.customErrorMessage) > 0
-
-			// checks whether the tag looks like '!something' or 'something'
-			if validator[0] == '!' {
-				validator = validator[1:]
-				negate = true
-			}
-
-			// checks for param validators
-			for key, value := range ParamTagRegexMap {
-				ps := value.FindStringSubmatch(validator)
-				if len(ps) == 0 {
-					continue
-				}
-
-				validatefunc, ok := ParamTagMap[key]
-				if !ok {
-					continue
-				}
-
-				delete(options, validatorSpec)
-
-				switch v.Kind() {
-				case reflect.String,
-					reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
-					reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64,
-					reflect.Float32, reflect.Float64:
-
-					field := fmt.Sprint(v) // make value into string, then validate with regex
-					if result := validatefunc(field, ps[1:]...); (!result && !negate) || (result && negate) {
-						if customMsgExists {
-							return false, Error{t.Name, TruncatingErrorf(validatorStruct.customErrorMessage, field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-						}
-						if negate {
-							return false, Error{t.Name, fmt.Errorf("%s does validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-						}
-						return false, Error{t.Name, fmt.Errorf("%s does not validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-					}
-				default:
-					// type not yet supported, fail
-					return false, Error{t.Name, fmt.Errorf("Validator %s doesn't support kind %s", validator, v.Kind()), false, stripParams(validatorSpec), []string{}}
-				}
-			}
-
-			if validatefunc, ok := TagMap[validator]; ok {
-				delete(options, validatorSpec)
-
-				switch v.Kind() {
-				case reflect.String,
-					reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
-					reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64,
-					reflect.Float32, reflect.Float64:
-					field := fmt.Sprint(v) // make value into string, then validate with regex
-					if result := validatefunc(field); !result && !negate || result && negate {
-						if customMsgExists {
-							return false, Error{t.Name, TruncatingErrorf(validatorStruct.customErrorMessage, field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-						}
-						if negate {
-							return false, Error{t.Name, fmt.Errorf("%s does validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-						}
-						return false, Error{t.Name, fmt.Errorf("%s does not validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}}
-					}
-				default:
-					//Not Yet Supported Types (Fail here!)
-					err := fmt.Errorf("Validator %s doesn't support kind %s for value %v", validator, v.Kind(), v)
-					return false, Error{t.Name, err, false, stripParams(validatorSpec), []string{}}
-				}
-			}
-		}
-		return true, nil
-	case reflect.Map:
-		if v.Type().Key().Kind() != reflect.String {
-			return false, &UnsupportedTypeError{v.Type()}
-		}
-		var sv stringValues
-		sv = v.MapKeys()
-		sort.Sort(sv)
-		result := true
-		for i, k := range sv {
-			var resultItem bool
-			var err error
-			if v.MapIndex(k).Kind() != reflect.Struct {
-				resultItem, err = typeCheck(v.MapIndex(k), t, o, options)
-				if err != nil {
-					return false, err
-				}
-			} else {
-				resultItem, err = ValidateStruct(v.MapIndex(k).Interface())
-				if err != nil {
-					err = prependPathToErrors(err, t.Name+"."+sv[i].Interface().(string))
-					return false, err
-				}
-			}
-			result = result && resultItem
-		}
-		return result, nil
-	case reflect.Slice, reflect.Array:
-		result := true
-		for i := 0; i < v.Len(); i++ {
-			var resultItem bool
-			var err error
-			if v.Index(i).Kind() != reflect.Struct {
-				resultItem, err = typeCheck(v.Index(i), t, o, options)
-				if err != nil {
-					return false, err
-				}
-			} else {
-				resultItem, err = ValidateStruct(v.Index(i).Interface())
-				if err != nil {
-					err = prependPathToErrors(err, t.Name+"."+strconv.Itoa(i))
-					return false, err
-				}
-			}
-			result = result && resultItem
-		}
-		return result, nil
-	case reflect.Interface:
-		// If the value is an interface then encode its element
-		if v.IsNil() {
-			return true, nil
-		}
-		return ValidateStruct(v.Interface())
-	case reflect.Ptr:
-		// If the value is a pointer then checks its element
-		if v.IsNil() {
-			return true, nil
-		}
-		return typeCheck(v.Elem(), t, o, options)
-	case reflect.Struct:
-		return true, nil
-	default:
-		return false, &UnsupportedTypeError{v.Type()}
-	}
-}
-
-func stripParams(validatorString string) string {
-	return paramsRegexp.ReplaceAllString(validatorString, "")
-}
-
-// isEmptyValue checks whether value empty or not
-func isEmptyValue(v reflect.Value) bool {
-	switch v.Kind() {
-	case reflect.String, reflect.Array:
-		return v.Len() == 0
-	case reflect.Map, reflect.Slice:
-		return v.Len() == 0 || v.IsNil()
-	case reflect.Bool:
-		return !v.Bool()
-	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
-		return v.Int() == 0
-	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
-		return v.Uint() == 0
-	case reflect.Float32, reflect.Float64:
-		return v.Float() == 0
-	case reflect.Interface, reflect.Ptr:
-		return v.IsNil()
-	}
-
-	return reflect.DeepEqual(v.Interface(), reflect.Zero(v.Type()).Interface())
-}
-
-// ErrorByField returns error for specified field of the struct
-// validated by ValidateStruct or empty string if there are no errors
-// or this field doesn't exists or doesn't have any errors.
-func ErrorByField(e error, field string) string {
-	if e == nil {
-		return ""
-	}
-	return ErrorsByField(e)[field]
-}
-
-// ErrorsByField returns map of errors of the struct validated
-// by ValidateStruct or empty map if there are no errors.
-func ErrorsByField(e error) map[string]string {
-	m := make(map[string]string)
-	if e == nil {
-		return m
-	}
-	// prototype for ValidateStruct
-
-	switch e := e.(type) {
-	case Error:
-		m[e.Name] = e.Err.Error()
-	case Errors:
-		for _, item := range e.Errors() {
-			n := ErrorsByField(item)
-			for k, v := range n {
-				m[k] = v
-			}
-		}
-	}
-
-	return m
-}
-
-// Error returns string equivalent for reflect.Type
-func (e *UnsupportedTypeError) Error() string {
-	return "validator: unsupported type: " + e.Type.String()
-}
-
-func (sv stringValues) Len() int           { return len(sv) }
-func (sv stringValues) Swap(i, j int)      { sv[i], sv[j] = sv[j], sv[i] }
-func (sv stringValues) Less(i, j int) bool { return sv.get(i) < sv.get(j) }
-func (sv stringValues) get(i int) string   { return sv[i].String() }

+ 51 - 6
fieldproject_com/common.toml

@@ -1,12 +1,21 @@
-[buyer]
-
-
-[winner]
-
 
 [db]
 
 [db.mongo]
+addr = "192.168.3.207:27001"
+dbname = "qfw_data"
+size = 5
+user = "root"
+password = "root"
+
+[db.mongo1]
+addr = "192.168.3.207:27092"
+dbname = "wjh"
+size = 5
+user = ""
+password = ""
+
+[db.mongo2]
 addr = "192.168.3.207:27092"
 dbname = "zhengkun"
 size = 5
@@ -14,12 +23,48 @@ user = ""
 password = ""
 
 [db.mysql]
+# mysql: [username[:password]@][protocol[(address)]]/dbname[?param1=value1&...&paramN=valueN]
+#        root:123456@tcp(localhost:3306)/crocodile?charset=utf8mb4&parseTime=True&loc=Local
+#drivename = "mysql"
+#dsn = "root:=PDT49#80Z!RVv52_z@tcp(192.168.3.217:4000)/medical_fileld_data?charset=utf8mb4&parseTime=True&loc=Local"
 addr = "192.168.3.217:4000"
-dbname = "field_medical_data"
+dbnameBasic = "global_common_data"
+dbnameMedical = "medical_field_data"
 size = 5
 user = "root"
 password = "=PDT49#80Z!RVv52_z"
 
+maxidle = 10
+maxconn = 20
+maxquerytime = "10s"
+
+[db.es]
+addr = "http://192.168.3.206:9800"
+size = 5
+indexm = "medical_institution_v1"
+typem = "medical_institution"
+indexs = "supplier_product_v1"
+types = "supplier_product"
+
+[db.es.fieldm]
+id = "int"
+company_id = "string"
+mi_name = "string"
+alias = "string"
+area_code = "string"
+level_code = "string"
+mi_type_code = "string"
+business_type = "int"
+sdequipment = "string"
+#fieldarrs = ["id", "company_id", "supplier", "productlist", "business_model", "area_code"]
+[db.es.fields]
+id = "int"
+company_id = "string"
+supplier = "string"
+productlist = ""
+business_model = "string"
+area_code = "string"
+
 # 日志
 [log]
 # 日志路径,为空将输出控制台

+ 28 - 7
fieldproject_com/config/conf.go

@@ -39,8 +39,11 @@ type Log struct {
 }
 
 type Db struct {
-	Mongo mgo
-	Mysql mysql
+	Mongo  mgo
+	Mongo1 mgo
+	Mongo2 mgo
+	Mysql  mysql
+	Es     es
 }
 
 type mgo struct {
@@ -52,11 +55,29 @@ type mgo struct {
 }
 
 type mysql struct {
-	Addr     string
-	Dbname   string
-	Size     int
-	User     string
-	Password string
+	Addr          string
+	DbnameBasic   string
+	DbnameMedical string
+	Size          int
+	User          string
+	Password      string
+
+	Drivename    string
+	Dsn          string
+	MaxIdle      int
+	MaxConn      int
+	MaxQueryTime duration
+}
+
+type es struct {
+	Addr   string
+	Size   int
+	IndexM string
+	TypeM  string
+	IndexS string
+	TypeS  string
+	FieldM map[string]interface{}
+	FieldS map[string]interface{}
 }
 
 type duration struct {

+ 33 - 1
fieldproject_com/config/conf_test.go

@@ -23,12 +23,44 @@ dbname = "qfw"
 size = 10
 user = ""
 password = ""
+[db.mongo1]
+addr = "192.168.3.207:27092"
+dbname = "wjh"
+size = 5
+user = ""
+password = ""
+[db.mysql]
+addr = "192.168.3.217:4000"
+dbnameBasic = "global_common_data"
+dbnameMedical = "medical_fileld_data"
+size = 5
+user = "root"
+password = "=PDT49#80Z!RVv52_z"
+
+[db.es]
+addr = "http://192.168.3.206:9800"
+size = 5
+indexm = "medical_institution_v1"
+typem = "medical_institution"
+indexs = "supplier_product_v1"
+types = "supplier_product"
+
+[db.es.fieldarrm]
+id = "int"
+company_id = "string"
+mi_name = "string"
+alias = "string"
+area_code = "string"
+level_code = "string"
+mi_type_code = "string"
+business_type = "int"
+sdequipment = "string"
 `
 
 func TestInit(t *testing.T) {
 	testfile := "/tmp/crocodile.toml"
 	ioutil.WriteFile(testfile, []byte(confs), 0644)
 	Init(testfile)
-	t.Logf("%+v", Conf.DB.Mongo.Addr)
+	t.Logf("%+v", Conf.DB.Mysql.DbnameBasic)
 	os.Remove(testfile)
 }

+ 9 - 5
fieldproject_com/go.mod

@@ -3,10 +3,14 @@ module fieldproject_common
 go 1.16
 
 require (
+	app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f
 	github.com/BurntSushi/toml v1.2.0
-	go.uber.org/zap v1.21.0 // indirect
-	gopkg.in/yaml.v2 v2.4.0 // indirect
-	utils v0.0.0
+	github.com/inconshreveable/mousetrap v1.0.1 // indirect
+	github.com/mailru/easyjson v0.7.7 // indirect
+	github.com/olivere/elastic v6.2.37+incompatible // indirect
+	github.com/spf13/cobra v0.0.3
+	github.com/spf13/pflag v1.0.5 // indirect
+	go.uber.org/zap v1.22.0
+	gopkg.in/olivere/elastic.v1 v1.0.1
+	gopkg.in/olivere/elastic.v2 v2.0.61 // indirect
 )
-
-replace utils => ../common_utils

+ 54 - 95
fieldproject_com/go.sum

@@ -1,172 +1,131 @@
-github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
+app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f h1:5fUbVRwPM3oBsZgvG76Bia3I4SdwdBB6PvJ6B28Qkyc=
+app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f/go.mod h1:9PlRUNzirlF/LL1W7fA7koCudxJe3uO5nshDWlCnGo8=
 github.com/BurntSushi/toml v1.2.0 h1:Rt8g24XnyGTyglgET/PRUNlrUeu9F5L+7FilkXfZgs0=
 github.com/BurntSushi/toml v1.2.0/go.mod h1:CxXYINrC8qIiEnFrOxCa7Jy5BFHlXnUU2pbicEuybxQ=
 github.com/PuerkitoBio/goquery v1.8.0 h1:PJTF7AmFCFKk1N6V6jmKfrNH9tV5pNE6lZMkG0gta/U=
 github.com/PuerkitoBio/goquery v1.8.0/go.mod h1:ypIiRMtY7COPGk+I/YbZLbxsxn9g5ejnI2HSMtkjZvI=
 github.com/andybalholm/cascadia v1.3.1 h1:nhxRkql1kdYCc8Snf7D5/D3spOX+dBgjA6u8x004T2c=
 github.com/andybalholm/cascadia v1.3.1/go.mod h1:R4bJ1UQfqADjvDa4P6HZHLh/3OxWWEqc0Sk8XGwHqvA=
-github.com/aws/aws-sdk-go v1.29.15 h1:0ms/213murpsujhsnxnNKNeVouW60aJqSd992Ks3mxs=
-github.com/aws/aws-sdk-go v1.29.15/go.mod h1:1KvfttTE3SPKMpo8g2c6jL3ZKfXtFvKscTgahTma5Xg=
 github.com/benbjohnson/clock v1.1.0 h1:Q92kusRqC1XV2MjkWETPvjJVqKetz1OzxZB7mHJLju8=
 github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
 github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
 github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
 github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
-github.com/dchest/captcha v0.0.0-20200903113550-03f5f0333e1f h1:q/DpyjJjZs94bziQ7YkBmIlpqbVP7yw179rnzoNVX1M=
-github.com/dchest/captcha v0.0.0-20200903113550-03f5f0333e1f/go.mod h1:QGrK8vMWWHQYQ3QU9bw9Y9OPNfxccGzfb41qjvVeXtY=
+github.com/dchest/captcha v1.0.0 h1:vw+bm/qMFvTgcjQlYVTuQBJkarm5R0YSsDKhm1HZI2o=
+github.com/dchest/captcha v1.0.0/go.mod h1:7zoElIawLp7GUMLcj54K9kbw+jEyvz2K0FDdRRYhvWo=
+github.com/fortytw2/leaktest v1.3.0 h1:u8491cBMTQ8ft8aeV+adlcytMZylmA5nnwwkRZjI8vw=
 github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g=
-github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs=
-github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
-github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk=
-github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
-github.com/gobuffalo/attrs v0.0.0-20190224210810-a9411de4debd/go.mod h1:4duuawTqi2wkkpB4ePgWMaai6/Kc6WEz83bhFwpHzj0=
-github.com/gobuffalo/depgen v0.0.0-20190329151759-d478694a28d3/go.mod h1:3STtPUQYuzV0gBVOY3vy6CfMm/ljR4pABfrTeHNLHUY=
-github.com/gobuffalo/depgen v0.1.0/go.mod h1:+ifsuy7fhi15RWncXQQKjWS9JPkdah5sZvtHc2RXGlg=
-github.com/gobuffalo/envy v1.6.15/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI=
-github.com/gobuffalo/envy v1.7.0/go.mod h1:n7DRkBerg/aorDM8kbduw5dN3oXGswK5liaSCx4T5NI=
-github.com/gobuffalo/flect v0.1.0/go.mod h1:d2ehjJqGOH/Kjqcoz+F7jHTBbmDb38yXA598Hb50EGs=
-github.com/gobuffalo/flect v0.1.1/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI=
-github.com/gobuffalo/flect v0.1.3/go.mod h1:8JCgGVbRjJhVgD6399mQr4fx5rRfGKVzFjbj6RE/9UI=
-github.com/gobuffalo/genny v0.0.0-20190329151137-27723ad26ef9/go.mod h1:rWs4Z12d1Zbf19rlsn0nurr75KqhYp52EAGGxTbBhNk=
-github.com/gobuffalo/genny v0.0.0-20190403191548-3ca520ef0d9e/go.mod h1:80lIj3kVJWwOrXWWMRzzdhW3DsrdjILVil/SFKBzF28=
-github.com/gobuffalo/genny v0.1.0/go.mod h1:XidbUqzak3lHdS//TPu2OgiFB+51Ur5f7CSnXZ/JDvo=
-github.com/gobuffalo/genny v0.1.1/go.mod h1:5TExbEyY48pfunL4QSXxlDOmdsD44RRq4mVZ0Ex28Xk=
-github.com/gobuffalo/gitgen v0.0.0-20190315122116-cc086187d211/go.mod h1:vEHJk/E9DmhejeLeNt7UVvlSGv3ziL+djtTr3yyzcOw=
-github.com/gobuffalo/gogen v0.0.0-20190315121717-8f38393713f5/go.mod h1:V9QVDIxsgKNZs6L2IYiGR8datgMhB577vzTDqypH360=
-github.com/gobuffalo/gogen v0.1.0/go.mod h1:8NTelM5qd8RZ15VjQTFkAW6qOMx5wBbW4dSCS3BY8gg=
-github.com/gobuffalo/gogen v0.1.1/go.mod h1:y8iBtmHmGc4qa3urIyo1shvOD8JftTtfcKi+71xfDNE=
-github.com/gobuffalo/logger v0.0.0-20190315122211-86e12af44bc2/go.mod h1:QdxcLw541hSGtBnhUc4gaNIXRjiDppFGaDqzbrBd3v8=
-github.com/gobuffalo/mapi v1.0.1/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc=
-github.com/gobuffalo/mapi v1.0.2/go.mod h1:4VAGh89y6rVOvm5A8fKFxYG+wIW6LO1FMTG9hnKStFc=
-github.com/gobuffalo/packd v0.0.0-20190315124812-a385830c7fc0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4=
-github.com/gobuffalo/packd v0.1.0/go.mod h1:M2Juc+hhDXf/PnmBANFCqx4DM3wRbgDvnVWeG2RIxq4=
-github.com/gobuffalo/packr/v2 v2.0.9/go.mod h1:emmyGweYTm6Kdper+iywB6YK5YzuKchGtJQZ0Odn4pQ=
-github.com/gobuffalo/packr/v2 v2.2.0/go.mod h1:CaAwI0GPIAv+5wKLtv8Afwl+Cm78K/I/VCm/3ptBN+0=
-github.com/gobuffalo/syncx v0.0.0-20190224160051-33c29581e754/go.mod h1:HhnNqWY95UYwwW3uSASeV7vtgYkT2t16hJgV3AEPUpw=
+github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE=
+github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
 github.com/golang/snappy v0.0.1 h1:Qgr9rKW7uDUkrbSmQeiDsGa8SjGyCOGtuasMWwvp2P4=
 github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
-github.com/gomodule/redigo v1.8.2 h1:H5XSIre1MB5NbPYFp+i1NBbb5qN1W8Y8YAQoAYbkm8k=
-github.com/gomodule/redigo v1.8.2/go.mod h1:P9dn9mFrCBvWhGE1wpxx6fgq7BAeLBk+UUUzlpkBYO0=
-github.com/google/go-cmp v0.2.0 h1:+dTQ8DZQJz0Mb/HjFlkptS1FeQ4cWSnN941F8aEG4SQ=
-github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
-github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
-github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af h1:pmfjZENx5imkbgOkpRUYLnmbU7UEFbjtDA2hxJ1ichM=
-github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k=
-github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg=
-github.com/karrick/godirwalk v1.8.0/go.mod h1:H5KPZjojv4lE+QYImBI8xVtrBRgYrIVsaRPx4tDPEn4=
-github.com/karrick/godirwalk v1.10.3/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA=
-github.com/klauspost/compress v1.9.5 h1:U+CaK85mrNNb4k8BNOfgJtJ/gr6kswUCFj6miSzVC6M=
-github.com/klauspost/compress v1.9.5/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A=
-github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
-github.com/konsorten/go-windows-terminal-sequences v1.0.2/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
+github.com/gomodule/redigo v1.8.9/go.mod h1:7ArFNvsTjH8GMMzB4uy1snslv2BwmginuMs06a1uzZE=
+github.com/google/go-cmp v0.5.2 h1:X2ev0eStA3AbceY54o37/0PQ/UWqKEiiO2dKL5OPaFM=
+github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
+github.com/inconshreveable/mousetrap v1.0.1 h1:U3uMjPSQEBMNp1lFxmllqCPM6P5u/Xq7Pgzkat/bFNc=
+github.com/inconshreveable/mousetrap v1.0.1/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw=
+github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY=
+github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y=
+github.com/klauspost/compress v1.13.6 h1:P76CopJELS0TiO2mebmnzgWaajssP/EszplttgQxcgc=
+github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
+github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
 github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
 github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
+github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
 github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
-github.com/markbates/oncer v0.0.0-20181203154359-bf2de49a0be2/go.mod h1:Ld9puTsIW75CHf65OeIOkyKbteujpZVXDpWK6YGZbxE=
-github.com/markbates/safe v1.0.1/go.mod h1:nAqgmRi7cY2nqMc92/bSEeQA+R4OheNU2T1kNSCBdG0=
+github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0=
+github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
+github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe h1:iruDEfMl2E6fbMZ9s0scYfZQ84/6SPL6zC8ACM2oIL0=
 github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
-github.com/natefinch/lumberjack v2.0.0+incompatible/go.mod h1:Wi9p2TTF5DG5oU+6YfsmYQpsTIOm0B1VNzQg9Mw6nPk=
-github.com/pelletier/go-toml v1.4.0/go.mod h1:PN7xzY2wHTK0K9p34ErDQMlFxa51Fk0OUruD3k1mMwo=
-github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
+github.com/nsqio/go-nsq v1.1.0/go.mod h1:vKq36oyeVXgsS5Q8YEO7WghqidAVXQlcFxzQbQTuDEY=
+github.com/olivere/elastic v6.2.37+incompatible h1:UfSGJem5czY+x/LqxgeCBgjDn6St+z8OnsCuxwD3L0U=
+github.com/olivere/elastic v6.2.37+incompatible/go.mod h1:J+q1zQJTgAz9woqsbVRqGeB5G1iqDKVBWLNSYW8yfJ8=
 github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
 github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
 github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
 github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
 github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
-github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/rogpeppe/go-internal v1.2.2/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
-github.com/sirupsen/logrus v1.4.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo=
-github.com/sirupsen/logrus v1.4.1/go.mod h1:ni0Sbl8bgC9z8RoU9G6nDWqqs/fq4eDPysMBDgk/93Q=
-github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE=
+github.com/spf13/cobra v0.0.3 h1:ZlrZ4XsMRm04Fr5pSFxBgfND2EBVa1nLpiy1stUsX/8=
 github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ=
-github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
+github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA=
+github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
 github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
 github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
-github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
-github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
+github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
 github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
 github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
 github.com/tidwall/pretty v1.0.0 h1:HsD+QiTn7sK6flMKIvNmpqz1qrpP3Ps6jOKIKMooyg4=
 github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
-github.com/xdg/scram v0.0.0-20180814205039-7eeb5667e42c h1:u40Z8hqBAAQyv+vATcGgV0YCnDjqSL7/q/JyPhhJSPk=
-github.com/xdg/scram v0.0.0-20180814205039-7eeb5667e42c/go.mod h1:lB8K/P019DLNhemzwFU4jHLhdvlE6uDZjXFejJXr49I=
-github.com/xdg/stringprep v0.0.0-20180714160509-73f8eece6fdc h1:n+nNi93yXLkJvKwXNP9d55HC7lGK4H/SRcwB5IaUZLo=
-github.com/xdg/stringprep v0.0.0-20180714160509-73f8eece6fdc/go.mod h1:Jhud4/sHMO4oL310DaZAKk9ZaJ08SJfe+sJh0HrGL1Y=
+github.com/xdg-go/pbkdf2 v1.0.0 h1:Su7DPu48wXMwC3bs7MCNG+z4FhcyEuz5dlvchbq0B0c=
+github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
+github.com/xdg-go/scram v1.1.1 h1:VOMT+81stJgXW3CpHyqHN3AXDYIMsx56mEFrB37Mb/E=
+github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g=
+github.com/xdg-go/stringprep v1.0.3 h1:kdwGpVNwPFtjs98xCGkHjQtGKh86rDcRZN17QEMCOIs=
+github.com/xdg-go/stringprep v1.0.3/go.mod h1:W3f5j4i+9rC0kuIEJL0ky1VpHXQU3ocBgklLGvcBnW8=
+github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d h1:splanxYIlg+5LfHAM6xpdFEAYOk8iySO56hMFq6uLyA=
+github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA=
 github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
-go.mongodb.org/mongo-driver v1.4.1 h1:38NSAyDPagwnFpUA/D5SFgbugUYR3NzYRNa4Qk9UxKs=
-go.mongodb.org/mongo-driver v1.4.1/go.mod h1:llVBH2pkj9HywK0Dtdt6lDikOjFLbceHVu/Rc0iMKLs=
+go.mongodb.org/mongo-driver v1.10.1 h1:NujsPveKwHaWuKUer/ceo9DzEe7HIj1SlJ6uvXZG0S4=
+go.mongodb.org/mongo-driver v1.10.1/go.mod h1:z4XpeoU6w+9Vht+jAFyLgVrD+jGSQQe0+CBWFHNiHt8=
 go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw=
 go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
 go.uber.org/goleak v1.1.11 h1:wy28qYRKZgnJTxGxvye5/wgWr1EKjmUDGYox5mGlRlI=
 go.uber.org/goleak v1.1.11/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ=
 go.uber.org/multierr v1.6.0 h1:y6IPFStTAIT5Ytl7/XYmHvzXQ7S3g/IeZW9hyZ5thw4=
 go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU=
-go.uber.org/zap v1.21.0 h1:WefMeulhovoZ2sYXz7st6K0sLj7bBhpiFaud4r4zST8=
-go.uber.org/zap v1.21.0/go.mod h1:wjWOCqI0f2ZZrJF/UufIOkiC8ii6tm1iqIsLo76RfJw=
-golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
+go.uber.org/zap v1.22.0 h1:Zcye5DUgBloQ9BaT4qc9BnjOFog5TvBSAGkJ3Nf70c0=
+go.uber.org/zap v1.22.0/go.mod h1:H4siCOZOrAolnUPJEkfaSjDqyP+BDS0DdDWzwcgt3+U=
 golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
-golang.org/x/crypto v0.0.0-20190422162423-af44ce270edf/go.mod h1:WFFai1msRO1wXaEeE5yQxYXgSfI8pQAWXbQop6sCtWE=
-golang.org/x/crypto v0.0.0-20190530122614-20be4c3c3ed5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
-golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550 h1:ObdrDkeb4kJdCP557AjRjq69pTHfNouLtWZG7j9rPN8=
 golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
+golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d h1:sK3txAijHtOK88l68nt020reeT1ZdKLIYetKl95FzVY=
+golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
 golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
 golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
 golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
 golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
 golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
-golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
 golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
-golang.org/x/net v0.0.0-20210916014120-12bc252f5db8 h1:/6y1LfuqNuQdHAm0jjtPtgRcxIxjVZgm5OTu8/QhZvk=
 golang.org/x/net v0.0.0-20210916014120-12bc252f5db8/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
-golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20190412183630-56d357773e84/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2 h1:CIJ76btIcR3eFI5EgSo6k1qKw9KJexJuRLI9G7Hp5wE=
+golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
 golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20210220032951-036812b2e83c h1:5KslGYwFpkhGh+Q16bwMP3cOontH8FOep7tGV86Y7SQ=
 golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20190403152447-81d4e9dc473e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190419153524-e8e3143a4f4a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20190531175056-4c3a928424d2/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
 golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
 golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
 golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
-golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M=
 golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
+golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk=
+golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
 golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
 golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190329151228-23e29df326fe/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190416151739-9c9e1878f421/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190420181800-aa740d480789/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190531172133-b3315ee88b7d/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc=
 golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
 golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
 golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
 golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
 gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
-gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI=
 gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22 h1:VpOs+IwYnYBaFnrNAeB8UUWtL3vEUnzSCL1nVjPhqrw=
 gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22/go.mod h1:yeKp02qBN3iKW1OzL3MGk2IdtZzaj7SFntXj72NppTA=
 gopkg.in/natefinch/lumberjack.v2 v2.0.0 h1:1Lc07Kr7qY4U2YPouBjpCLxpiyxIVoxqXgkXLknAOE8=
 gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24xpD6X8LsfU/+k=
+gopkg.in/olivere/elastic.v1 v1.0.1 h1:ZoJwTKCI0jJdVptoGB0QEFt/4bDUs6A5Pjrmn/Zb+5g=
+gopkg.in/olivere/elastic.v1 v1.0.1/go.mod h1:sMIrW2Y2hS8bEAqdTvdcrNN/KV21XXOfjdi4tHxwVnI=
 gopkg.in/olivere/elastic.v2 v2.0.61 h1:7cpl3MW8ysa4GYFBXklpo5mspe4NK0rpZTdyZ+QcD4U=
 gopkg.in/olivere/elastic.v2 v2.0.61/go.mod h1:CTVyl1gckiFw1aLZYxC00g3f9jnHmhoOKcWF7W3c6n4=
-gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
-gopkg.in/yaml.v2 v2.2.8/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
 gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
 gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
 gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
-gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo=
-gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
+gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
+gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

+ 46 - 9
fieldproject_com/init.go

@@ -1,12 +1,13 @@
 package main
 
 import (
+	"app.yhyue.com/data_processing/common_utils/elastic"
+	"app.yhyue.com/data_processing/common_utils/log"
+	"app.yhyue.com/data_processing/common_utils/mongodb"
+	"app.yhyue.com/data_processing/common_utils/mysqldb"
 	"fieldproject_common/config"
 	"fmt"
 	"os"
-	"utils/log"
-	"utils/mongodb"
-	"utils/mysqldb"
 )
 
 // InitLog @Description
@@ -38,14 +39,50 @@ func InitMgo() {
 		Password:    config.Conf.DB.Mongo.Password,
 	}
 	MongoTool.InitPool()
+
+	MongoTool1 = &mongodb.MongodbSim{
+		MongodbAddr: config.Conf.DB.Mongo1.Addr,
+		Size:        config.Conf.DB.Mongo1.Size,
+		DbName:      config.Conf.DB.Mongo1.Dbname,
+		UserName:    config.Conf.DB.Mongo1.User,
+		Password:    config.Conf.DB.Mongo1.Password,
+	}
+	MongoTool1.InitPool()
+
+	MongoTool2 = &mongodb.MongodbSim{
+		MongodbAddr: config.Conf.DB.Mongo2.Addr,
+		Size:        config.Conf.DB.Mongo2.Size,
+		DbName:      config.Conf.DB.Mongo2.Dbname,
+		UserName:    config.Conf.DB.Mongo2.User,
+		Password:    config.Conf.DB.Mongo2.Password,
+	}
+	MongoTool2.InitPool()
+}
+
+func InitEs() {
+	Es = &elastic.Elastic{
+		S_esurl: config.Conf.DB.Es.Addr,
+		I_size:  config.Conf.DB.Es.Size,
+	}
+	Es.InitElasticSize()
 }
 
 func InitMysql() {
-	MysqlTool = &mysqldb.Mysql{
-		Address:  config.Conf.DB.Mysql.Addr,
-		DBName:   config.Conf.DB.Mysql.Dbname,
-		UserName: config.Conf.DB.Mysql.User,
-		PassWord: config.Conf.DB.Mysql.Password,
+	dbcfg := config.Conf.DB.Mysql
+	MysqlB = &mysqldb.Mysql{
+		Address:  dbcfg.Addr,
+		DBName:   dbcfg.DbnameBasic,
+		UserName: dbcfg.User,
+		PassWord: dbcfg.Password,
 	}
-	MysqlTool.Init()
+	MysqlB.Init()
+
+	MysqlM = &mysqldb.Mysql{
+		Address:  dbcfg.Addr,
+		DBName:   dbcfg.DbnameMedical,
+		UserName: dbcfg.User,
+		PassWord: dbcfg.Password,
+	}
+	MysqlM.Init()
+
 }

+ 168 - 21
fieldproject_com/main.go

@@ -1,19 +1,32 @@
 package main
 
 import (
+	util "app.yhyue.com/data_processing/common_utils"
+	"app.yhyue.com/data_processing/common_utils/elastic"
+	"app.yhyue.com/data_processing/common_utils/log"
+	"app.yhyue.com/data_processing/common_utils/mongodb"
+	"app.yhyue.com/data_processing/common_utils/mysqldb"
 	"fieldproject_common/config"
 	"fmt"
+	"github.com/spf13/cobra"
+	"go.uber.org/zap"
 	"sync"
 	"time"
-	"utils"
-	"utils/log"
-	"utils/mongodb"
-	"utils/mysqldb"
 )
 
 var (
-	MongoTool *mongodb.MongodbSim
-	MysqlTool *mysqldb.Mysql
+	MongoTool, MongoTool1, MongoTool2 *mongodb.MongodbSim
+	MysqlB, MysqlM                    *mysqldb.Mysql
+	Es                                *elastic.Elastic
+	ChEs                              chan bool
+
+	saveSize     int
+	savePool     chan map[string]interface{}
+	saveSp       chan bool
+	EsSaveCache  chan map[string]interface{}
+	SP           chan bool
+	updateEsPool chan []map[string]interface{}
+	updateEsSp   chan bool
 )
 
 func init() {
@@ -21,11 +34,37 @@ func init() {
 	InitLog()
 	InitMgo()
 	InitMysql()
+	InitEs()
+
+	ChEs = make(chan bool, 10)
+	saveSize = 200
+	savePool = make(chan map[string]interface{}, 5000)
+	saveSp = make(chan bool, 2)
+	EsSaveCache = make(chan map[string]interface{}, 1000)
+	SP = make(chan bool, 5)
+	updateEsPool = make(chan []map[string]interface{}, 5000)
+	updateEsSp = make(chan bool, 1)
+
 	log.Info("init success")
 }
 
 func main() {
-	task()
+	//task()
+
+	//taskBiddingData()
+	//taskCompanyData()
+	//taskMedicalData()
+
+	rootCmd := &cobra.Command{Use: "my cmd"}
+	rootCmd.AddCommand(institution())
+	rootCmd.AddCommand(product())
+	rootCmd.AddCommand(bidding())
+	if err := rootCmd.Execute(); err != nil {
+		fmt.Println("rootCmd.Execute failed", err.Error())
+	}
+
+	c := make(chan bool, 1)
+	<-c
 }
 
 func task() {
@@ -35,9 +74,9 @@ func task() {
 	ch := make(chan bool, 2)
 	wg := &sync.WaitGroup{}
 
-	log.Info(fmt.Sprintf("%d", MongoTool.Count("zktest_mysql_company_info", nil)))
+	log.Info(fmt.Sprintf("%d", MongoTool.Count("qyxy_0824", nil)))
 	field := map[string]interface{}{"use_flag": 0, "province_short": 0, "create_time": 0, "update_time": 0}
-	query := sess.DB(config.Conf.DB.Mongo.Dbname).C("zktest_mysql_company_info").Find(nil).Select(field).Sort("-_id").Iter()
+	query := sess.DB(config.Conf.DB.Mongo.Dbname).C("qyxy_0824").Find(nil).Select(field).Iter()
 	count := 0
 	for tmp := make(map[string]interface{}); query.Next(tmp); count++ {
 		if count%2000 == 0 {
@@ -53,33 +92,141 @@ func task() {
 			}()
 			delete(tmp, "_id")
 			m := make(map[string]interface{})
-			if util.ObjToString(tmp["district"]) != "" {
-				m["district"] = tmp["district"]
+			if util.ObjToString(tmp["company_district"]) != "" {
+				m["district"] = tmp["company_district"]
 			} else if util.ObjToString(tmp["city"]) != "" {
-				m["city"] = tmp["city"]
+				m["city"] = tmp["company_city"]
 			} else {
-				m["area"] = tmp["area"]
+				m["area"] = tmp["company_area"]
 			}
 			if len(m) > 0 {
-				info := MysqlTool.FindOne("code_area", m, "", "")
+				info := MysqlB.FindOne("code_area", m, "", "")
 				if info != nil && len(*info) > 0 {
-					tmp["areacode"] = (*info)["code"]
+					tmp["area_code"] = (*info)["code"]
 				} else {
-					tmp["areacode"] = "000000"
+					tmp["area_code"] = "000000"
 				}
 			} else {
-				tmp["areacode"] = "000000"
+				tmp["area_code"] = "000000"
 			}
-			delete(tmp, "area")
-			delete(tmp, "city")
-			delete(tmp, "district")
+			delete(tmp, "company_area")
+			delete(tmp, "company_city")
+			delete(tmp, "company_district")
 			tmp["comeintime"] = time.Now()
 			tmp["updatetime"] = time.Now()
 			tmp["sourcetype"] = 1
-			MysqlTool.Insert("company_baseinfo", tmp)
+			MysqlB.Insert("company_business_model", map[string]interface{}{"company_id": tmp["company_id"],
+				"business_model": util.IntAll(tmp["business_type"]), "company_field_code": "0101", "comeintime": time.Now()})
+			delete(tmp, "business_type")
+			MysqlB.Insert("company_baseinfo", tmp)
 		}(tmp)
 		tmp = make(map[string]interface{})
 	}
 	wg.Wait()
 	log.Info(fmt.Sprintf("over --- %d", count))
 }
+
+// @Description mysql迭代
+// @Author J 2022/8/9 17:32
+func taskMedicalData() {
+	pool := make(chan bool, 10) //控制线程数
+	wg := &sync.WaitGroup{}
+
+	finalId := 0
+	lastInfo := MysqlM.SelectBySql(fmt.Sprintf("SELECT * FROM %s where mark_id = 4 ORDER BY id DESC LIMIT 1", "institution_baseinfo"))
+	//lastInfo := MysqlM.SelectBySql(fmt.Sprintf("SELECT * FROM %s where id=58830 ORDER BY id DESC LIMIT 1", "institution_baseinfo"))
+	if len(*lastInfo) > 0 {
+		finalId = util.IntAll((*lastInfo)[0]["id"])
+	}
+	log.Info("查询最后id---", zap.Int("finally id: ", finalId))
+	lastid, count := 0, 0
+	for {
+		log.Info("重新查询,lastid---", zap.Int("lastid: ", lastid))
+		q := fmt.Sprintf("SELECT id, company_id FROM %s WHERE id > %d AND mark_id = 4 ORDER BY id ASC limit 1000000", "institution_baseinfo", lastid)
+		//q := fmt.Sprintf("SELECT id, company_id FROM %s WHERE id=58830 ORDER BY id ASC limit 1000000", "institution_baseinfo")
+		rows, err := MysqlM.DB.Query(q)
+		if err != nil {
+			log.Error("mysql query err ", zap.Error(err))
+		}
+		columns, err := rows.Columns()
+		if finalId == lastid {
+			log.Info("----finish-----", zap.Int("count: ", count))
+			break
+		}
+		for rows.Next() {
+			scanArgs := make([]interface{}, len(columns))
+			values := make([]interface{}, len(columns))
+			ret := make(map[string]interface{})
+			for k := range values {
+				scanArgs[k] = &values[k]
+			}
+			err = rows.Scan(scanArgs...)
+			if err != nil {
+				log.Error("mysql scan err ", zap.Error(err))
+				break
+			}
+			for i, col := range values {
+				if v, ok := col.([]uint8); ok {
+					ret[columns[i]] = string(v)
+				} else {
+					ret[columns[i]] = col
+				}
+			}
+			lastid = util.IntAll(ret["id"])
+			count++
+			if count%2000 == 0 {
+				log.Info("current----", zap.Int("count: ", count), zap.Int("lastid: ", lastid))
+			}
+			pool <- true
+			wg.Add(1)
+			go func(tmp map[string]interface{}) {
+				defer func() {
+					<-pool
+					wg.Done()
+				}()
+				// mark_id = 1
+				//taskB(util.ObjToString(tmp["company_id"]))
+				// mark_id = 4
+				taskB_1(util.ObjToString(tmp["company_id"]))
+			}(ret)
+			ret = make(map[string]interface{})
+		}
+		_ = rows.Close()
+		wg.Wait()
+	}
+}
+
+func SaveMethod() {
+	arru := make([]map[string]interface{}, saveSize)
+	indexu := 0
+	for {
+		select {
+		case v := <-savePool:
+			arru[indexu] = v
+			indexu++
+			if indexu == saveSize {
+				saveSp <- true
+				go func(arru []map[string]interface{}) {
+					defer func() {
+						<-saveSp
+					}()
+					MongoTool.SaveBulk("bidding_p_list_0907", arru...)
+				}(arru)
+				arru = make([]map[string]interface{}, saveSize)
+				indexu = 0
+			}
+		case <-time.After(1000 * time.Millisecond):
+			if indexu > 0 {
+				saveSp <- true
+				go func(arru []map[string]interface{}) {
+					defer func() {
+						<-saveSp
+					}()
+					MongoTool.SaveBulk("bidding_p_list_0907", arru...)
+				}(arru[:indexu])
+				arru = make([]map[string]interface{}, saveSize)
+				indexu = 0
+			}
+		}
+	}
+}

BIN
fieldproject_com/orgdata


BIN
fieldproject_com/orgdata_linux


+ 392 - 0
fieldproject_com/task.go

@@ -0,0 +1,392 @@
+package main
+
+import (
+	util "app.yhyue.com/data_processing/common_utils"
+	"app.yhyue.com/data_processing/common_utils/log"
+	"encoding/json"
+	"fieldproject_common/config"
+	"fmt"
+	es "gopkg.in/olivere/elastic.v2"
+	"strconv"
+	"sync"
+	"time"
+)
+
+var province_map = map[string]string{
+	"BJ": "北京", "TJ": "天津", "SH": "上海", "CQ": "重庆", "HB": "河北", "SX": "山西", "NMG": "内蒙古", "LN": "辽宁", "JL": "吉林",
+	"HLJ": "黑龙江", "JS": "江苏", "ZJ": "浙江", "AH": "安徽", "FJ": "福建", "JX": "江西", "SD": "山东", "HEN": "河南", "HUB": "湖北",
+	"HUN": "湖南", "GD": "广东", "GX": "广西", "HAIN": "海南", "SC": "四川", "GZ": "贵州", "YN": "云南", "XZ": "西藏", "SAX": "陕西",
+	"GS": "甘肃", "QH": "青海", "NX": "宁夏", "XJ": "新疆",
+}
+
+// @Description 标讯数据
+// @Author J 2022/9/7 11:42
+func taskBiddingData1() {
+	go SaveMethod()
+
+	sess := MongoTool.GetMgoConn()
+	defer MongoTool.DestoryMongoConn(sess)
+
+	ch := make(chan bool, 10)
+	wg := &sync.WaitGroup{}
+
+	//q := map[string]interface{}{"_id": mongodb.StringTOBsonId("5a8d7f4840d2d9bbe8962002")}
+	query := sess.DB(config.Conf.DB.Mongo.Dbname).C("bidding").Find(nil).Iter()
+	count := 0
+	for tmp := make(map[string]interface{}); query.Next(tmp); count++ {
+		if count%20000 == 0 {
+			log.Info(fmt.Sprintf("current --- %d", count))
+		}
+		ch <- true
+		wg.Add(1)
+		go func(tmp map[string]interface{}) {
+			defer func() {
+				<-ch
+				wg.Done()
+			}()
+			if b := util.ObjToString(tmp["bid_field"]); b != "" {
+				taskA(tmp)
+			}
+		}(tmp)
+		tmp = make(map[string]interface{})
+	}
+	wg.Wait()
+	log.Info(fmt.Sprintf("over --- %d", count))
+}
+
+// @Description 企业数据
+// @Author J 2022/8/23 09:08
+func taskCompanyData() {
+	sess := MongoTool.GetMgoConn()
+	defer MongoTool.DestoryMongoConn(sess)
+
+	ch := make(chan bool, 10)
+	wg := &sync.WaitGroup{}
+
+	//log.Info(fmt.Sprintf("%d", MongoTool2.Count("zktest_mysql_company_info", nil)))
+	var p1 []map[string]interface{}
+	p1 = append(p1, map[string]interface{}{"$group": map[string]interface{}{"_id": "$company_id"}})
+	query := sess.DB(config.Conf.DB.Mongo.Dbname).C("bidding_p_list_0907").Pipe(p1).Iter()
+	//q := map[string]interface{}{"_id": mongodb.StringTOBsonId("61efb24b70f4a1409599badb")}
+	//query := sess.DB(config.Conf.DB.Mongo2.Dbname).C("zktest_mysql_company_info").Find(nil).Iter()
+	count := 0
+	for tmp := make(map[string]interface{}); query.Next(tmp); count++ {
+		if count%5000 == 0 {
+			log.Info(fmt.Sprintf("current --- %d", count))
+		}
+		ch <- true
+		wg.Add(1)
+		go func(tmp map[string]interface{}) {
+			defer func() {
+				<-ch
+				wg.Done()
+			}()
+			//taskC(tmp)
+			taskB(util.ObjToString(tmp["_id"]))
+			//info, _ := MongoTool.FindOne("qyxy_std", map[string]interface{}{"_id": util.ObjToString(tmp["company_id"])})
+			//if len(*info) > 0 {
+			//	savePool <- *info
+			//}
+
+		}(tmp)
+		tmp = make(map[string]interface{})
+	}
+	wg.Wait()
+	log.Info(fmt.Sprintf("over --- %d", count))
+}
+
+// @Description 标讯数据企业与产品
+// @Author J 2022/8/24 14:37
+func taskA(tmp map[string]interface{}) {
+	if tmp["entidlist"] != nil {
+		saveMap := make(map[string]interface{})
+		for _, eid := range tmp["entidlist"].([]interface{}) {
+			if util.ObjToString(eid) != "" && util.ObjToString(eid) != "-" {
+				saveMap["company_id"] = eid
+				if tmp["purchasinglist"] != nil {
+					for _, p1 := range tmp["purchasinglist"].([]interface{}) {
+						p2 := p1.(map[string]interface{})
+						if p2["itemname"] != nil {
+							saveMap["itemname"] = p2["itemname"]
+							if p2["brandname"] != nil {
+								saveMap["brand"] = p2["brandname"]
+							}
+							if p2["model"] != nil {
+								saveMap["model"] = p2["model"]
+							}
+							MongoTool.Save("bidding_p_list_0907", saveMap)
+							//savePool <- saveMap
+						}
+					}
+				}
+			}
+		}
+	}
+}
+
+var company_field = []string{"company_id", "company_name", "company_code", "credit_no", "org_code", "tax_code", "establish_date", "legal_person", "legal_person_caption",
+	"company_status", "company_type", "authority", "issue_date", "operation_startdate", "operation_enddate", "capital", "company_address", "business_scope", "cancel_date",
+	"cancel_reason", "revoke_date", "revoke_reason", "legal_person_type", "real_capital", "en_name", "list_code", "area_code", "employee_no", "company_phone", "company_email",
+	"website", "sourcetype"}
+
+// @Description 医疗企业
+// @Author J 2022/8/24 14:37
+func taskB(tid string) {
+	saveM := make(map[string]interface{})
+	info, _ := MongoTool1.FindOneByField("company_base", map[string]interface{}{"company_id": tid}, "")
+	if len(*info) == 0 {
+		info, _ = MongoTool1.FindOneByField("special_enterprise", map[string]interface{}{"company_id": tid}, "")
+	}
+	if len(*info) > 0 {
+		for _, v := range company_field {
+			if (*info)[v] != nil {
+				saveM[v] = (*info)[v]
+			}
+			if v == "area_code" {
+				std, _ := MongoTool.FindOneByField("qyxy_std", map[string]interface{}{"_id": tid}, map[string]interface{}{"company_area": 1, "company_city": 1, "company_district": 1, "website_url": 1, "capital": 1})
+				if len(*std) > 0 {
+					m := make(map[string]interface{})
+					for k, v := range map[string]string{"company_district": "district", "company_city": "city", "company_area": "area"} {
+						if v1 := util.ObjToString((*std)[k]); v1 != "" {
+							m = map[string]interface{}{v: v1}
+							info := MysqlB.FindOne("code_area", m, "", "")
+							if info != nil && len(*info) > 0 {
+								saveM["area_code"] = (*info)["code"]
+								break
+							}
+						}
+					}
+					if saveM["area_code"] == nil {
+						saveM["area_code"] = "000000"
+					}
+
+					if (*std)["website_url"] != nil && len(util.ObjToString((*std)["website_url"])) <= 255 {
+						saveM["website"] = (*std)["website_url"]
+					}
+					if (*std)["company_phone"] != nil {
+						saveM["company_phone"] = (*std)["company_phone"]
+					}
+					if (*std)["company_email"] != nil {
+						saveM["company_email"] = (*std)["company_email"]
+					}
+					if (*std)["capital"] != nil {
+						saveM["capital"] = util.ObjToString((*std)["capital"])
+					}
+				}
+			} else if v == "employee_no" {
+				rep, _ := MongoTool1.Find("annual_report_base", map[string]interface{}{"company_id": tid}, map[string]interface{}{"_id": -1}, "", false, -1, -1)
+				if len(*rep) > 0 && util.ObjToString((*rep)[0]["employee_no"]) != "" {
+					i, err := strconv.Atoi(util.ObjToString((*rep)[0]["employee_no"]))
+					if err != nil {
+						saveM[v] = i
+					}
+				}
+			}
+			//else if v == "website" {
+			//	info, _ := MongoTool.Find("annual_report_website", map[string]interface{}{"company_id": tid}, map[string]interface{}{"_id": -1}, "", false, -1, -1)
+			//	if len(*info) > 0 && util.ObjToString((*info)[0]["website_url"]) != "" {
+			//		saveM[v] = util.ObjToString((*info)[0]["website_url"])
+			//	}
+			//}
+		}
+		saveM["comeintime"] = time.Now()
+		saveM["updatetime"] = time.Now()
+		saveM["sourcetype"] = 3
+		MysqlB.Insert("company_baseinfo", saveM)
+		//savePool <- saveM
+	} else {
+		util.Debug("company_id err", tid)
+	}
+}
+
+func taskB_1(tid string) {
+	saveM := make(map[string]interface{})
+	info, _ := MongoTool1.FindOneByField("company_base", map[string]interface{}{"company_id": tid}, "")
+	if len(*info) == 0 {
+		info, _ = MongoTool1.FindOneByField("special_enterprise", map[string]interface{}{"company_id": tid}, "")
+	}
+	if len(*info) > 0 {
+		for _, v := range company_field {
+			if (*info)[v] != nil {
+				saveM[v] = (*info)[v]
+			}
+			if v == "area_code" {
+				if a := util.ObjToString((*info)["province_short"]); a != "" {
+					m := map[string]interface{}{"area": province_map[a]}
+					info := MysqlB.FindOne("code_area", m, "", "")
+					if info != nil && len(*info) > 0 {
+						saveM["area_code"] = (*info)["code"]
+					}
+
+				}
+			} else if (*info)["capital"] != nil {
+				text := util.ObjToString((*info)["capital"])
+				capital := ObjToMoney(text)
+				capital = capital / 10000
+				if capital != 0 {
+					saveM["capital"] = fmt.Sprint(capital)
+				}
+			}
+		}
+		saveM["comeintime"] = time.Now()
+		saveM["updatetime"] = time.Now()
+		saveM["sourcetype"] = 1
+		MysqlB.Insert("company_baseinfo", saveM)
+		//savePool <- saveM
+	} else {
+		util.Debug("company_id err", tid)
+	}
+}
+
+func taskC(tmp map[string]interface{}) {
+	tid := util.ObjToString(tmp["company_id"])
+	saveM := make(map[string]interface{})
+	for _, v := range company_field {
+		if tmp[v] != nil {
+			saveM[v] = tmp[v]
+		}
+		if v == "area_code" {
+			std, _ := MongoTool.FindOneByField("qyxy_std", map[string]interface{}{"_id": tid}, map[string]interface{}{"company_area": 1, "company_city": 1, "company_district": 1, "website_url": 1, "company_phone": 1, "company_email": 1, "capital": 1})
+			if len(*std) > 0 {
+				m := make(map[string]interface{})
+				for k, v := range map[string]string{"company_district": "district", "company_city": "city", "company_area": "area"} {
+					if v1 := util.ObjToString((*std)[k]); v1 != "" {
+						m = map[string]interface{}{v: v1}
+						info := MysqlB.FindOne("code_area", m, "", "")
+						if info != nil && len(*info) > 0 {
+							saveM["area_code"] = (*info)["code"]
+							break
+						}
+					}
+				}
+				if saveM["area_code"] == nil {
+					saveM["area_code"] = "000000"
+				}
+				if (*std)["website_url"] != nil && len(util.ObjToString((*std)["website_url"])) <= 255 {
+					saveM["website"] = (*std)["website_url"]
+				}
+				if (*std)["company_phone"] != nil {
+					saveM["company_phone"] = (*std)["company_phone"]
+				}
+				if (*std)["company_email"] != nil {
+					saveM["company_email"] = (*std)["company_email"]
+				}
+				if (*std)["capital"] != nil {
+					saveM["capital"] = fmt.Sprint((*std)["capital"])
+				}
+			}
+		} else if v == "employee_no" {
+			rep, _ := MongoTool1.Find("annual_report_base", map[string]interface{}{"company_id": tid}, map[string]interface{}{"_id": -1}, "", false, -1, -1)
+			if len(*rep) > 0 && util.ObjToString((*rep)[0]["employee_no"]) != "" {
+				i, err := strconv.Atoi(util.ObjToString((*rep)[0]["employee_no"]))
+				if err != nil {
+					saveM[v] = i
+				}
+			}
+		}
+	}
+	saveM["comeintime"] = time.Now()
+	saveM["updatetime"] = time.Now()
+	saveM["sourcetype"] = 2
+	//MysqlB.Insert("company_business_model", map[string]interface{}{"company_id": tmp["company_id"],
+	//	"business_model": util.IntAll(tmp["business_type"]), "company_field_code": "0101", "comeintime": time.Now()})
+	MysqlB.Insert("company_baseinfo", saveM)
+}
+
+func taskBiddingData() {
+	client := Es.GetEsConn()
+	defer Es.DestoryEsConn(client)
+
+	wg := &sync.WaitGroup{}
+	//lock := &sync.Mutex{}
+
+	esquery := `{"query":{"bool":{"must":[],"must_not":[{"constant_score":{"filter":{"missing":{"field":"bid_field"}}}}],"should":[{"match_all":{}}]}},"from":0,"size":10,"sort":[],"facets":{}}`
+
+	q := es.NewRawStringQuery(esquery)
+	util.Debug(Es.Count("bidding", "bidding", q))
+	countDocs := 0
+	res, err := client.Scroll().Index("bidding").Type("bidding").Query(q).Size(200).Do() //查询一条获取游标
+	if err == nil {
+		taskInfoA(res, wg, &countDocs)
+		scrollId := res.ScrollId
+		for {
+			searchResult, err := client.Scroll("1m").ScrollId(scrollId).Size(200).Do() //查询
+			if err != nil {
+				util.Debug("Es Search Data Error:", err)
+				break
+			}
+			taskInfoA(searchResult, wg, &countDocs)
+			scrollId = searchResult.ScrollId
+		}
+		wg.Wait()
+		util.Debug("over---", countDocs)
+		_, _ = client.ClearScroll().ScrollId(scrollId).Do() //清理游标
+	} else {
+		util.Debug(err)
+	}
+
+	c := make(chan bool, 1)
+	<-c
+}
+
+func taskInfoA(searchResult *es.SearchResult, wg *sync.WaitGroup, countDocs *int) {
+	for _, hit := range searchResult.Hits.Hits {
+		//开始处理数据
+		wg.Add(1)
+		ChEs <- true
+		go func(tmpHit *es.SearchHit) {
+			defer func() {
+				<-ChEs
+				wg.Done()
+			}()
+			tmp := make(map[string]interface{})
+			if json.Unmarshal(*tmpHit.Source, &tmp) == nil {
+				id := util.ObjToString(tmp["_id"])
+				if tmp["entidlist"] != nil && tmp["purchasinglist"] != nil {
+					for _, eid := range util.ObjArrToStringArr(tmp["entidlist"].([]interface{})) {
+						if util.ObjToString(eid) != "" && util.ObjToString(eid) != "-" {
+							saveMap := make(map[string]interface{})
+							saveMap["infoid"] = id
+							saveMap["company_id"] = eid
+							for _, p1 := range tmp["purchasinglist"].([]interface{}) {
+								p2 := p1.(map[string]interface{})
+								if p2["itemname"] != nil {
+									b := method3(id, util.ObjToString(p2["itemname"]))
+									if b {
+										saveMap["itemname"] = p2["itemname"]
+										if p2["brandname"] != nil {
+											saveMap["brand"] = p2["brandname"]
+										}
+										if p2["model"] != nil {
+											saveMap["model"] = p2["model"]
+										}
+										MongoTool.Save("bidding_p_list_0907", saveMap)
+									}
+								}
+							}
+						}
+					}
+				}
+
+			}
+		}(hit)
+		*countDocs += 1
+
+		if *countDocs%20000 == 0 {
+			util.Debug("Current:", *countDocs)
+		}
+	}
+}
+
+func method3(id, itemname string) bool {
+	q := map[string]interface{}{"infoid": id, "itemname": itemname}
+	info := MysqlB.FindOne("bid_purchasinginfo", q, "id", "")
+	if info != nil && len(*info) > 0 {
+		q1 := map[string]interface{}{"bid_purchasing_id": (*info)["id"]}
+		info1 := MysqlB.FindOne("bid_purchasing_field_record", q1, "id", "")
+		if info1 != nil && len(*info1) > 0 {
+			return true
+		}
+	}
+	return false
+}

File diff suppressed because it is too large
+ 180 - 0
fieldproject_com/taskEs.go


+ 272 - 0
fieldproject_com/util.go

@@ -0,0 +1,272 @@
+package main
+
+import (
+	"regexp"
+	"strconv"
+	"strings"
+)
+
+var (
+	regNumFloat, _  	= regexp.Compile(`([1-9]\d*|0)(\.\d+)?`)
+	regStrUnit, _   	= regexp.Compile(`[元|万|亿]`)
+	contentUnit, _ 		= regexp.Compile(`(万元|单位/万)`)
+	numCapitals, _		= regexp.Compile(`([〇|零|点|壹|贰|叁|肆|伍|陆|柒|捌|玖|拾|百|佰|千|仟|万|亿|億|元|圆|角|分|整|正]{4,40})`)
+	regStrChar      	= `[〇|零|点|壹|贰|叁|肆|伍|陆|柒|捌|玖|拾|百|佰|千|仟|万|亿|億|元|圆|角|分|整|正]`
+	moneyRegChar, _ 	= regexp.Compile(regStrChar)
+	regQianw, _    		= regexp.Compile(`\d{1,2}千万`)
+
+	cutAllSpace, _ 		= regexp.Compile(`\s*`)
+	spaces        		= []string{"\u3000", "\u2003", "\u00a0", "\t", "\r", "\n"}
+
+	moneyChar      = map[string]interface{}{ //"〇": "0", "零": "0",
+		"一": float64(1), "壹": float64(1), "二": float64(2), "贰": float64(2), "三": float64(3), "叁": float64(3), "四": float64(4), "肆": float64(4), "五": float64(5), "伍": float64(5),
+		"六": float64(6), "陆": float64(6), "七": float64(7), "柒": float64(7), "八": float64(8), "捌": float64(8), "九": float64(9), "玖": float64(9), "十": float64(10), "拾": float64(10),
+		"百": float64(100), "佰": float64(100), "千": float64(1000), "仟": float64(1000), "万": float64(10000), "亿": float64(100000000), "億": float64(100000000),
+		"零": float64(0), "点": ".", "角": float64(0.1), "分": float64(0.01),
+	}
+	moneyUnit = map[string]float64{
+		"元": float64(1), "万": float64(10000), "亿": float64(100000000), "億": float64(100000000), //单位
+	}
+)
+
+var currencyItem = map[string]string{
+	"人民币": "人民币",
+	"rmb": "人民币",
+	"RMB": "人民币",
+	"$":   "美元",
+	"$":   "美元",
+	"美元":  "美元",
+	"港元":  "港币",
+	"港币":  "港币",
+	"澳币":  "澳币",
+	"澳元":  "澳币",
+}
+
+//获取币种
+func GetCurrency(text string) (currency string) {
+	if text == "" {
+		return
+	}
+	currency = "人民币"
+	for k, v := range currencyItem {
+		if strings.Contains(text, k) {
+			currency = v
+			return
+		}
+	}
+	return
+}
+
+//金额转换
+func ObjToMoney(text string) float64 {
+	isfindUnit := true
+	ret := capitalMoney(text)
+	if ret < float64(10000) || ret > float64(50000000000) {
+		ret2, b := numMoney(text)
+		isfindUnit = b
+		if ret2 > ret {
+			ret = ret2
+		}
+	}
+	f, _ := strconv.ParseFloat(strconv.FormatFloat(ret, 'f', 4, 64), 64)
+	// if f < 1 {
+	// 	f = 0
+	// }
+	//如果金额小于50,全文检索单位:万
+	if f < 50 && f > 0 && isfindUnit {
+		rep := contentUnit.FindAllStringIndex(text, -1)
+		if len(rep) > 0 {
+			f = f * 10000
+		}
+	}
+	return f
+}
+
+func capitalMoney(text string) float64 {
+	nodes := []float64{}
+	node := float64(0)
+	tmp := float64(0)
+	decimals := 0.0
+	ishaspoint := false //是否含小数点
+	fnum := float64(0)
+	end := false
+	//str := fmt.Sprint(data[0])
+	//提取第一个大写信息
+	strmatch := numCapitals.FindAllStringSubmatch(text, -1)
+	if len(strmatch) > 0 {
+		text = strmatch[0][0]
+	}
+	suffixUnit := float64(1)
+	if strings.HasSuffix(text, "万") || strings.HasSuffix(text, "万元") || strings.HasSuffix(text, "万元整") {
+		index := strings.LastIndex(text, "万")
+		text = text[0:index]
+		suffixUnit = float64(10000)
+	}
+	moneyRegChar.ReplaceAllStringFunc(text, func(key string) string {
+		if key == "元" || key == "圆" || key == "点" {
+			ishaspoint = true
+		}
+		if v, ok := moneyChar[key].(float64); ok && !end {
+			if ishaspoint && v > 10 { //排除后面有其他的单位
+				return ""
+			}
+			//fmt.Println(key, v, fnum)
+			if v < 10 && v >= 0 {
+				if ishaspoint { //小数部分
+					if v >= 1 {
+						fnum = v
+					} else if v < 1 && v > 0 {
+						decimals += fnum * v
+					}
+				} else {
+					if tmp != float64(0) {
+						node += tmp
+					}
+					tmp = float64(v)
+				}
+			} else if v == 10000 || v == 100000000 { //单位万、亿
+				if tmp != float64(0) {
+					node += tmp
+					tmp = float64(0)
+				}
+				nodes = append(nodes, node*float64(v))
+				node = float64(0)
+			} else {
+				if v == 10 && tmp == 0 {
+					tmp = 1
+				}
+				tmp = tmp * float64(v)
+				node += tmp
+				tmp = float64(0)
+			}
+		}
+		if key == "整" || key == "正" || key == "分" {
+			end = true
+		}
+		return ""
+	})
+	nodes = append(nodes, node, tmp)
+	ret := float64(0)
+	for _, v := range nodes {
+		ret += v
+	}
+	return (ret + decimals) * suffixUnit
+}
+
+//数字金额转换
+func numMoney(text string) (moneyFloat float64, flag bool) {
+	//tmp := fmt.Sprintf("%f", data[0])
+	repUnit := float64(1)
+	if regQianw.MatchString(text) {
+		text = strings.Replace(text, "千万", "万", -1)
+		repUnit = float64(1000)
+	}
+	text = replaceSymbol(text, []string{",", ",", "(", ")", "(", ")", ":", "\n"})
+	text = replaceString(text, []string{"万元", "亿元", "."}, []string{"万", "亿", "."})
+	text = CutAllSpace(text)
+	rets := regNumFloat.FindAllString(text, -1)
+	fnums := []float64{}
+	unitstrs := []string{}
+	if len(rets) > 0 {
+		pindex := 0 //单位前置
+		for k, v := range rets {
+			f, err := strconv.ParseFloat(v, 64)
+			if err == nil {
+				fnums = append(fnums, f)
+				index := strings.Index(text, v)
+				//单位后置
+				start := index + len(v)
+				end := start + 3
+				//log.Println("vvv", tmp, v, pindex, index, start)
+				if k > 0 {
+					if start >= pindex+3 {
+						pstart := pindex + 3
+						if pstart >= index {
+							pstart = index
+						}
+						if len(text) > end {
+							unitstrs = append(unitstrs, text[pstart:index]+text[start:end])
+						} else {
+							unitstrs = append(unitstrs, text[pstart:index]+text[start:])
+						}
+					} else {
+						if len(text) > end {
+							unitstrs = append(unitstrs, text[start:end])
+						} else {
+							unitstrs = append(unitstrs, text[start:])
+						}
+					}
+				} else {
+					if len(text) > end {
+						if index-3 >= 0 {
+							unitstrs = append(unitstrs, text[index-3:index]+text[start:end])
+						} else {
+							unitstrs = append(unitstrs, text[start:end])
+						}
+					} else {
+						if index-3 >= 0 {
+							unitstrs = append(unitstrs, text[index-3:index]+text[start:])
+						} else {
+							unitstrs = append(unitstrs, text[start:])
+						}
+					}
+				}
+				pindex = start
+			}
+		}
+	}
+	//log.Println("unitstrs", fnums, unitstrs)
+	unit := float64(0)
+	fnum := float64(0)
+	for k, v := range fnums {
+		fnum = v
+		units := regStrUnit.FindAllString(unitstrs[k], -1)
+		for _, v := range units {
+			if moneyUnit[v] != 0 {
+				unit = moneyUnit[v]
+				break
+			}
+		}
+		if unit != float64(0) { //取第一个
+			break
+		}
+	}
+	fnum = fnum * repUnit
+	if unit == float64(0) {
+		moneyFloat = fnum
+	} else {
+		moneyFloat = fnum * unit
+	}
+	if unit == 10000 {
+		flag = false
+	} else {
+		flag = true
+	}
+	return
+}
+
+//清理所有空白符
+func CutAllSpace(text string) string {
+	tmp := cutAllSpace.ReplaceAllString(text, "")
+	tmp = replaceSymbol(tmp, spaces)
+	return tmp
+}
+
+//符号替换
+func replaceString(con string, ret, rep []string) string {
+	for k, v := range ret {
+		if len(rep) > k {
+			con = strings.Replace(con, v, rep[k], -1)
+		}
+	}
+	return con
+}
+
+//过滤符号
+func replaceSymbol(con string, rep []string) string {
+	for _, v := range rep {
+		con = strings.Replace(con, v, "", -1)
+	}
+	return con
+}
+

+ 41 - 0
fieldproject_inc_data/common.toml

@@ -0,0 +1,41 @@
+
+[db]
+
+[db.mongo]
+addr = "192.168.3.207:27001"
+dbname = "qfw_data"
+size = 5
+user = "root"
+password = "root"
+
+[db.mongo1]
+addr = "192.168.3.207:27092"
+dbname = "wjh"
+size = 5
+user = ""
+password = ""
+
+[db.es]
+addr = "http://192.168.3.206:9800"
+size = 5
+indexm = "medical_institution_v1"
+typem = "medical_institution"
+indexs = "supplier_product_v1"
+types = "supplier_product"
+
+# 日志
+[log]
+# 日志路径,为空将输出控制台
+logpath = ""
+# log size (M)
+maxsize = 10
+# compress log
+compress = true
+# log save  time (day)
+maxage =  7
+# save total log file total
+maxbackups = 10
+# log level
+loglevel  = "debug"
+# text or json output
+format = "text"

+ 92 - 0
fieldproject_inc_data/config/conf.go

@@ -0,0 +1,92 @@
+package config
+
+import (
+	"fmt"
+	"os"
+	"time"
+
+	"github.com/BurntSushi/toml"
+)
+
+var (
+	// Conf crocodile conf
+	Conf *conf
+)
+
+// Init Config
+func Init(conf string) {
+	_, err := toml.DecodeFile(conf, &Conf)
+	if err != nil {
+		fmt.Printf("Err %v", err)
+		os.Exit(1)
+	}
+}
+
+type conf struct {
+	DB  Db
+	Log Log
+}
+
+// Log Config
+type Log struct {
+	LogPath    string
+	MaxSize    int
+	Compress   bool
+	MaxAge     int
+	MaxBackups int
+	LogLevel   string
+	Format     string
+}
+
+type Db struct {
+	Mongo  mgo
+	Mongo1 mgo
+	Mongo2 mgo
+	Mysql  mysql
+	Es     es
+}
+
+type mgo struct {
+	Addr     string
+	Dbname   string
+	Size     int
+	User     string
+	Password string
+}
+
+type mysql struct {
+	Addr          string
+	DbnameBasic   string
+	DbnameMedical string
+	Size          int
+	User          string
+	Password      string
+
+	Drivename    string
+	Dsn          string
+	MaxIdle      int
+	MaxConn      int
+	MaxQueryTime duration
+}
+
+type es struct {
+	Addr   string
+	Size   int
+	IndexM string
+	TypeM  string
+	IndexS string
+	TypeS  string
+	FieldM map[string]interface{}
+	FieldS map[string]interface{}
+}
+
+type duration struct {
+	time.Duration
+}
+
+// UnmarshalText parse 10s to time.Time
+func (d *duration) UnmarshalText(text []byte) error {
+	var err error
+	d.Duration, err = time.ParseDuration(string(text))
+	return err
+}

+ 66 - 0
fieldproject_inc_data/config/conf_test.go

@@ -0,0 +1,66 @@
+package config
+
+import (
+	"io/ioutil"
+	"os"
+	"testing"
+)
+
+var confs = `# log
+[log]
+logpath = ""
+maxsize = 10
+compress = true
+maxage =  7
+maxbackups = 10
+loglevel  = "info"
+format = "text"
+
+[db]
+[db.mongo]
+addr = "192.168.3.207:27092"
+dbname = "qfw"
+size = 10
+user = ""
+password = ""
+[db.mongo1]
+addr = "192.168.3.207:27092"
+dbname = "wjh"
+size = 5
+user = ""
+password = ""
+[db.mysql]
+addr = "192.168.3.217:4000"
+dbnameBasic = "global_common_data"
+dbnameMedical = "medical_fileld_data"
+size = 5
+user = "root"
+password = "=PDT49#80Z!RVv52_z"
+
+[db.es]
+addr = "http://192.168.3.206:9800"
+size = 5
+indexm = "medical_institution_v1"
+typem = "medical_institution"
+indexs = "supplier_product_v1"
+types = "supplier_product"
+
+[db.es.fieldarrm]
+id = "int"
+company_id = "string"
+mi_name = "string"
+alias = "string"
+area_code = "string"
+level_code = "string"
+mi_type_code = "string"
+business_type = "int"
+sdequipment = "string"
+`
+
+func TestInit(t *testing.T) {
+	testfile := "/tmp/crocodile.toml"
+	ioutil.WriteFile(testfile, []byte(confs), 0644)
+	Init(testfile)
+	t.Logf("%+v", Conf.DB.Mysql.DbnameBasic)
+	os.Remove(testfile)
+}

+ 9 - 0
fieldproject_inc_data/go.mod

@@ -0,0 +1,9 @@
+module fieldproject_inc_data
+
+go 1.16
+
+require (
+	app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f
+	github.com/BurntSushi/toml v1.2.0
+	github.com/spf13/cobra v1.5.0
+)

+ 100 - 0
fieldproject_inc_data/go.sum

@@ -0,0 +1,100 @@
+app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f h1:5fUbVRwPM3oBsZgvG76Bia3I4SdwdBB6PvJ6B28Qkyc=
+app.yhyue.com/data_processing/common_utils v0.0.0-20220830011833-76d58ef43f4f/go.mod h1:9PlRUNzirlF/LL1W7fA7koCudxJe3uO5nshDWlCnGo8=
+github.com/BurntSushi/toml v1.2.0 h1:Rt8g24XnyGTyglgET/PRUNlrUeu9F5L+7FilkXfZgs0=
+github.com/BurntSushi/toml v1.2.0/go.mod h1:CxXYINrC8qIiEnFrOxCa7Jy5BFHlXnUU2pbicEuybxQ=
+github.com/PuerkitoBio/goquery v1.8.0/go.mod h1:ypIiRMtY7COPGk+I/YbZLbxsxn9g5ejnI2HSMtkjZvI=
+github.com/andybalholm/cascadia v1.3.1/go.mod h1:R4bJ1UQfqADjvDa4P6HZHLh/3OxWWEqc0Sk8XGwHqvA=
+github.com/benbjohnson/clock v1.1.0 h1:Q92kusRqC1XV2MjkWETPvjJVqKetz1OzxZB7mHJLju8=
+github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
+github.com/cpuguy83/go-md2man/v2 v2.0.2/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o=
+github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
+github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
+github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
+github.com/dchest/captcha v1.0.0/go.mod h1:7zoElIawLp7GUMLcj54K9kbw+jEyvz2K0FDdRRYhvWo=
+github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g=
+github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
+github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
+github.com/gomodule/redigo v1.8.9/go.mod h1:7ArFNvsTjH8GMMzB4uy1snslv2BwmginuMs06a1uzZE=
+github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
+github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM=
+github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
+github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
+github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
+github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
+github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
+github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe/go.mod h1:wL8QJuTMNUDYhXwkmfOly8iTdp5TEcJFWZD2D7SIkUc=
+github.com/nsqio/go-nsq v1.1.0/go.mod h1:vKq36oyeVXgsS5Q8YEO7WghqidAVXQlcFxzQbQTuDEY=
+github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
+github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
+github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
+github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
+github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
+github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM=
+github.com/spf13/cobra v1.5.0 h1:X+jTBEBqF0bHN+9cSMgmfuvv2VHJ9ezmFNf9Y/XstYU=
+github.com/spf13/cobra v1.5.0/go.mod h1:dWXEIy2H428czQCjInthrTRUg7yKbok+2Qi/yBIJoUM=
+github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA=
+github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg=
+github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
+github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
+github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
+github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
+github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
+github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
+github.com/xdg-go/pbkdf2 v1.0.0/go.mod h1:jrpuAogTd400dnrH08LKmI/xc1MbPOebTwRqcT5RDeI=
+github.com/xdg-go/scram v1.1.1/go.mod h1:RaEWvsqvNKKvBPvcKeFjrG2cJqOkHTiyTpzz23ni57g=
+github.com/xdg-go/stringprep v1.0.3/go.mod h1:W3f5j4i+9rC0kuIEJL0ky1VpHXQU3ocBgklLGvcBnW8=
+github.com/youmark/pkcs8 v0.0.0-20181117223130-1be2e3e5546d/go.mod h1:rHwXgn7JulP+udvsHwJoVG1YGAP6VLg4y9I5dyZdqmA=
+github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
+go.mongodb.org/mongo-driver v1.10.1/go.mod h1:z4XpeoU6w+9Vht+jAFyLgVrD+jGSQQe0+CBWFHNiHt8=
+go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw=
+go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
+go.uber.org/goleak v1.1.11 h1:wy28qYRKZgnJTxGxvye5/wgWr1EKjmUDGYox5mGlRlI=
+go.uber.org/goleak v1.1.11/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ=
+go.uber.org/multierr v1.6.0 h1:y6IPFStTAIT5Ytl7/XYmHvzXQ7S3g/IeZW9hyZ5thw4=
+go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU=
+go.uber.org/zap v1.22.0 h1:Zcye5DUgBloQ9BaT4qc9BnjOFog5TvBSAGkJ3Nf70c0=
+go.uber.org/zap v1.22.0/go.mod h1:H4siCOZOrAolnUPJEkfaSjDqyP+BDS0DdDWzwcgt3+U=
+golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
+golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
+golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
+golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
+golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
+golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
+golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
+golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
+golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
+golang.org/x/net v0.0.0-20210916014120-12bc252f5db8/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
+golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
+golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
+golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
+golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
+golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
+golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
+golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
+golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
+golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
+golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
+golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
+golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22/go.mod h1:yeKp02qBN3iKW1OzL3MGk2IdtZzaj7SFntXj72NppTA=
+gopkg.in/natefinch/lumberjack.v2 v2.0.0 h1:1Lc07Kr7qY4U2YPouBjpCLxpiyxIVoxqXgkXLknAOE8=
+gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24xpD6X8LsfU/+k=
+gopkg.in/olivere/elastic.v2 v2.0.61/go.mod h1:CTVyl1gckiFw1aLZYxC00g3f9jnHmhoOKcWF7W3c6n4=
+gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
+gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
+gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
+gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
+gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

+ 95 - 0
fieldproject_inc_data/init.go

@@ -0,0 +1,95 @@
+package main
+
+import (
+	"app.yhyue.com/data_processing/common_utils/elastic"
+	"app.yhyue.com/data_processing/common_utils/log"
+	"app.yhyue.com/data_processing/common_utils/mongodb"
+	"fieldproject_inc_data/config"
+	"fmt"
+	"os"
+)
+
+var (
+	MongoTool, MongoTool1, MongoTool2 *mongodb.MongodbSim
+	Es                                *elastic.Elastic
+
+	saveSize     int
+	savePool     chan map[string]interface{}
+	saveSp       chan bool
+	EsSaveCache  chan map[string]interface{}
+	SP           chan bool
+	updateEsPool chan []map[string]interface{}
+	updateEsSp   chan bool
+)
+
+func init() {
+	config.Init("./common.toml")
+	InitLog()
+	InitMgo()
+	InitEs()
+
+	saveSize = 200
+	savePool = make(chan map[string]interface{}, 5000)
+	saveSp = make(chan bool, 5)
+	EsSaveCache = make(chan map[string]interface{}, 1000)
+	SP = make(chan bool, 5)
+	updateEsPool = make(chan []map[string]interface{}, 5000)
+	updateEsSp = make(chan bool, 1)
+
+	log.Info("init success")
+}
+
+func InitLog() {
+	logcfg := config.Conf.Log
+
+	err := log.InitLog(
+		log.Path(logcfg.LogPath),
+		log.Level(logcfg.LogLevel),
+		log.Compress(logcfg.Compress),
+		log.MaxSize(logcfg.MaxSize),
+		log.MaxBackups(logcfg.MaxBackups),
+		log.MaxAge(logcfg.MaxAge),
+		log.Format(logcfg.Format),
+	)
+	if err != nil {
+		fmt.Printf("InitLog failed: %v\n", err)
+		os.Exit(1)
+	}
+}
+
+func InitMgo() {
+	MongoTool = &mongodb.MongodbSim{
+		MongodbAddr: config.Conf.DB.Mongo.Addr,
+		Size:        config.Conf.DB.Mongo.Size,
+		DbName:      config.Conf.DB.Mongo.Dbname,
+		UserName:    config.Conf.DB.Mongo.User,
+		Password:    config.Conf.DB.Mongo.Password,
+	}
+	MongoTool.InitPool()
+
+	MongoTool1 = &mongodb.MongodbSim{
+		MongodbAddr: config.Conf.DB.Mongo1.Addr,
+		Size:        config.Conf.DB.Mongo1.Size,
+		DbName:      config.Conf.DB.Mongo1.Dbname,
+		UserName:    config.Conf.DB.Mongo1.User,
+		Password:    config.Conf.DB.Mongo1.Password,
+	}
+	MongoTool1.InitPool()
+
+	MongoTool2 = &mongodb.MongodbSim{
+		MongodbAddr: config.Conf.DB.Mongo2.Addr,
+		Size:        config.Conf.DB.Mongo2.Size,
+		DbName:      config.Conf.DB.Mongo2.Dbname,
+		UserName:    config.Conf.DB.Mongo2.User,
+		Password:    config.Conf.DB.Mongo2.Password,
+	}
+	MongoTool2.InitPool()
+}
+
+func InitEs() {
+	Es = &elastic.Elastic{
+		S_esurl: config.Conf.DB.Es.Addr,
+		I_size:  config.Conf.DB.Es.Size,
+	}
+	Es.InitElasticSize()
+}

+ 33 - 0
fieldproject_inc_data/main.go

@@ -0,0 +1,33 @@
+package main
+
+import (
+	"fmt"
+	"github.com/spf13/cobra"
+)
+
+func init() {
+
+}
+
+func main() {
+	rootCmd := &cobra.Command{Use: "my cmd"}
+	rootCmd.AddCommand(timeTask())
+	//rootCmd.AddCommand(bidding())
+	if err := rootCmd.Execute(); err != nil {
+		fmt.Println("rootCmd.Execute failed", err.Error())
+	}
+}
+
+// @Description 供应商/经销商数据
+// @Author J 2022/8/11 16:49
+func timeTask() *cobra.Command {
+	cmdClient := &cobra.Command{
+		Use:   "time task",
+		Short: "Start processing inc field data",
+		Run: func(cmd *cobra.Command, args []string) {
+			//task()
+		},
+	}
+	//cmdClient.Flags().StringVarP(&cfg, "conf", "c", "", "server config [toml]")
+	return cmdClient
+}

Some files were not shown because too many files changed in this diff