Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.

118 lines
2.8KB

  1. package main
  2. import (
  3. "encoding/json"
  4. "fmt"
  5. "io"
  6. "io/ioutil"
  7. "log"
  8. "mime"
  9. "net/http"
  10. "net/url"
  11. "os"
  12. "strconv"
  13. "time"
  14. )
  15. func saveURL(url string) (tmpFile string, contentType string, err error) {
  16. req, err := http.NewRequest("GET", url, nil)
  17. if err != nil {
  18. return
  19. }
  20. return saveHTTPRequest(req)
  21. }
  22. //{"video_url":"http://153.37.232.145/vweixinp.tc.qq.com/1007_6475d21fb443453b8adeac7e59cc0e1c.f10.mp4?vkey=E79C6B0DA06E7A434D15E24774F91412386D1956768C400AC93ECA5320ACAAAF050E1E1BA5C22DFD81B5EE3FBA97E928E0FC2DC597CF611B3E6641BC1AEE2892736FFE29E993F200AA4A0811FEB4E234C48516131207DDE4&sha=0&save=1"}
  23. type videoURL struct {
  24. VideoURL string `json:"video_url"`
  25. }
  26. //readVideoURL try to read a file into json structure
  27. //containing video_url
  28. //
  29. func readVideoURL(path string) (u string) {
  30. body, err := ioutil.ReadFile(path)
  31. if err == nil {
  32. var v = videoURL{}
  33. err = json.Unmarshal([]byte(body), &v)
  34. if err == nil {
  35. _, err = url.ParseRequestURI(v.VideoURL)
  36. if err == nil {
  37. return v.VideoURL
  38. }
  39. }
  40. }
  41. return ""
  42. }
  43. func buildHTTPReqWithHeader(httpMethod, targetURL string, headers map[string]string) (req *http.Request, err error) {
  44. req, err = http.NewRequest(httpMethod, targetURL, nil)
  45. if err != nil {
  46. return
  47. }
  48. if headers != nil {
  49. for k, v := range headers {
  50. req.Header.Set(k, v)
  51. }
  52. }
  53. return
  54. }
  55. func saveHTTPRequest(req *http.Request) (tmpFile string, contentType string, err error) {
  56. var myClient = &http.Client{Timeout: 20 * time.Second}
  57. r, err := myClient.Do(req)
  58. if err != nil {
  59. log.Printf("Fail to get URL: %s", req.RequestURI)
  60. log.Println(err)
  61. return "", "", err
  62. }
  63. defer r.Body.Close()
  64. contentType = r.Header.Get("Content-Type")
  65. contentLen := r.Header.Get("Content-Length")
  66. len, _ := strconv.Atoi(contentLen)
  67. log.Println(r)
  68. file, err := ioutil.TempFile(os.TempDir(), "wechat_hitxy_")
  69. // Use io.Copy to just dump the response body to the file. This supports huge files
  70. _, err = io.Copy(file, r.Body)
  71. if err != nil {
  72. log.Println(err)
  73. return "", contentType, err
  74. }
  75. noSuffix := file.Name()
  76. file.Close()
  77. tmpFile = noSuffix + contentType2Suffix(contentType)
  78. os.Rename(noSuffix, tmpFile)
  79. //see if its a video url
  80. if len < 4096 && contentType == "text/plain" {
  81. u := readVideoURL(tmpFile)
  82. if u != "" {
  83. fmt.Println("saveing video url: " + u)
  84. os.Remove(tmpFile) //remove json file
  85. tmpFile, contentType, err = saveURL(u)
  86. }
  87. }
  88. return
  89. }
  90. func saveURLwithHTTPHeader(url string, headers map[string]string) (tmpFile string, contentType string, err error) {
  91. log.Println("saveURL: " + url)
  92. req, err := buildHTTPReqWithHeader("GET", url, headers)
  93. if err != nil {
  94. return
  95. }
  96. return saveHTTPRequest(req)
  97. }
  98. func contentType2Suffix(typ string) string {
  99. exts, err := mime.ExtensionsByType(typ)
  100. if err != nil {
  101. return ""
  102. }
  103. return exts[0]
  104. }