util_curl.go raw
1 package resty
2
3 import (
4 "bytes"
5 "io"
6 "net/http"
7 "net/http/cookiejar"
8
9 "net/url"
10 "strings"
11
12 "github.com/go-resty/resty/v2/shellescape"
13 )
14
15 func buildCurlRequest(req *http.Request, httpCookiejar http.CookieJar) (curl string) {
16 // 1. Generate curl raw headers
17
18 curl = "curl -X " + req.Method + " "
19 // req.Host + req.URL.Path + "?" + req.URL.RawQuery + " " + req.Proto + " "
20 headers := dumpCurlHeaders(req)
21 for _, kv := range *headers {
22 curl += `-H ` + shellescape.Quote(kv[0]+": "+kv[1]) + ` `
23 }
24
25 // 2. Generate curl cookies
26 // TODO validate this block of code, I think its not required since cookie captured via Headers
27 if cookieJar, ok := httpCookiejar.(*cookiejar.Jar); ok {
28 cookies := cookieJar.Cookies(req.URL)
29 if len(cookies) > 0 {
30 curl += `-H ` + shellescape.Quote(dumpCurlCookies(cookies)) + " "
31 }
32 }
33
34 // 3. Generate curl body
35 if req.Body != nil {
36 buf, _ := io.ReadAll(req.Body)
37 req.Body = io.NopCloser(bytes.NewBuffer(buf)) // important!!
38 curl += `-d ` + shellescape.Quote(string(buf)) + " "
39 }
40
41 urlString := shellescape.Quote(req.URL.String())
42 if urlString == "''" {
43 urlString = "'http://unexecuted-request'"
44 }
45 curl += urlString
46 return curl
47 }
48
49 // dumpCurlCookies dumps cookies to curl format
50 func dumpCurlCookies(cookies []*http.Cookie) string {
51 sb := strings.Builder{}
52 sb.WriteString("Cookie: ")
53 for _, cookie := range cookies {
54 sb.WriteString(cookie.Name + "=" + url.QueryEscape(cookie.Value) + "&")
55 }
56 return strings.TrimRight(sb.String(), "&")
57 }
58
59 // dumpCurlHeaders dumps headers to curl format
60 func dumpCurlHeaders(req *http.Request) *[][2]string {
61 headers := [][2]string{}
62 for k, vs := range req.Header {
63 for _, v := range vs {
64 headers = append(headers, [2]string{k, v})
65 }
66 }
67 n := len(headers)
68 for i := 0; i < n; i++ {
69 for j := n - 1; j > i; j-- {
70 jj := j - 1
71 h1, h2 := headers[j], headers[jj]
72 if h1[0] < h2[0] {
73 headers[jj], headers[j] = headers[j], headers[jj]
74 }
75 }
76 }
77 return &headers
78 }
79