util.go 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463
  1. package common
  2. import (
  3. "bytes"
  4. "encoding/base64"
  5. "encoding/binary"
  6. "errors"
  7. "html/template"
  8. "io"
  9. "io/ioutil"
  10. "net"
  11. "net/http"
  12. "os"
  13. "regexp"
  14. "strconv"
  15. "strings"
  16. "sync"
  17. "ehang.io/nps/lib/crypt"
  18. )
  19. //Get the corresponding IP address through domain name
  20. func GetHostByName(hostname string) string {
  21. if !DomainCheck(hostname) {
  22. return hostname
  23. }
  24. ips, _ := net.LookupIP(hostname)
  25. if ips != nil {
  26. for _, v := range ips {
  27. if v.To4() != nil {
  28. return v.String()
  29. }
  30. }
  31. }
  32. return ""
  33. }
  34. //Check the legality of domain
  35. func DomainCheck(domain string) bool {
  36. var match bool
  37. IsLine := "^((http://)|(https://))?([a-zA-Z0-9]([a-zA-Z0-9\\-]{0,61}[a-zA-Z0-9])?\\.)+[a-zA-Z]{2,6}(/)"
  38. NotLine := "^((http://)|(https://))?([a-zA-Z0-9]([a-zA-Z0-9\\-]{0,61}[a-zA-Z0-9])?\\.)+[a-zA-Z]{2,6}"
  39. match, _ = regexp.MatchString(IsLine, domain)
  40. if !match {
  41. match, _ = regexp.MatchString(NotLine, domain)
  42. }
  43. return match
  44. }
  45. //Check if the Request request is validated
  46. func CheckAuth(r *http.Request, user, passwd string) bool {
  47. s := strings.SplitN(r.Header.Get("Authorization"), " ", 2)
  48. if len(s) != 2 {
  49. s = strings.SplitN(r.Header.Get("Proxy-Authorization"), " ", 2)
  50. if len(s) != 2 {
  51. return false
  52. }
  53. }
  54. b, err := base64.StdEncoding.DecodeString(s[1])
  55. if err != nil {
  56. return false
  57. }
  58. pair := strings.SplitN(string(b), ":", 2)
  59. if len(pair) != 2 {
  60. return false
  61. }
  62. return pair[0] == user && pair[1] == passwd
  63. }
  64. //get bool by str
  65. func GetBoolByStr(s string) bool {
  66. switch s {
  67. case "1", "true":
  68. return true
  69. }
  70. return false
  71. }
  72. //get str by bool
  73. func GetStrByBool(b bool) string {
  74. if b {
  75. return "1"
  76. }
  77. return "0"
  78. }
  79. //int
  80. func GetIntNoErrByStr(str string) int {
  81. i, _ := strconv.Atoi(strings.TrimSpace(str))
  82. return i
  83. }
  84. //Get verify value
  85. func Getverifyval(vkey string) string {
  86. return crypt.Md5(vkey)
  87. }
  88. //Change headers and host of request
  89. func ChangeHostAndHeader(r *http.Request, host string, header string, addr string,addOrigin bool) {
  90. if host != "" {
  91. r.Host = host
  92. }
  93. if header != "" {
  94. h := strings.Split(header, "\n")
  95. for _, v := range h {
  96. hd := strings.Split(v, ":")
  97. if len(hd) == 2 {
  98. r.Header.Set(hd[0], hd[1])
  99. }
  100. }
  101. }
  102. addr = strings.Split(addr, ":")[0]
  103. if prior, ok := r.Header["X-Forwarded-For"]; ok {
  104. addr = strings.Join(prior, ", ") + ", " + addr
  105. }
  106. if addOrigin {
  107. r.Header.Set("X-Forwarded-For", addr)
  108. r.Header.Set("X-Real-IP", addr)
  109. }
  110. }
  111. //Read file content by file path
  112. func ReadAllFromFile(filePath string) ([]byte, error) {
  113. f, err := os.Open(filePath)
  114. if err != nil {
  115. return nil, err
  116. }
  117. defer f.Close()
  118. return ioutil.ReadAll(f)
  119. }
  120. // FileExists reports whether the named file or directory exists.
  121. func FileExists(name string) bool {
  122. if _, err := os.Stat(name); err != nil {
  123. if os.IsNotExist(err) {
  124. return false
  125. }
  126. }
  127. return true
  128. }
  129. //Judge whether the TCP port can open normally
  130. func TestTcpPort(port int) bool {
  131. l, err := net.ListenTCP("tcp", &net.TCPAddr{net.ParseIP("0.0.0.0"), port, ""})
  132. defer func() {
  133. if l != nil {
  134. l.Close()
  135. }
  136. }()
  137. if err != nil {
  138. return false
  139. }
  140. return true
  141. }
  142. //Judge whether the UDP port can open normally
  143. func TestUdpPort(port int) bool {
  144. l, err := net.ListenUDP("udp", &net.UDPAddr{net.ParseIP("0.0.0.0"), port, ""})
  145. defer func() {
  146. if l != nil {
  147. l.Close()
  148. }
  149. }()
  150. if err != nil {
  151. return false
  152. }
  153. return true
  154. }
  155. //Write length and individual byte data
  156. //Length prevents sticking
  157. //# Characters are used to separate data
  158. func BinaryWrite(raw *bytes.Buffer, v ...string) {
  159. b := GetWriteStr(v...)
  160. binary.Write(raw, binary.LittleEndian, int32(len(b)))
  161. binary.Write(raw, binary.LittleEndian, b)
  162. }
  163. // get seq str
  164. func GetWriteStr(v ...string) []byte {
  165. buffer := new(bytes.Buffer)
  166. var l int32
  167. for _, v := range v {
  168. l += int32(len([]byte(v))) + int32(len([]byte(CONN_DATA_SEQ)))
  169. binary.Write(buffer, binary.LittleEndian, []byte(v))
  170. binary.Write(buffer, binary.LittleEndian, []byte(CONN_DATA_SEQ))
  171. }
  172. return buffer.Bytes()
  173. }
  174. //inArray str interface
  175. func InStrArr(arr []string, val string) bool {
  176. for _, v := range arr {
  177. if v == val {
  178. return true
  179. }
  180. }
  181. return false
  182. }
  183. //inArray int interface
  184. func InIntArr(arr []int, val int) bool {
  185. for _, v := range arr {
  186. if v == val {
  187. return true
  188. }
  189. }
  190. return false
  191. }
  192. //format ports str to a int array
  193. func GetPorts(p string) []int {
  194. var ps []int
  195. arr := strings.Split(p, ",")
  196. for _, v := range arr {
  197. fw := strings.Split(v, "-")
  198. if len(fw) == 2 {
  199. if IsPort(fw[0]) && IsPort(fw[1]) {
  200. start, _ := strconv.Atoi(fw[0])
  201. end, _ := strconv.Atoi(fw[1])
  202. for i := start; i <= end; i++ {
  203. ps = append(ps, i)
  204. }
  205. } else {
  206. continue
  207. }
  208. } else if IsPort(v) {
  209. p, _ := strconv.Atoi(v)
  210. ps = append(ps, p)
  211. }
  212. }
  213. return ps
  214. }
  215. //is the string a port
  216. func IsPort(p string) bool {
  217. pi, err := strconv.Atoi(p)
  218. if err != nil {
  219. return false
  220. }
  221. if pi > 65536 || pi < 1 {
  222. return false
  223. }
  224. return true
  225. }
  226. //if the s is just a port,return 127.0.0.1:s
  227. func FormatAddress(s string) string {
  228. if strings.Contains(s, ":") {
  229. return s
  230. }
  231. return "127.0.0.1:" + s
  232. }
  233. //get address from the complete address
  234. func GetIpByAddr(addr string) string {
  235. arr := strings.Split(addr, ":")
  236. return arr[0]
  237. }
  238. //get port from the complete address
  239. func GetPortByAddr(addr string) int {
  240. arr := strings.Split(addr, ":")
  241. if len(arr) < 2 {
  242. return 0
  243. }
  244. p, err := strconv.Atoi(arr[1])
  245. if err != nil {
  246. return 0
  247. }
  248. return p
  249. }
  250. func CopyBuffer(dst io.Writer, src io.Reader, label ...string) (written int64, err error) {
  251. buf := CopyBuff.Get()
  252. defer CopyBuff.Put(buf)
  253. for {
  254. nr, er := src.Read(buf)
  255. //if len(pr)>0 && pr[0] && nr > 50 {
  256. // logs.Warn(string(buf[:50]))
  257. //}
  258. if nr > 0 {
  259. nw, ew := dst.Write(buf[0:nr])
  260. if nw > 0 {
  261. written += int64(nw)
  262. }
  263. if ew != nil {
  264. err = ew
  265. break
  266. }
  267. if nr != nw {
  268. err = io.ErrShortWrite
  269. break
  270. }
  271. }
  272. if er != nil {
  273. err = er
  274. break
  275. }
  276. }
  277. return written, err
  278. }
  279. //send this ip forget to get a local udp port
  280. func GetLocalUdpAddr() (net.Conn, error) {
  281. tmpConn, err := net.Dial("udp", "114.114.114.114:53")
  282. if err != nil {
  283. return nil, err
  284. }
  285. return tmpConn, tmpConn.Close()
  286. }
  287. //parse template
  288. func ParseStr(str string) (string, error) {
  289. tmp := template.New("npc")
  290. var err error
  291. w := new(bytes.Buffer)
  292. if tmp, err = tmp.Parse(str); err != nil {
  293. return "", err
  294. }
  295. if err = tmp.Execute(w, GetEnvMap()); err != nil {
  296. return "", err
  297. }
  298. return w.String(), nil
  299. }
  300. //get env
  301. func GetEnvMap() map[string]string {
  302. m := make(map[string]string)
  303. environ := os.Environ()
  304. for i := range environ {
  305. tmp := strings.Split(environ[i], "=")
  306. if len(tmp) == 2 {
  307. m[tmp[0]] = tmp[1]
  308. }
  309. }
  310. return m
  311. }
  312. //throw the empty element of the string array
  313. func TrimArr(arr []string) []string {
  314. newArr := make([]string, 0)
  315. for _, v := range arr {
  316. if v != "" {
  317. newArr = append(newArr, v)
  318. }
  319. }
  320. return newArr
  321. }
  322. //
  323. func IsArrContains(arr []string, val string) bool {
  324. if arr == nil {
  325. return false
  326. }
  327. for _, v := range arr {
  328. if v == val {
  329. return true
  330. }
  331. }
  332. return false
  333. }
  334. //remove value from string array
  335. func RemoveArrVal(arr []string, val string) []string {
  336. for k, v := range arr {
  337. if v == val {
  338. arr = append(arr[:k], arr[k+1:]...)
  339. return arr
  340. }
  341. }
  342. return arr
  343. }
  344. //convert bytes to num
  345. func BytesToNum(b []byte) int {
  346. var str string
  347. for i := 0; i < len(b); i++ {
  348. str += strconv.Itoa(int(b[i]))
  349. }
  350. x, _ := strconv.Atoi(str)
  351. return int(x)
  352. }
  353. //get the length of the sync map
  354. func GeSynctMapLen(m sync.Map) int {
  355. var c int
  356. m.Range(func(key, value interface{}) bool {
  357. c++
  358. return true
  359. })
  360. return c
  361. }
  362. func GetExtFromPath(path string) string {
  363. s := strings.Split(path, ".")
  364. re, err := regexp.Compile(`(\w+)`)
  365. if err != nil {
  366. return ""
  367. }
  368. return string(re.Find([]byte(s[0])))
  369. }
  370. var externalIp string
  371. func GetExternalIp() string {
  372. if externalIp != "" {
  373. return externalIp
  374. }
  375. resp, err := http.Get("http://myexternalip.com/raw")
  376. if err != nil {
  377. return ""
  378. }
  379. defer resp.Body.Close()
  380. content, _ := ioutil.ReadAll(resp.Body)
  381. externalIp = string(content)
  382. return externalIp
  383. }
  384. func GetIntranetIp() (error, string) {
  385. addrs, err := net.InterfaceAddrs()
  386. if err != nil {
  387. return nil, ""
  388. }
  389. for _, address := range addrs {
  390. // 检查ip地址判断是否回环地址
  391. if ipnet, ok := address.(*net.IPNet); ok && !ipnet.IP.IsLoopback() {
  392. if ipnet.IP.To4() != nil {
  393. return nil, ipnet.IP.To4().String()
  394. }
  395. }
  396. }
  397. return errors.New("get intranet ip error"), ""
  398. }
  399. func IsPublicIP(IP net.IP) bool {
  400. if IP.IsLoopback() || IP.IsLinkLocalMulticast() || IP.IsLinkLocalUnicast() {
  401. return false
  402. }
  403. if ip4 := IP.To4(); ip4 != nil {
  404. switch true {
  405. case ip4[0] == 10:
  406. return false
  407. case ip4[0] == 172 && ip4[1] >= 16 && ip4[1] <= 31:
  408. return false
  409. case ip4[0] == 192 && ip4[1] == 168:
  410. return false
  411. default:
  412. return true
  413. }
  414. }
  415. return false
  416. }
  417. func GetServerIpByClientIp(clientIp net.IP) string {
  418. if IsPublicIP(clientIp) {
  419. return GetExternalIp()
  420. }
  421. _, ip := GetIntranetIp()
  422. return ip
  423. }