url_connectedness_helper.go 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182
  1. package url_connectedness_helper
  2. import (
  3. "crypto/tls"
  4. "errors"
  5. "net/http"
  6. "net/url"
  7. "regexp"
  8. "time"
  9. )
  10. // UrlConnectednessTest 测试输入 url 的连通性
  11. func UrlConnectednessTest(testUrl, proxyAddr string) (bool, int64, error) {
  12. var httpClient http.Client
  13. if proxyAddr == "" {
  14. // 无需代理
  15. // 创建连接客户端
  16. httpClient = http.Client{
  17. Timeout: time.Second * testUrlTimeOut,
  18. }
  19. } else {
  20. // 需要代理
  21. // 检测代理iP访问地址
  22. if proxyAddressValidHttpFormat(proxyAddr) == false {
  23. return false, 0, errors.New("proxy address illegal, only support http://xx:xx")
  24. }
  25. // 解析代理地址
  26. proxy, err := url.Parse(proxyAddr)
  27. if err != nil {
  28. return false, 0, err
  29. }
  30. // 设置网络传输
  31. netTransport := &http.Transport{
  32. Proxy: http.ProxyURL(proxy),
  33. MaxIdleConnsPerHost: 1000,
  34. ResponseHeaderTimeout: time.Second * time.Duration(testUrlTimeOut),
  35. TLSClientConfig: &tls.Config{
  36. InsecureSkipVerify: true,
  37. },
  38. }
  39. // 创建连接客户端
  40. httpClient = http.Client{
  41. Timeout: time.Second * testUrlTimeOut,
  42. Transport: netTransport,
  43. }
  44. }
  45. begin := time.Now() //判断代理访问时间
  46. // 使用代理IP访问测试地址
  47. res, err := httpClient.Get(testUrl)
  48. if err != nil {
  49. return false, 0, err
  50. }
  51. defer func() {
  52. _ = res.Body.Close()
  53. }()
  54. speed := time.Now().Sub(begin).Nanoseconds() / 1000 / 1000 //ms
  55. // 判断是否成功访问,如果成功访问StatusCode应该为200
  56. if res.StatusCode != http.StatusOK {
  57. return false, 0, nil
  58. }
  59. return true, speed, nil
  60. }
  61. // proxyAddressValidHttpFormat 代理地址是否是有效的格式,必须是 http 的代理
  62. func proxyAddressValidHttpFormat(proxyAddr string) bool {
  63. // 首先检测 proxyAddr 是否合法,必须是 http 的代理,不支持 https 代理
  64. re := regexp.MustCompile(`(http):\/\/[\w\-_]+(\.[\w\-_]+)+([\w\-\.,@?^=%&:/~\+#]*[\w\-\@?^=%&/~\+#])?`)
  65. result := re.FindAllStringSubmatch(proxyAddr, -1)
  66. if result == nil || len(result) < 1 {
  67. return false
  68. }
  69. return true
  70. }
  71. const testUrlTimeOut = 5
  72. const (
  73. GoogleUrl = "https://google.com"
  74. BaiduUrl = "https://baidu.com"
  75. )