123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320 |
- package tool
- import (
- "bufio"
- "bytes"
- "errors"
- "fmt"
- "io"
- "math"
- "math/rand"
- "net"
- "net/http"
- "net/url"
- "os"
- "regexp"
- "strconv"
- "strings"
- "time"
- "unicode"
- )
- // GetOrderNumber 获取订单号
- func GetOrderNumber() string {
- parse, _ := time.Parse(time.DateTime, "2021-04-27 00:00:00")
- hours := time.Now().Sub(parse).Hours()
- day := math.Floor(hours / 24)
- prefix := fmt.Sprintf("%05d", int64(day))
- format := time.Now().Format("") + "%0" + strconv.Itoa(10) + "d"
- n := math.Pow10(10)
- return prefix + fmt.Sprintf(format, rand.New(rand.NewSource(time.Now().UnixNano())).Int63n(int64(n)))
- }
- // ByteFmt 格式化显示文件大小
- func ByteFmt(size int64) string {
- var unitArr = []string{"B", "KB", "MB", "GB", "TB", "EB"}
- if size == 0 {
- return "unknown"
- }
- fs := float64(size)
- p := int(math.Log(fs) / math.Log(1024))
- val := fs / math.Pow(1024, float64(p))
- _, frac := math.Modf(val)
- if frac > 0 {
- return fmt.Sprintf("%.1f%s", math.Floor(val*10)/10, unitArr[p])
- } else {
- return fmt.Sprintf("%d%s", int(val), unitArr[p])
- }
- }
- // UniqueArray 切片唯一值
- func UniqueArray[T comparable](array []T) []T {
- result := make([]T, 0, len(array))
- temp := map[T]struct{}{}
- for _, item := range array {
- if _, ok := temp[item]; !ok {
- temp[item] = struct{}{}
- result = append(result, item)
- }
- }
- return result
- }
- // InArray 是否在切片
- func InArray[T comparable](item T, array []T) bool {
- for _, s := range array {
- if item == s {
- return true
- }
- }
- return false
- }
- func ChunkArray[T comparable](array []T, size int) (ss [][]T) {
- if size <= 0 || len(array) <= size {
- return
- }
- mod := len(array) % size
- k := len(array) / size
- var end int
- if mod == 0 {
- end = k
- } else {
- end = k + 1
- }
- for i := 0; i < end; i++ {
- if i != k {
- ss = append(ss, array[i*size:(i+1)*size])
- } else {
- ss = append(ss, array[i*size:])
- }
- }
- return
- }
- // IsChinese 判断字符串是否包含中文
- func IsChinese(str string) bool {
- var count int
- for _, v := range str {
- if unicode.Is(unicode.Han, v) {
- count++
- break
- }
- }
- return count > 0
- }
- // RandInt 随机数
- func RandInt(max int) int {
- if max <= 0 {
- return 0
- }
- return rand.Intn(max)
- }
- // FindIPv4 字符串中查找IP4
- func FindIPv4(input string) string {
- partIp := "(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])"
- must := partIp + "\\." + partIp + "\\." + partIp + "\\." + partIp
- matchMe := regexp.MustCompile(must)
- return matchMe.FindString(input)
- }
- // RandString 随机字符串
- func RandString(n int) string {
- var letterRunes = []rune("0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")
- b := make([]rune, n)
- for i := range b {
- b[i] = letterRunes[RandInt(len(letterRunes))]
- }
- return string(b)
- }
- // IP4ToInt ip4地址转Int类型
- func IP4ToInt(ip net.IP) int {
- ipSplit := strings.Split(ip.To4().String(), ".")
- var ipInt = 0
- var pos uint = 24
- for _, ipSeg := range ipSplit {
- tempInt, _ := strconv.Atoi(ipSeg)
- tempInt = tempInt << pos
- ipInt = ipInt | tempInt
- pos -= 8
- }
- return ipInt
- }
- // IP4IntToString 反序列化Int为IP4地址
- func IP4IntToString(ipInt int) string {
- ipSplit := make([]string, 4)
- var length = len(ipSplit)
- buffer := bytes.NewBufferString("")
- for i := 0; i < length; i++ {
- tempInt := ipInt & 0xFF
- ipSplit[length-i-1] = strconv.Itoa(tempInt)
- ipInt = ipInt >> 8
- }
- for i := 0; i < length; i++ {
- buffer.WriteString(ipSplit[i])
- if i < length-1 {
- buffer.WriteString(".")
- }
- }
- return buffer.String()
- }
- // CompareVersion 比较`x.y.z`类型版本号大小
- func CompareVersion(verCurrent, verUpdate string) int {
- versionA := strings.Split(verCurrent, ".")
- versionB := strings.Split(verUpdate, ".")
- for i := len(versionA); i < 4; i++ {
- versionA = append(versionA, "0")
- }
- for i := len(versionB); i < 4; i++ {
- versionB = append(versionB, "0")
- }
- for i := 0; i < 4; i++ {
- version1, _ := strconv.Atoi(versionA[i])
- version2, _ := strconv.Atoi(versionB[i])
- if version1 == version2 {
- continue
- } else if version1 > version2 {
- return 1
- } else {
- return -1
- }
- }
- return 0
- }
- // GetLocalIP 获取内网本机ipv4地址
- func GetLocalIP() (string, error) {
- var address []net.Addr
- eth0Interface, err := net.InterfaceByName("eth0")
- if err == nil {
- address, err = eth0Interface.Addrs()
- } else {
- address, err = net.InterfaceAddrs()
- }
- if err != nil {
- return "", err
- }
- for _, addr := range address {
- if it, ok := addr.(*net.IPNet); ok && !it.IP.IsLoopback() {
- if it.IP.To4() != nil {
- return it.IP.String(), nil
- }
- }
- }
- return "", err
- }
- // GetInternetIP 获取外网本机ipv4地址
- func GetInternetIP() (string, error) {
- resp, err := http.Get("https://api.ipify.org")
- if err != nil {
- resp, err = http.Get("https://icanhazip.com")
- if err != nil {
- return "", err
- }
- }
- defer func() {
- _ = resp.Body.Close()
- }()
- s, readErr := io.ReadAll(resp.Body)
- if readErr != nil {
- return "", readErr
- }
- return string(s), nil
- }
- // IsExists 检测指定路径文件或者文件夹是否存在
- func IsExists(path string) bool {
- _, err := os.Stat(path) //os.Stat获取文件信息
- if err != nil {
- if os.IsExist(err) {
- return true
- }
- return false
- }
- return true
- }
- // CheckWebsiteAddr 检查域名是否正确
- func CheckWebsiteAddr(addr string) error {
- if 0 == len(addr) {
- return errors.New("url is empty")
- }
- parse, err := url.Parse(addr)
- if err != nil {
- return err
- }
- if "http" != parse.Scheme && "https" != parse.Scheme {
- return errors.New("url Scheme illegal. err:" + parse.Scheme)
- }
- re := regexp.MustCompile(`^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$|^(([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)+([A-Za-z]|[A-Za-z][A-Za-z0-9\-]*[A-Za-z0-9])$`)
- u := strings.Split(parse.Host, ":")
- if 2 == len(u) && 0 != len(u[1]) {
- result := re.FindAllStringSubmatch(u[0], -1)
- if result == nil {
- return errors.New("url illegal. err:" + u[0])
- }
- return nil
- }
- result := re.FindAllStringSubmatch(parse.Host, -1)
- if result == nil {
- return errors.New("url illegal. err:" + parse.Host)
- }
- return nil
- }
- // LoadKeyValConfig 获取本地`a=c\n`类型文件的键值对
- func LoadKeyValConfig(text string) map[string]string {
- config := make(map[string]string)
- r := bufio.NewReader(bytes.NewBufferString(text))
- for {
- b, _, err := r.ReadLine()
- if err != nil {
- if err == io.EOF {
- break
- }
- panic(err)
- }
- s := strings.TrimSpace(string(b))
- index := strings.Index(s, "=")
- if index < 0 || strings.HasPrefix(s, "#") {
- continue
- }
- key := strings.TrimSpace(s[:index])
- if len(key) == 0 {
- continue
- }
- value := strings.TrimSpace(s[index+1:])
- if len(value) == 0 {
- continue
- }
- config[key] = value
- }
- return config
- }
- // PortIsUse 判断端口是否占用
- func PortIsUse(port int) bool {
- _, tcpError := net.DialTimeout("tcp", fmt.Sprintf(":%d", port), time.Millisecond*50)
- udpAddr, _ := net.ResolveUDPAddr("udp4", fmt.Sprintf(":%d", port))
- udpConn, udpError := net.ListenUDP("udp", udpAddr)
- if udpConn != nil {
- defer func() {
- _ = udpConn.Close()
- }()
- }
- return tcpError == nil || udpError != nil
- }
|