-
Notifications
You must be signed in to change notification settings - Fork 1
/
extractors.go
102 lines (81 loc) · 2.4 KB
/
extractors.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
package valueextractor
import (
"errors"
"net/http"
"net/url"
"strings"
)
// ErrNotFound is an error that is returned when a key is not found
var ErrNotFound = errors.New("key not found")
// extractors
type ValueExtractor interface {
Get(key string) (val string, err error)
}
// MapExtractor is a value extractor that extracts values from a map
type MapExtractor map[string]string
// Get returns the value of a key from the map
func (m MapExtractor) Get(key string) (string, error) {
value, ok := m[key]
if !ok {
return "", ErrNotFound
}
return value, nil
}
// QueryExtractor is a value extractor that extracts values from a http request's query parameters
type QueryExtractor struct {
Query url.Values
}
// Get returns the value of a query parameter from the request
func (qe QueryExtractor) Get(key string) (string, error) {
value := qe.Query.Get(key)
if value == "" {
return "", ErrNotFound
}
return value, nil
}
// ErrRequestNil is an error that is returned when the request is nil
var ErrRequestNil = errors.New("request is nil")
var ErrRequestParseForm = errors.New("error parsing form")
// FormExtractor is a value extractor that extracts values from a http request's form
type FormExtractor struct {
Request *http.Request
parsed bool
getter func(string) string
}
func (fe *FormExtractor) isMultipart() bool {
ctype := fe.Request.Header.Get("Content-Type")
return strings.HasPrefix(ctype, "multipart/form-data")
}
// ensureParsed ensures that the form has been parsed
// for multipart forms, it parses the form using ParseMultipartForm and sets the getter to FormValue
// for urlencoded forms, it parses the form using ParseForm and sets the getter to Get
func (fe *FormExtractor) ensureParsed() error {
if fe.parsed {
return nil
}
fe.getter = fe.Request.FormValue
if fe.isMultipart() {
if err := fe.Request.ParseMultipartForm(0); err != nil {
return errors.Join(ErrRequestParseForm, err)
}
fe.getter = fe.Request.FormValue
} else if err := fe.Request.ParseForm(); err != nil {
return errors.Join(ErrRequestParseForm, err)
}
fe.parsed = true
return nil
}
// Get returns the value of a form parameter from the Request
func (fe *FormExtractor) Get(key string) (string, error) {
if fe.Request == nil {
return "", ErrRequestNil
}
if err := fe.ensureParsed(); err != nil {
return "", err
}
value := fe.getter(key)
if value == "" {
return "", ErrNotFound
}
return value, nil
}