-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathresponses.go
118 lines (98 loc) · 3.21 KB
/
responses.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
111
112
113
114
115
116
117
118
package trama
import (
"fmt"
"net/http"
"path"
)
// Response is the interface to write HTTP responses.
type Response interface {
// SetTemplateGroup specifies which group of templates, among those from
// the registered group set (see Handler’s method Template) will be used
// when ExecuteTemplate is called. Useful for set system language for
// example.
SetTemplateGroup(name string)
// SetHeader sets the HTTP header that will be sent with the response. All
// current values of the HTTP header key are going to be replaced.
SetHeader(key string, value ...string)
// SetCookie sets the cookies that will be sent with the response.
SetCookie(cookie *http.Cookie)
// Redirect redirects the request to the specified URL.
Redirect(url string, statusCode int)
// ExecuteTemplate looks for the named template among those registered in
// the template group specified with SetTemplateGroup, and prepares it to
// be parsed using the input data and to be written to the response. The
// actual writing will only happen after all the interceptors be executed.
ExecuteTemplate(name string, data interface{})
// TemplateName returns the name of the template set by a previous call to
// ExecuteTemplate. It is meant to be used by an interceptor that would
// wanto to instrospect in its After method the response set by the
// handler.
TemplateName() string
}
type response struct {
redirectURL string
redirectStatusCode int
templateName string
templateData interface{}
currentTemplateGroup string
templates TemplateGroupSet
written bool
responseWriter http.ResponseWriter
request *http.Request
log func(error)
returnStatus int
}
func (r *response) TemplateName() string {
return r.templateName
}
func (r *response) SetTemplateGroup(name string) {
r.currentTemplateGroup = name
}
func (r *response) Redirect(url string, statusCode int) {
r.written = true
r.redirectURL = url
r.redirectStatusCode = statusCode
}
func (r *response) ExecuteTemplate(name string, data interface{}) {
r.written = true
_, filename := path.Split(name)
r.templateName = filename
r.templateData = data
}
func (r *response) SetHeader(key string, value ...string) {
if len(value) == 1 {
r.responseWriter.Header().Set(key, value[0])
return
}
r.responseWriter.Header().Del(key)
for _, v := range value {
r.responseWriter.Header().Add(key, v)
}
}
func (r *response) SetCookie(cookie *http.Cookie) {
http.SetCookie(r.responseWriter, cookie)
}
func (r *response) write() {
if !r.written {
if r.returnStatus != 0 {
r.responseWriter.WriteHeader(r.returnStatus)
} else {
r.responseWriter.WriteHeader(http.StatusInternalServerError)
}
return
}
if r.redirectStatusCode != 0 {
http.Redirect(r.responseWriter, r.request, r.redirectURL, r.redirectStatusCode)
} else {
group, found := r.templates.elements[r.currentTemplateGroup]
if !found {
r.log(fmt.Errorf("No template group named “%s” was found", r.currentTemplateGroup))
r.responseWriter.WriteHeader(http.StatusInternalServerError)
return
}
err := group.executeTemplate(r.responseWriter, r.templateName, r.templateData)
if err != nil {
r.log(err)
}
}
}