-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathcookiejarparser.go
110 lines (92 loc) · 2.27 KB
/
cookiejarparser.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
package cookiejarparser
import (
"bufio"
"fmt"
"net/http"
"net/http/cookiejar"
"net/url"
"os"
"strconv"
"strings"
"time"
"golang.org/x/net/publicsuffix"
)
const httpOnlyPrefix = "#HttpOnly_"
func parseCookieLine(cookieLine string, lineNum int) (*http.Cookie, error) {
var err error
cookieLineHttpOnly := false
if strings.HasPrefix(cookieLine, httpOnlyPrefix) {
cookieLineHttpOnly = true
cookieLine = strings.TrimPrefix(cookieLine, httpOnlyPrefix)
}
if strings.HasPrefix(cookieLine, "#") || cookieLine == "" {
return nil, nil
}
cookieFields := strings.Split(cookieLine, "\t")
if len(cookieFields) < 6 || len(cookieFields) > 7 {
return nil, fmt.Errorf("incorrect number of fields in line %d. Expected 6 or 7, got %d.", lineNum, len(cookieFields))
}
for i, v := range cookieFields {
cookieFields[i] = strings.TrimSpace(v)
}
cookie := &http.Cookie{
Domain: cookieFields[0],
Path: cookieFields[2],
Name: cookieFields[5],
HttpOnly: cookieLineHttpOnly,
}
cookie.Secure, err = strconv.ParseBool(cookieFields[3])
if err != nil {
return nil, err
}
expiresInt, err := strconv.ParseInt(cookieFields[4], 10, 64)
if err != nil {
return nil, err
}
if expiresInt > 0 {
cookie.Expires = time.Unix(expiresInt, 0)
}
if len(cookieFields) == 7 {
cookie.Value = cookieFields[6]
}
return cookie, nil
}
// LoadCookieJarFile takes a path to a curl (netscape) cookie jar file and crates a go http.CookieJar with the contents
func LoadCookieJarFile(path string) (http.CookieJar, error) {
jar, err := cookiejar.New(&cookiejar.Options{PublicSuffixList: publicsuffix.List})
if err != nil {
return nil, err
}
file, err := os.Open(path)
if err != nil {
return nil, err
}
defer file.Close()
lineNum := 1
scanner := bufio.NewScanner(file)
for scanner.Scan() {
cookieLine := scanner.Text()
cookie, err := parseCookieLine(cookieLine, lineNum)
if cookie == nil {
continue
}
if err != nil {
return nil, err
}
var cookieScheme string
if cookie.Secure {
cookieScheme = "https"
} else {
cookieScheme = "http"
}
cookieUrl := &url.URL{
Scheme: cookieScheme,
Host: cookie.Domain,
}
cookies := jar.Cookies(cookieUrl)
cookies = append(cookies, cookie)
jar.SetCookies(cookieUrl, cookies)
lineNum++
}
return jar, nil
}