|
@@ -0,0 +1,988 @@
|
|
|
+package utils
|
|
|
+
|
|
|
+import (
|
|
|
+ "bufio"
|
|
|
+ "crypto/md5"
|
|
|
+ cryRand "crypto/rand"
|
|
|
+ "crypto/sha1"
|
|
|
+ "encoding/base64"
|
|
|
+ "encoding/hex"
|
|
|
+ "encoding/json"
|
|
|
+ "errors"
|
|
|
+ "fmt"
|
|
|
+ "image"
|
|
|
+ "image/png"
|
|
|
+ "io"
|
|
|
+ "math"
|
|
|
+ "math/big"
|
|
|
+ "math/rand"
|
|
|
+ "net"
|
|
|
+ "net/http"
|
|
|
+ "os"
|
|
|
+ "os/exec"
|
|
|
+ "path"
|
|
|
+ "regexp"
|
|
|
+ "strconv"
|
|
|
+ "strings"
|
|
|
+ "time"
|
|
|
+)
|
|
|
+
|
|
|
+// 随机数种子
|
|
|
+var rnd = rand.New(rand.NewSource(time.Now().UnixNano()))
|
|
|
+
|
|
|
+func GetRandString(size int) string {
|
|
|
+ allLetterDigit := []string{"0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z", "!", "@", "#", "$", "%", "^", "&", "*"}
|
|
|
+ randomSb := ""
|
|
|
+ digitSize := len(allLetterDigit)
|
|
|
+ for i := 0; i < size; i++ {
|
|
|
+ randomSb += allLetterDigit[rnd.Intn(digitSize)]
|
|
|
+ }
|
|
|
+ return randomSb
|
|
|
+}
|
|
|
+
|
|
|
+func GetRandStringNoSpecialChar(size int) string {
|
|
|
+ allLetterDigit := []string{"0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z", "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z"}
|
|
|
+ randomSb := ""
|
|
|
+ digitSize := len(allLetterDigit)
|
|
|
+ for i := 0; i < size; i++ {
|
|
|
+ randomSb += allLetterDigit[rnd.Intn(digitSize)]
|
|
|
+ }
|
|
|
+ return randomSb
|
|
|
+}
|
|
|
+
|
|
|
+func StringsToJSON(str string) string {
|
|
|
+ rs := []rune(str)
|
|
|
+ jsons := ""
|
|
|
+ for _, r := range rs {
|
|
|
+ rint := int(r)
|
|
|
+ if rint < 128 {
|
|
|
+ jsons += string(r)
|
|
|
+ } else {
|
|
|
+ jsons += "\\u" + strconv.FormatInt(int64(rint), 16) // json
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return jsons
|
|
|
+}
|
|
|
+
|
|
|
+// 序列化
|
|
|
+func ToString(v interface{}) string {
|
|
|
+ data, _ := json.Marshal(v)
|
|
|
+ return string(data)
|
|
|
+}
|
|
|
+
|
|
|
+// md5加密
|
|
|
+func MD5(data string) string {
|
|
|
+ m := md5.Sum([]byte(data))
|
|
|
+ return hex.EncodeToString(m[:])
|
|
|
+}
|
|
|
+
|
|
|
+// 获取数字随机字符
|
|
|
+func GetRandDigit(n int) string {
|
|
|
+ return fmt.Sprintf("%0"+strconv.Itoa(n)+"d", rnd.Intn(int(math.Pow10(n))))
|
|
|
+}
|
|
|
+
|
|
|
+// 获取随机数
|
|
|
+func GetRandNumber(n int) int {
|
|
|
+ return rnd.Intn(n)
|
|
|
+}
|
|
|
+
|
|
|
+func GetRandInt(min, max int) int {
|
|
|
+ if min >= max || min == 0 || max == 0 {
|
|
|
+ return max
|
|
|
+ }
|
|
|
+ return rand.Intn(max-min) + min
|
|
|
+}
|
|
|
+
|
|
|
+func GetToday(format string) string {
|
|
|
+ today := time.Now().Format(format)
|
|
|
+ return today
|
|
|
+}
|
|
|
+
|
|
|
+// 获取今天剩余秒数
|
|
|
+func GetTodayLastSecond() time.Duration {
|
|
|
+ today := GetToday(FormatDate) + " 23:59:59"
|
|
|
+ end, _ := time.ParseInLocation(FormatDateTime, today, time.Local)
|
|
|
+ return time.Duration(end.Unix()-time.Now().Local().Unix()) * time.Second
|
|
|
+}
|
|
|
+
|
|
|
+// 处理出生日期函数
|
|
|
+func GetBrithDate(idcard string) string {
|
|
|
+ l := len(idcard)
|
|
|
+ var s string
|
|
|
+ if l == 15 {
|
|
|
+ s = "19" + idcard[6:8] + "-" + idcard[8:10] + "-" + idcard[10:12]
|
|
|
+ return s
|
|
|
+ }
|
|
|
+ if l == 18 {
|
|
|
+ s = idcard[6:10] + "-" + idcard[10:12] + "-" + idcard[12:14]
|
|
|
+ return s
|
|
|
+ }
|
|
|
+ return GetToday(FormatDate)
|
|
|
+}
|
|
|
+
|
|
|
+// 处理性别
|
|
|
+func WhichSexByIdcard(idcard string) string {
|
|
|
+ var sexs = [2]string{"女", "男"}
|
|
|
+ length := len(idcard)
|
|
|
+ if length == 18 {
|
|
|
+ sex, _ := strconv.Atoi(string(idcard[16]))
|
|
|
+ return sexs[sex%2]
|
|
|
+ } else if length == 15 {
|
|
|
+ sex, _ := strconv.Atoi(string(idcard[14]))
|
|
|
+ return sexs[sex%2]
|
|
|
+ }
|
|
|
+ return "男"
|
|
|
+}
|
|
|
+
|
|
|
+// 截取小数点后几位
|
|
|
+func SubFloatToString(f float64, m int) string {
|
|
|
+ n := strconv.FormatFloat(f, 'f', -1, 64)
|
|
|
+ if n == "" {
|
|
|
+ return ""
|
|
|
+ }
|
|
|
+ if m >= len(n) {
|
|
|
+ return n
|
|
|
+ }
|
|
|
+ newn := strings.Split(n, ".")
|
|
|
+ if m == 0 {
|
|
|
+ return newn[0]
|
|
|
+ }
|
|
|
+ if len(newn) < 2 || m >= len(newn[1]) {
|
|
|
+ return n
|
|
|
+ }
|
|
|
+ return newn[0] + "." + newn[1][:m]
|
|
|
+}
|
|
|
+
|
|
|
+// 截取小数点后几位
|
|
|
+func SubFloatToFloat(f float64, m int) float64 {
|
|
|
+ newn := SubFloatToString(f, m)
|
|
|
+ newf, _ := strconv.ParseFloat(newn, 64)
|
|
|
+ return newf
|
|
|
+}
|
|
|
+
|
|
|
+// 截取小数点后几位
|
|
|
+func SubFloatToFloatStr(f float64, m int) string {
|
|
|
+ newn := SubFloatToString(f, m)
|
|
|
+ return newn
|
|
|
+}
|
|
|
+
|
|
|
+// 获取相差时间-年
|
|
|
+func GetYearDiffer(start_time, end_time string) int {
|
|
|
+ t1, _ := time.ParseInLocation("2006-01-02", start_time, time.Local)
|
|
|
+ t2, _ := time.ParseInLocation("2006-01-02", end_time, time.Local)
|
|
|
+ age := t2.Year() - t1.Year()
|
|
|
+ if t2.Month() < t1.Month() || (t2.Month() == t1.Month() && t2.Day() < t1.Day()) {
|
|
|
+ age--
|
|
|
+ }
|
|
|
+ return age
|
|
|
+}
|
|
|
+
|
|
|
+// 获取相差时间-秒
|
|
|
+func GetSecondDifferByTime(start_time, end_time time.Time) int64 {
|
|
|
+ diff := end_time.Unix() - start_time.Unix()
|
|
|
+ return diff
|
|
|
+}
|
|
|
+
|
|
|
+func FixFloat(f float64, m int) float64 {
|
|
|
+ newn := SubFloatToString(f+0.00000001, m)
|
|
|
+ newf, _ := strconv.ParseFloat(newn, 64)
|
|
|
+ return newf
|
|
|
+}
|
|
|
+
|
|
|
+// 将字符串数组转化为逗号分割的字符串形式 ["str1","str2","str3"] >>> "str1,str2,str3"
|
|
|
+func StrListToString(strList []string) (str string) {
|
|
|
+ if len(strList) > 0 {
|
|
|
+ for k, v := range strList {
|
|
|
+ if k == 0 {
|
|
|
+ str = v
|
|
|
+ } else {
|
|
|
+ str = str + "," + v
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return
|
|
|
+ }
|
|
|
+ return ""
|
|
|
+}
|
|
|
+
|
|
|
+// Token
|
|
|
+func GetToken() string {
|
|
|
+ randStr := GetRandString(64)
|
|
|
+ token := MD5(randStr + Md5Key)
|
|
|
+ tokenLen := 64 - len(token)
|
|
|
+ return strings.ToUpper(token + GetRandString(tokenLen))
|
|
|
+}
|
|
|
+
|
|
|
+// 数据没有记录
|
|
|
+func ErrNoRow() string {
|
|
|
+ return "<QuerySeter> no row found"
|
|
|
+}
|
|
|
+
|
|
|
+// 判断文件是否存在
|
|
|
+func FileIsExist(filePath string) bool {
|
|
|
+ _, err := os.Stat(filePath)
|
|
|
+ return err == nil || os.IsExist(err)
|
|
|
+}
|
|
|
+
|
|
|
+// 获取图片扩展名
|
|
|
+func GetImgExt(file string) (ext string, err error) {
|
|
|
+ var headerByte []byte
|
|
|
+ headerByte = make([]byte, 8)
|
|
|
+ fd, err := os.Open(file)
|
|
|
+ if err != nil {
|
|
|
+ return "", err
|
|
|
+ }
|
|
|
+ defer fd.Close()
|
|
|
+ _, err = fd.Read(headerByte)
|
|
|
+ if err != nil {
|
|
|
+ return "", err
|
|
|
+ }
|
|
|
+ xStr := fmt.Sprintf("%x", headerByte)
|
|
|
+ switch {
|
|
|
+ case xStr == "89504e470d0a1a0a":
|
|
|
+ ext = ".png"
|
|
|
+ case xStr == "0000010001002020":
|
|
|
+ ext = ".ico"
|
|
|
+ case xStr == "0000020001002020":
|
|
|
+ ext = ".cur"
|
|
|
+ case xStr[:12] == "474946383961" || xStr[:12] == "474946383761":
|
|
|
+ ext = ".gif"
|
|
|
+ case xStr[:10] == "0000020000" || xStr[:10] == "0000100000":
|
|
|
+ ext = ".tga"
|
|
|
+ case xStr[:8] == "464f524d":
|
|
|
+ ext = ".iff"
|
|
|
+ case xStr[:8] == "52494646":
|
|
|
+ ext = ".ani"
|
|
|
+ case xStr[:4] == "4d4d" || xStr[:4] == "4949":
|
|
|
+ ext = ".tiff"
|
|
|
+ case xStr[:4] == "424d":
|
|
|
+ ext = ".bmp"
|
|
|
+ case xStr[:4] == "ffd8":
|
|
|
+ ext = ".jpg"
|
|
|
+ case xStr[:2] == "0a":
|
|
|
+ ext = ".pcx"
|
|
|
+ default:
|
|
|
+ ext = ""
|
|
|
+ }
|
|
|
+ return ext, nil
|
|
|
+}
|
|
|
+
|
|
|
+// 保存图片
|
|
|
+func SaveImage(path string, img image.Image) (err error) {
|
|
|
+ //需要保持的文件
|
|
|
+ imgfile, err := os.Create(path)
|
|
|
+ defer imgfile.Close()
|
|
|
+ // 以PNG格式保存文件
|
|
|
+ err = png.Encode(imgfile, img)
|
|
|
+ return err
|
|
|
+}
|
|
|
+
|
|
|
+// 下载图片
|
|
|
+func DownloadImage(imgUrl string) (filePath string, err error) {
|
|
|
+ imgPath := "./static/imgs/"
|
|
|
+ fileName := path.Base(imgUrl)
|
|
|
+ res, err := http.Get(imgUrl)
|
|
|
+ if err != nil {
|
|
|
+ fmt.Println("A error occurred!")
|
|
|
+ return
|
|
|
+ }
|
|
|
+ defer res.Body.Close()
|
|
|
+ // 获得get请求响应的reader对象
|
|
|
+ reader := bufio.NewReaderSize(res.Body, 32*1024)
|
|
|
+
|
|
|
+ filePath = imgPath + fileName
|
|
|
+ file, err := os.Create(filePath)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ // 获得文件的writer对象
|
|
|
+ writer := bufio.NewWriter(file)
|
|
|
+
|
|
|
+ written, _ := io.Copy(writer, reader)
|
|
|
+ fmt.Printf("Total length: %d \n", written)
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// 保存base64数据为文件
|
|
|
+func SaveBase64ToFile(content, path string) error {
|
|
|
+ data, err := base64.StdEncoding.DecodeString(content)
|
|
|
+ if err != nil {
|
|
|
+ return err
|
|
|
+ }
|
|
|
+ f, err := os.Create(path)
|
|
|
+ defer f.Close()
|
|
|
+ if err != nil {
|
|
|
+ return err
|
|
|
+ }
|
|
|
+ f.Write(data)
|
|
|
+ return nil
|
|
|
+}
|
|
|
+
|
|
|
+func SaveBase64ToFileBySeek(content, path string) (err error) {
|
|
|
+ data, err := base64.StdEncoding.DecodeString(content)
|
|
|
+ exist, err := PathExists(path)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ if !exist {
|
|
|
+ f, err := os.Create(path)
|
|
|
+ if err != nil {
|
|
|
+ return err
|
|
|
+ }
|
|
|
+ n, _ := f.Seek(0, 2)
|
|
|
+ // 从末尾的偏移量开始写入内容
|
|
|
+ _, err = f.WriteAt([]byte(data), n)
|
|
|
+ defer f.Close()
|
|
|
+ } else {
|
|
|
+ f, err := os.OpenFile(path, os.O_WRONLY, 0644)
|
|
|
+ if err != nil {
|
|
|
+ return err
|
|
|
+ }
|
|
|
+ n, _ := f.Seek(0, 2)
|
|
|
+ // 从末尾的偏移量开始写入内容
|
|
|
+ _, err = f.WriteAt([]byte(data), n)
|
|
|
+ defer f.Close()
|
|
|
+ }
|
|
|
+
|
|
|
+ return nil
|
|
|
+}
|
|
|
+
|
|
|
+func PathExists(path string) (bool, error) {
|
|
|
+ _, err := os.Stat(path)
|
|
|
+ if err == nil {
|
|
|
+ return true, nil
|
|
|
+ }
|
|
|
+ if os.IsNotExist(err) {
|
|
|
+ return false, nil
|
|
|
+ }
|
|
|
+ return false, err
|
|
|
+}
|
|
|
+
|
|
|
+func StartIndex(page, pagesize int) int {
|
|
|
+ if page > 1 {
|
|
|
+ return (page - 1) * pagesize
|
|
|
+ }
|
|
|
+ return 0
|
|
|
+}
|
|
|
+func PageCount(count, pagesize int) int {
|
|
|
+ if count%pagesize > 0 {
|
|
|
+ return count/pagesize + 1
|
|
|
+ } else {
|
|
|
+ return count / pagesize
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+func TrimHtml(src string) string {
|
|
|
+ //将HTML标签全转换成小写
|
|
|
+ re, _ := regexp.Compile("\\<[\\S\\s]+?\\>")
|
|
|
+ src = re.ReplaceAllStringFunc(src, strings.ToLower)
|
|
|
+
|
|
|
+ re, _ = regexp.Compile("\\<img[\\S\\s]+?\\>")
|
|
|
+ src = re.ReplaceAllString(src, "[图片]")
|
|
|
+
|
|
|
+ re, _ = regexp.Compile("class[\\S\\s]+?>")
|
|
|
+ src = re.ReplaceAllString(src, "")
|
|
|
+ re, _ = regexp.Compile("\\<[\\S\\s]+?\\>")
|
|
|
+ src = re.ReplaceAllString(src, "")
|
|
|
+ return strings.TrimSpace(src)
|
|
|
+}
|
|
|
+
|
|
|
+//1556164246 -> 2019-04-25 03:50:46 +0000
|
|
|
+//timestamp
|
|
|
+
|
|
|
+func TimeToTimestamp() {
|
|
|
+ fmt.Println(time.Unix(1556164246, 0).Format("2006-01-02 15:04:05"))
|
|
|
+}
|
|
|
+
|
|
|
+func ToUnicode(text string) string {
|
|
|
+ textQuoted := strconv.QuoteToASCII(text)
|
|
|
+ textUnquoted := textQuoted[1 : len(textQuoted)-1]
|
|
|
+ return textUnquoted
|
|
|
+}
|
|
|
+
|
|
|
+func VersionToInt(version string) int {
|
|
|
+ version = strings.Replace(version, ".", "", -1)
|
|
|
+ n, _ := strconv.Atoi(version)
|
|
|
+ return n
|
|
|
+}
|
|
|
+func IsCheckInList(list []int, s int) bool {
|
|
|
+ for _, v := range list {
|
|
|
+ if v == s {
|
|
|
+ return true
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return false
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+func round(num float64) int {
|
|
|
+ return int(num + math.Copysign(0.5, num))
|
|
|
+}
|
|
|
+
|
|
|
+func toFixed(num float64, precision int) float64 {
|
|
|
+ output := math.Pow(10, float64(precision))
|
|
|
+ return float64(round(num*output)) / output
|
|
|
+}
|
|
|
+
|
|
|
+// GetWilsonScore returns Wilson Score
|
|
|
+func GetWilsonScore(p, n float64) float64 {
|
|
|
+ if p == 0 && n == 0 {
|
|
|
+ return 0
|
|
|
+ }
|
|
|
+
|
|
|
+ return toFixed(((p+1.9208)/(p+n)-1.96*math.Sqrt(p*n/(p+n)+0.9604)/(p+n))/(1+3.8416/(p+n)), 2)
|
|
|
+}
|
|
|
+
|
|
|
+// 将中文数字转化成数字,比如 第三百四十五章,返回第345章 不支持一亿及以上
|
|
|
+func ChangeWordsToNum(str string) (numStr string) {
|
|
|
+ words := ([]rune)(str)
|
|
|
+ num := 0
|
|
|
+ n := 0
|
|
|
+ for i := 0; i < len(words); i++ {
|
|
|
+ word := string(words[i : i+1])
|
|
|
+ switch word {
|
|
|
+ case "万":
|
|
|
+ if n == 0 {
|
|
|
+ n = 1
|
|
|
+ }
|
|
|
+ n = n * 10000
|
|
|
+ num = num*10000 + n
|
|
|
+ n = 0
|
|
|
+ case "千":
|
|
|
+ if n == 0 {
|
|
|
+ n = 1
|
|
|
+ }
|
|
|
+ n = n * 1000
|
|
|
+ num += n
|
|
|
+ n = 0
|
|
|
+ case "百":
|
|
|
+ if n == 0 {
|
|
|
+ n = 1
|
|
|
+ }
|
|
|
+ n = n * 100
|
|
|
+ num += n
|
|
|
+ n = 0
|
|
|
+ case "十":
|
|
|
+ if n == 0 {
|
|
|
+ n = 1
|
|
|
+ }
|
|
|
+ n = n * 10
|
|
|
+ num += n
|
|
|
+ n = 0
|
|
|
+ case "一":
|
|
|
+ n += 1
|
|
|
+ case "二":
|
|
|
+ n += 2
|
|
|
+ case "三":
|
|
|
+ n += 3
|
|
|
+ case "四":
|
|
|
+ n += 4
|
|
|
+ case "五":
|
|
|
+ n += 5
|
|
|
+ case "六":
|
|
|
+ n += 6
|
|
|
+ case "七":
|
|
|
+ n += 7
|
|
|
+ case "八":
|
|
|
+ n += 8
|
|
|
+ case "九":
|
|
|
+ n += 9
|
|
|
+ case "零":
|
|
|
+ default:
|
|
|
+ if n > 0 {
|
|
|
+ num += n
|
|
|
+ n = 0
|
|
|
+ }
|
|
|
+ if num == 0 {
|
|
|
+ numStr += word
|
|
|
+ } else {
|
|
|
+ numStr += strconv.Itoa(num) + word
|
|
|
+ num = 0
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if n > 0 {
|
|
|
+ num += n
|
|
|
+ n = 0
|
|
|
+ }
|
|
|
+ if num != 0 {
|
|
|
+ numStr += strconv.Itoa(num)
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+func Sha1(data string) string {
|
|
|
+ sha1 := sha1.New()
|
|
|
+ sha1.Write([]byte(data))
|
|
|
+ return hex.EncodeToString(sha1.Sum([]byte("")))
|
|
|
+}
|
|
|
+
|
|
|
+func GetVideoPlaySeconds(videoPath string) (playSeconds float64, err error) {
|
|
|
+ cmd := `ffmpeg -i ` + videoPath + ` 2>&1 | grep 'Duration' | cut -d ' ' -f 4 | sed s/,//`
|
|
|
+ out, err := exec.Command("bash", "-c", cmd).Output()
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ outTimes := string(out)
|
|
|
+ fmt.Println("outTimes:", outTimes)
|
|
|
+ if outTimes != "" {
|
|
|
+ timeArr := strings.Split(outTimes, ":")
|
|
|
+ h := timeArr[0]
|
|
|
+ m := timeArr[1]
|
|
|
+ s := timeArr[2]
|
|
|
+ hInt, err := strconv.Atoi(h)
|
|
|
+ if err != nil {
|
|
|
+ return playSeconds, err
|
|
|
+ }
|
|
|
+
|
|
|
+ mInt, err := strconv.Atoi(m)
|
|
|
+ if err != nil {
|
|
|
+ return playSeconds, err
|
|
|
+ }
|
|
|
+ s = strings.Trim(s, " ")
|
|
|
+ s = strings.Trim(s, "\n")
|
|
|
+ sInt, err := strconv.ParseFloat(s, 64)
|
|
|
+ if err != nil {
|
|
|
+ return playSeconds, err
|
|
|
+ }
|
|
|
+ playSeconds = float64(hInt)*3600 + float64(mInt)*60 + float64(sInt)
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+func GetMaxTradeCode(tradeCode string) (maxTradeCode string, err error) {
|
|
|
+ tradeCode = strings.Replace(tradeCode, "W", "", -1)
|
|
|
+ tradeCode = strings.Trim(tradeCode, " ")
|
|
|
+ tradeCodeInt, err := strconv.Atoi(tradeCode)
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ tradeCodeInt = tradeCodeInt + 1
|
|
|
+ maxTradeCode = fmt.Sprintf("W%06d", tradeCodeInt)
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// excel日期字段格式化 yyyy-mm-dd
|
|
|
+func ConvertToFormatDay(excelDaysString string) string {
|
|
|
+ // 2006-01-02 距离 1900-01-01的天数
|
|
|
+ baseDiffDay := 38719 //在网上工具计算的天数需要加2天,什么原因没弄清楚
|
|
|
+ curDiffDay := excelDaysString
|
|
|
+ b, _ := strconv.Atoi(curDiffDay)
|
|
|
+ // 获取excel的日期距离2006-01-02的天数
|
|
|
+ realDiffDay := b - baseDiffDay
|
|
|
+ //fmt.Println("realDiffDay:",realDiffDay)
|
|
|
+ // 距离2006-01-02 秒数
|
|
|
+ realDiffSecond := realDiffDay * 24 * 3600
|
|
|
+ //fmt.Println("realDiffSecond:",realDiffSecond)
|
|
|
+ // 2006-01-02 15:04:05距离1970-01-01 08:00:00的秒数 网上工具可查出
|
|
|
+ baseOriginSecond := 1136185445
|
|
|
+ resultTime := time.Unix(int64(baseOriginSecond+realDiffSecond), 0).Format("2006-01-02")
|
|
|
+ return resultTime
|
|
|
+}
|
|
|
+
|
|
|
+func CheckPwd(pwd string) bool {
|
|
|
+ compile := `([0-9a-z]+){6,12}|(a-z0-9]+){6,12}`
|
|
|
+ reg := regexp.MustCompile(compile)
|
|
|
+ flag := reg.MatchString(pwd)
|
|
|
+ return flag
|
|
|
+}
|
|
|
+
|
|
|
+func GetMonthStartAndEnd(myYear string, myMonth string) (startDate, endDate string) {
|
|
|
+ // 数字月份必须前置补零
|
|
|
+ if len(myMonth) == 1 {
|
|
|
+ myMonth = "0" + myMonth
|
|
|
+ }
|
|
|
+ yInt, _ := strconv.Atoi(myYear)
|
|
|
+
|
|
|
+ timeLayout := "2006-01-02 15:04:05"
|
|
|
+ loc, _ := time.LoadLocation("Local")
|
|
|
+ theTime, _ := time.ParseInLocation(timeLayout, myYear+"-"+myMonth+"-01 00:00:00", loc)
|
|
|
+ newMonth := theTime.Month()
|
|
|
+
|
|
|
+ t1 := time.Date(yInt, newMonth, 1, 0, 0, 0, 0, time.Local).Format("2006-01-02")
|
|
|
+ t2 := time.Date(yInt, newMonth+1, 0, 0, 0, 0, 0, time.Local).Format("2006-01-02")
|
|
|
+ return t1, t2
|
|
|
+}
|
|
|
+
|
|
|
+// 移除字符串中的空格
|
|
|
+func TrimStr(str string) (str2 string) {
|
|
|
+ return strings.Replace(str, " ", "", -1)
|
|
|
+}
|
|
|
+
|
|
|
+// 字符串转换为time
|
|
|
+func StrTimeToTime(strTime string) time.Time {
|
|
|
+ timeLayout := "2006-01-02 15:04:05" //转化所需模板
|
|
|
+ loc, _ := time.LoadLocation("Local") //重要:获取时区
|
|
|
+ resultTime, _ := time.ParseInLocation(timeLayout, strTime, loc)
|
|
|
+ return resultTime
|
|
|
+}
|
|
|
+
|
|
|
+// 字符串类型时间转周几
|
|
|
+func StrDateTimeToWeek(strTime string) string {
|
|
|
+ var WeekDayMap = map[string]string{
|
|
|
+ "Monday": "周一",
|
|
|
+ "Tuesday": "周二",
|
|
|
+ "Wednesday": "周三",
|
|
|
+ "Thursday": "周四",
|
|
|
+ "Friday": "周五",
|
|
|
+ "Saturday": "周六",
|
|
|
+ "Sunday": "周日",
|
|
|
+ }
|
|
|
+ var ctime = StrTimeToTime(strTime).Format("2006-01-02")
|
|
|
+ startday, _ := time.Parse("2006-01-02", ctime)
|
|
|
+ staweek_int := startday.Weekday().String()
|
|
|
+ return WeekDayMap[staweek_int]
|
|
|
+}
|
|
|
+
|
|
|
+// 时间格式转年月日字符串
|
|
|
+func TimeToStrYmd(time2 time.Time) string {
|
|
|
+ var Ymd string
|
|
|
+ year := time2.Year()
|
|
|
+ month := time2.Format("1")
|
|
|
+ day1 := time.Now().Day()
|
|
|
+ Ymd = strconv.Itoa(year) + "年" + month + "月" + strconv.Itoa(day1) + "日"
|
|
|
+ return Ymd
|
|
|
+}
|
|
|
+
|
|
|
+// 时间格式去掉时分秒
|
|
|
+func TimeRemoveHms(strTime string) string {
|
|
|
+ var Ymd string
|
|
|
+ var resultTime = StrTimeToTime(strTime)
|
|
|
+ year := resultTime.Year()
|
|
|
+ month := resultTime.Format("01")
|
|
|
+ day1 := resultTime.Day()
|
|
|
+ Ymd = strconv.Itoa(year) + "." + month + "." + strconv.Itoa(day1)
|
|
|
+ return Ymd
|
|
|
+}
|
|
|
+
|
|
|
+// 文章上一次编辑时间
|
|
|
+func ArticleLastTime(strTime string) string {
|
|
|
+ var newTime string
|
|
|
+ stamp, _ := time.ParseInLocation("2006-01-02 15:04:05", strTime, time.Local)
|
|
|
+ diffTime := time.Now().Unix() - stamp.Unix()
|
|
|
+ if diffTime <= 60 {
|
|
|
+ newTime = "当前"
|
|
|
+ } else if diffTime < 60*60 {
|
|
|
+ newTime = strconv.FormatInt(diffTime/60, 10) + "分钟前"
|
|
|
+ } else if diffTime < 24*60*60 {
|
|
|
+ newTime = strconv.FormatInt(diffTime/(60*60), 10) + "小时前"
|
|
|
+ } else if diffTime < 30*24*60*60 {
|
|
|
+ newTime = strconv.FormatInt(diffTime/(24*60*60), 10) + "天前"
|
|
|
+ } else if diffTime < 12*30*24*60*60 {
|
|
|
+ newTime = strconv.FormatInt(diffTime/(30*24*60*60), 10) + "月前"
|
|
|
+ } else {
|
|
|
+ newTime = "1年前"
|
|
|
+ }
|
|
|
+ return newTime
|
|
|
+}
|
|
|
+
|
|
|
+// 人民币小写转大写
|
|
|
+func ConvertNumToCny(num float64) (str string, err error) {
|
|
|
+ strNum := strconv.FormatFloat(num*100, 'f', 0, 64)
|
|
|
+ sliceUnit := []string{"仟", "佰", "拾", "亿", "仟", "佰", "拾", "万", "仟", "佰", "拾", "元", "角", "分"}
|
|
|
+ // log.Println(sliceUnit[:len(sliceUnit)-2])
|
|
|
+ s := sliceUnit[len(sliceUnit)-len(strNum):]
|
|
|
+ upperDigitUnit := map[string]string{"0": "零", "1": "壹", "2": "贰", "3": "叁", "4": "肆", "5": "伍", "6": "陆", "7": "柒", "8": "捌", "9": "玖"}
|
|
|
+ for k, v := range strNum[:] {
|
|
|
+ str = str + upperDigitUnit[string(v)] + s[k]
|
|
|
+ }
|
|
|
+ reg, err := regexp.Compile(`零角零分$`)
|
|
|
+ str = reg.ReplaceAllString(str, "整")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零角`)
|
|
|
+ str = reg.ReplaceAllString(str, "零")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零分$`)
|
|
|
+ str = reg.ReplaceAllString(str, "整")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零[仟佰拾]`)
|
|
|
+ str = reg.ReplaceAllString(str, "零")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零{2,}`)
|
|
|
+ str = reg.ReplaceAllString(str, "零")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零亿`)
|
|
|
+ str = reg.ReplaceAllString(str, "亿")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零万`)
|
|
|
+ str = reg.ReplaceAllString(str, "万")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零*元`)
|
|
|
+ str = reg.ReplaceAllString(str, "元")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`亿零{0, 3}万`)
|
|
|
+ str = reg.ReplaceAllString(str, "^元")
|
|
|
+
|
|
|
+ reg, err = regexp.Compile(`零元`)
|
|
|
+ str = reg.ReplaceAllString(str, "零")
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowWeekMonday 获取本周周一的时间
|
|
|
+func GetNowWeekMonday() time.Time {
|
|
|
+ offset := int(time.Monday - time.Now().Weekday())
|
|
|
+ mondayTime := time.Now().AddDate(0, 0, offset)
|
|
|
+ mondayTime = time.Date(mondayTime.Year(), mondayTime.Month(), mondayTime.Day(), 0, 0, 0, 0, mondayTime.Location())
|
|
|
+ return mondayTime
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowWeekLastDay 获取本周最后一天的时间
|
|
|
+func GetNowWeekLastDay() time.Time {
|
|
|
+ offset := int(time.Monday - time.Now().Weekday())
|
|
|
+ firstDayTime := time.Now().AddDate(0, 0, offset)
|
|
|
+ firstDayTime = time.Date(firstDayTime.Year(), firstDayTime.Month(), firstDayTime.Day(), 0, 0, 0, 0, firstDayTime.Location()).AddDate(0, 0, 6)
|
|
|
+ lastDayTime := time.Date(firstDayTime.Year(), firstDayTime.Month(), firstDayTime.Day(), 23, 59, 59, 0, firstDayTime.Location())
|
|
|
+
|
|
|
+ return lastDayTime
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowMonthFirstDay 获取本月第一天的时间
|
|
|
+func GetNowMonthFirstDay() time.Time {
|
|
|
+ nowMonthFirstDay := time.Date(time.Now().Year(), time.Now().Month(), 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ return nowMonthFirstDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowMonthLastDay 获取本月最后一天的时间
|
|
|
+func GetNowMonthLastDay() time.Time {
|
|
|
+ nowMonthLastDay := time.Date(time.Now().Year(), time.Now().Month(), 1, 0, 0, 0, 0, time.Now().Location()).AddDate(0, 1, -1)
|
|
|
+ nowMonthLastDay = time.Date(nowMonthLastDay.Year(), nowMonthLastDay.Month(), nowMonthLastDay.Day(), 23, 59, 59, 0, nowMonthLastDay.Location())
|
|
|
+ return nowMonthLastDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowQuarterFirstDay 获取本季度第一天的时间
|
|
|
+func GetNowQuarterFirstDay() time.Time {
|
|
|
+ month := int(time.Now().Month())
|
|
|
+ var nowQuarterFirstDay time.Time
|
|
|
+ if month >= 1 && month <= 3 {
|
|
|
+ //1月1号
|
|
|
+ nowQuarterFirstDay = time.Date(time.Now().Year(), 1, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ } else if month >= 4 && month <= 6 {
|
|
|
+ //4月1号
|
|
|
+ nowQuarterFirstDay = time.Date(time.Now().Year(), 4, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ } else if month >= 7 && month <= 9 {
|
|
|
+ nowQuarterFirstDay = time.Date(time.Now().Year(), 7, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ } else {
|
|
|
+ nowQuarterFirstDay = time.Date(time.Now().Year(), 10, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ }
|
|
|
+ return nowQuarterFirstDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowQuarterLastDay 获取本季度最后一天的时间
|
|
|
+func GetNowQuarterLastDay() time.Time {
|
|
|
+ month := int(time.Now().Month())
|
|
|
+ var nowQuarterLastDay time.Time
|
|
|
+ if month >= 1 && month <= 3 {
|
|
|
+ //03-31 23:59:59
|
|
|
+ nowQuarterLastDay = time.Date(time.Now().Year(), 3, 31, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ } else if month >= 4 && month <= 6 {
|
|
|
+ //06-30 23:59:59
|
|
|
+ nowQuarterLastDay = time.Date(time.Now().Year(), 6, 30, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ } else if month >= 7 && month <= 9 {
|
|
|
+ //09-30 23:59:59
|
|
|
+ nowQuarterLastDay = time.Date(time.Now().Year(), 9, 30, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ } else {
|
|
|
+ //12-31 23:59:59
|
|
|
+ nowQuarterLastDay = time.Date(time.Now().Year(), 12, 31, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ }
|
|
|
+ return nowQuarterLastDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowHalfYearFirstDay 获取当前半年的第一天的时间
|
|
|
+func GetNowHalfYearFirstDay() time.Time {
|
|
|
+ month := int(time.Now().Month())
|
|
|
+ var nowHalfYearLastDay time.Time
|
|
|
+ if month >= 1 && month <= 6 {
|
|
|
+ //03-31 23:59:59
|
|
|
+ nowHalfYearLastDay = time.Date(time.Now().Year(), 1, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ } else {
|
|
|
+ //12-31 23:59:59
|
|
|
+ nowHalfYearLastDay = time.Date(time.Now().Year(), 7, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ }
|
|
|
+ return nowHalfYearLastDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowHalfYearLastDay 获取当前半年的最后一天的时间
|
|
|
+func GetNowHalfYearLastDay() time.Time {
|
|
|
+ month := int(time.Now().Month())
|
|
|
+ var nowHalfYearLastDay time.Time
|
|
|
+ if month >= 1 && month <= 6 {
|
|
|
+ //03-31 23:59:59
|
|
|
+ nowHalfYearLastDay = time.Date(time.Now().Year(), 6, 30, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ } else {
|
|
|
+ //12-31 23:59:59
|
|
|
+ nowHalfYearLastDay = time.Date(time.Now().Year(), 12, 31, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ }
|
|
|
+ return nowHalfYearLastDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowYearFirstDay 获取当前年的最后一天的时间
|
|
|
+func GetNowYearFirstDay() time.Time {
|
|
|
+ //12-31 23:59:59
|
|
|
+ nowYearFirstDay := time.Date(time.Now().Year(), 1, 1, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ return nowYearFirstDay
|
|
|
+}
|
|
|
+
|
|
|
+// GetNowYearLastDay 获取当前年的最后一天的时间
|
|
|
+func GetNowYearLastDay() time.Time {
|
|
|
+ //12-31 23:59:59
|
|
|
+ nowYearLastDay := time.Date(time.Now().Year(), 12, 31, 23, 59, 59, 0, time.Now().Location())
|
|
|
+ return nowYearLastDay
|
|
|
+}
|
|
|
+
|
|
|
+// CalculationDate 计算两个日期之间相差n年m月y天
|
|
|
+func CalculationDate(startDate, endDate time.Time) (beetweenDay string, err error) {
|
|
|
+ //startDate := time.Date(2021, 3, 28, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ //endDate := time.Date(2022, 3, 31, 0, 0, 0, 0, time.Now().Location())
|
|
|
+ numYear := endDate.Year() - startDate.Year()
|
|
|
+
|
|
|
+ numMonth := int(endDate.Month()) - int(startDate.Month())
|
|
|
+
|
|
|
+ numDay := 0
|
|
|
+ //获取截止月的总天数
|
|
|
+ endDateDays := getMonthDay(endDate.Year(), int(endDate.Month()))
|
|
|
+
|
|
|
+ //获取截止月的前一个月
|
|
|
+ endDatePrevMonthDate := endDate.AddDate(0, -1, 0)
|
|
|
+ //获取截止日期的上一个月的总天数
|
|
|
+ endDatePrevMonthDays := getMonthDay(endDatePrevMonthDate.Year(), int(endDatePrevMonthDate.Month()))
|
|
|
+ //获取开始日期的的月份总天数
|
|
|
+ startDateMonthDays := getMonthDay(startDate.Year(), int(startDate.Month()))
|
|
|
+
|
|
|
+ //判断,截止月是否完全被选中,如果相等,那么代表截止月份全部天数被选择
|
|
|
+ if endDate.Day() == endDateDays {
|
|
|
+ numDay = startDateMonthDays - startDate.Day() + 1
|
|
|
+
|
|
|
+ //如果剩余天数正好与开始日期的天数是一致的,那么月份加1
|
|
|
+ if numDay == startDateMonthDays {
|
|
|
+ numMonth++
|
|
|
+ numDay = 0
|
|
|
+ //超过月份了,那么年份加1
|
|
|
+ if numMonth == 12 {
|
|
|
+ numYear++
|
|
|
+ numMonth = 0
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ numDay = endDate.Day() - startDate.Day() + 1
|
|
|
+ }
|
|
|
+
|
|
|
+ //天数小于0,那么向月份借一位
|
|
|
+ if numDay < 0 {
|
|
|
+ //向上一个月借一个月的天数
|
|
|
+ numDay += endDatePrevMonthDays
|
|
|
+
|
|
|
+ //总月份减去一个月
|
|
|
+ numMonth = numMonth - 1
|
|
|
+ }
|
|
|
+
|
|
|
+ //月份小于0,那么向年份借一位
|
|
|
+ if numMonth < 0 {
|
|
|
+ //向上一个年借12个月
|
|
|
+ numMonth += 12
|
|
|
+
|
|
|
+ //总年份减去一年
|
|
|
+ numYear = numYear - 1
|
|
|
+ }
|
|
|
+ if numYear < 0 {
|
|
|
+ err = errors.New("日期异常")
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ if numYear > 0 {
|
|
|
+ beetweenDay += fmt.Sprint(numYear, "年")
|
|
|
+ }
|
|
|
+ if numMonth > 0 {
|
|
|
+ beetweenDay += fmt.Sprint(numMonth, "个月")
|
|
|
+ }
|
|
|
+ if numDay > 0 {
|
|
|
+ beetweenDay += fmt.Sprint(numDay, "天")
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// getMonthDay 获取某年某月有多少天
|
|
|
+func getMonthDay(year, month int) (days int) {
|
|
|
+ if month != 2 {
|
|
|
+ if month == 4 || month == 6 || month == 9 || month == 11 {
|
|
|
+ days = 30
|
|
|
+
|
|
|
+ } else {
|
|
|
+ days = 31
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ if ((year%4) == 0 && (year%100) != 0) || (year%400) == 0 {
|
|
|
+ days = 29
|
|
|
+ } else {
|
|
|
+ days = 28
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// GetOrmInReplace 获取orm的in查询替换?的方法
|
|
|
+func GetOrmInReplace(num int) string {
|
|
|
+ template := make([]string, num)
|
|
|
+ for i := 0; i < num; i++ {
|
|
|
+ template[i] = "?"
|
|
|
+ }
|
|
|
+ return strings.Join(template, ",")
|
|
|
+}
|
|
|
+
|
|
|
+// InArrayByInt php中的in_array(判断Int类型的切片中是否存在该int值)
|
|
|
+func InArrayByInt(idIntList []int, searchId int) (has bool) {
|
|
|
+ for _, id := range idIntList {
|
|
|
+ if id == searchId {
|
|
|
+ has = true
|
|
|
+ return
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// InArrayByStr php中的in_array(判断String类型的切片中是否存在该string值)
|
|
|
+func InArrayByStr(idStrList []string, searchId string) (has bool) {
|
|
|
+ for _, id := range idStrList {
|
|
|
+ if id == searchId {
|
|
|
+ has = true
|
|
|
+ return
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|
|
|
+
|
|
|
+// RangeRand 取区间随机数
|
|
|
+func RangeRand(min, max int64) int64 {
|
|
|
+ if min > max {
|
|
|
+ return max
|
|
|
+ }
|
|
|
+ if min < 0 {
|
|
|
+ f64Min := math.Abs(float64(min))
|
|
|
+ i64Min := int64(f64Min)
|
|
|
+ result, _ := cryRand.Int(cryRand.Reader, big.NewInt(max+1+i64Min))
|
|
|
+
|
|
|
+ return result.Int64() - i64Min
|
|
|
+ } else {
|
|
|
+ result, _ := cryRand.Int(cryRand.Reader, big.NewInt(max-min+1))
|
|
|
+ return min + result.Int64()
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+func GetLocalIP() (ip string, err error) {
|
|
|
+ addrs, err := net.InterfaceAddrs()
|
|
|
+ if err != nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+ for _, addr := range addrs {
|
|
|
+ ipAddr, ok := addr.(*net.IPNet)
|
|
|
+ if !ok {
|
|
|
+ continue
|
|
|
+ }
|
|
|
+ if ipAddr.IP.IsLoopback() {
|
|
|
+ continue
|
|
|
+ }
|
|
|
+ if !ipAddr.IP.IsGlobalUnicast() {
|
|
|
+ continue
|
|
|
+ }
|
|
|
+ return ipAddr.IP.String(), nil
|
|
|
+ }
|
|
|
+ return
|
|
|
+}
|