Skip to content

Commit 9e4be1f

Browse files
committed
Conflicts: cookie.go web.go web_test.go
2 parents 56fb5f6 + 3b40eac commit 9e4be1f

File tree

5 files changed

+68
-64
lines changed

5 files changed

+68
-64
lines changed

cookie.go

Lines changed: 52 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -86,20 +86,19 @@ func writeSetCookies(w io.Writer, kk []*http.Cookie) os.Error {
8686
var b bytes.Buffer
8787
for _, c := range kk {
8888
b.Reset()
89-
fmt.Fprintf(&b, "%s=%s", sanitizeName(c.Name), sanitizeValue(c.Value))
89+
// TODO(petar): c.Value (below) should be unquoted if it is recognized as quoted
90+
fmt.Fprintf(&b, "%s=%s", http.CanonicalHeaderKey(c.Name), c.Value)
9091
if len(c.Path) > 0 {
91-
fmt.Fprintf(&b, "; Path=%s", sanitizeValue(c.Path))
92+
fmt.Fprintf(&b, "; Path=%s", http.URLEscape(c.Path))
9293
}
9394
if len(c.Domain) > 0 {
94-
fmt.Fprintf(&b, "; Domain=%s", sanitizeValue(c.Domain))
95+
fmt.Fprintf(&b, "; Domain=%s", http.URLEscape(c.Domain))
9596
}
9697
if len(c.Expires.Zone) > 0 {
9798
fmt.Fprintf(&b, "; Expires=%s", c.Expires.Format(time.RFC1123))
9899
}
99-
if c.MaxAge > 0 {
100+
if c.MaxAge >= 0 {
100101
fmt.Fprintf(&b, "; Max-Age=%d", c.MaxAge)
101-
} else if c.MaxAge < 0 {
102-
fmt.Fprintf(&b, "; Max-Age=0")
103102
}
104103
if c.HttpOnly {
105104
fmt.Fprintf(&b, "; HttpOnly")
@@ -124,8 +123,22 @@ func writeSetCookies(w io.Writer, kk []*http.Cookie) os.Error {
124123
// line-length, so it seems safer to place cookies on separate lines.
125124
func writeCookies(w io.Writer, kk []*http.Cookie) os.Error {
126125
lines := make([]string, 0, len(kk))
126+
var b bytes.Buffer
127127
for _, c := range kk {
128-
lines = append(lines, fmt.Sprintf("Cookie: %s=%s\r\n", sanitizeName(c.Name), sanitizeValue(c.Value)))
128+
b.Reset()
129+
n := c.Name
130+
// TODO(petar): c.Value (below) should be unquoted if it is recognized as quoted
131+
fmt.Fprintf(&b, "%s=%s", http.CanonicalHeaderKey(n), c.Value)
132+
if len(c.Path) > 0 {
133+
fmt.Fprintf(&b, "; $Path=%s", http.URLEscape(c.Path))
134+
}
135+
if len(c.Domain) > 0 {
136+
fmt.Fprintf(&b, "; $Domain=%s", http.URLEscape(c.Domain))
137+
}
138+
if c.HttpOnly {
139+
fmt.Fprintf(&b, "; $HttpOnly")
140+
}
141+
lines = append(lines, "Cookie: "+b.String()+"\r\n")
129142
}
130143
sort.SortStrings(lines)
131144
for _, l := range lines {
@@ -152,29 +165,51 @@ func readCookies(h http.Header) []*http.Cookie {
152165
continue
153166
}
154167
// Per-line attributes
155-
parsedPairs := 0
168+
var lineCookies = make(map[string]string)
169+
var path string
170+
var domain string
171+
var httponly bool
156172
for i := 0; i < len(parts); i++ {
157173
parts[i] = strings.TrimSpace(parts[i])
158174
if len(parts[i]) == 0 {
159175
continue
160176
}
161177
attr, val := parts[i], ""
178+
var err os.Error
162179
if j := strings.Index(attr, "="); j >= 0 {
163180
attr, val = attr[:j], attr[j+1:]
181+
val, err = http.URLUnescape(val)
182+
if err != nil {
183+
continue
184+
}
164185
}
165-
if !isCookieNameValid(attr) {
166-
continue
167-
}
168-
val, success := parseCookieValue(val)
169-
if !success {
170-
continue
186+
switch strings.ToLower(attr) {
187+
case "$httponly":
188+
httponly = true
189+
case "$domain":
190+
domain = val
191+
// TODO: Add domain parsing
192+
case "$path":
193+
path = val
194+
// TODO: Add path parsing
195+
default:
196+
lineCookies[attr] = val
171197
}
172-
cookies = append(cookies, &http.Cookie{Name: attr, Value: val})
173-
parsedPairs++
174198
}
175-
if parsedPairs == 0 {
199+
if len(lineCookies) == 0 {
176200
unparsedLines = append(unparsedLines, line)
177201
}
202+
for n, v := range lineCookies {
203+
cookies = append(cookies, &http.Cookie{
204+
Name: n,
205+
Value: v,
206+
Path: path,
207+
Domain: domain,
208+
HttpOnly: httponly,
209+
MaxAge: -1,
210+
Raw: line,
211+
})
212+
}
178213
}
179214
h["Cookie"] = unparsedLines, len(unparsedLines) > 0
180215
return cookies

examples/logger.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ import (
99
func hello(val string) string { return "hello " + val }
1010

1111
func main() {
12-
f, err := os.Open("server.log", os.O_RDWR|os.O_CREATE, 0644)
12+
f, err := os.Create("server.log")
1313
if err != nil {
1414
println(err.String())
1515
return

request.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ func (r *Request) parseParams() (err os.Error) {
181181
switch r.Method {
182182
case "POST":
183183
if r.Body == nil {
184-
return os.ErrorString("missing form body")
184+
return os.NewError("missing form body")
185185
}
186186

187187
ct := r.Headers.Get("Content-Type")

web.go

Lines changed: 2 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ func (s *Server) addRoute(r string, method string, handler interface{}) {
198198
s.Logger.Printf("Error in route regex %q\n", r)
199199
return
200200
}
201-
//is this already a reflect.FuncValue?
201+
202202
if fv, ok := handler.(reflect.Value); ok {
203203
s.routes.Push(route{r, cr, method, fv})
204204
} else {
@@ -216,11 +216,7 @@ func (c *httpConn) StartResponse(status int) { c.conn.WriteHeader(status) }
216216
func (c *httpConn) SetHeader(hdr string, val string, unique bool) {
217217
//right now unique can't be implemented through the http package.
218218
//see issue 488
219-
if unique {
220-
c.conn.Header().Set(hdr, val)
221-
} else {
222-
c.conn.Header().Add(hdr, val)
223-
}
219+
c.conn.Header().Set(hdr, val)
224220
}
225221

226222
func (c *httpConn) WriteString(content string) {
@@ -275,7 +271,6 @@ func (s *Server) safelyCall(function reflect.Value, args []reflect.Value) (resp
275271

276272
//should the context be passed to the handler?
277273
func requiresContext(handlerType reflect.Type) bool {
278-
//fmt.Printf("type %v\n", handlerType)
279274
//if the method doesn't take arguments, no
280275
if handlerType.NumIn() == 0 {
281276
return false
@@ -291,18 +286,6 @@ func requiresContext(handlerType reflect.Type) bool {
291286
return true
292287
}
293288

294-
//another case -- the first argument is a method receiver, and the
295-
//second argument is a web.Context
296-
if handlerType.NumIn() > 1 {
297-
a1 := handlerType.In(1)
298-
if a1.Kind() != reflect.Ptr {
299-
return false
300-
}
301-
if a1.Elem() == contextType {
302-
return true
303-
}
304-
}
305-
306289
return false
307290
}
308291

@@ -599,19 +582,3 @@ func Urlencode(data map[string]string) string {
599582
s := buf.String()
600583
return s[0 : len(s)-1]
601584
}
602-
603-
//Extracts the method "name" from the value represented by "val"
604-
//This allows methods to be handlers
605-
func MethodHandler(val interface{}, name string) reflect.Value {
606-
v := reflect.ValueOf(val)
607-
typ := v.Type()
608-
n := typ.NumMethod()
609-
for i := 0; i < n; i++ {
610-
m := typ.Method(i)
611-
if m.Name == name {
612-
return v.Method(i)
613-
}
614-
}
615-
616-
return reflect.ValueOf(nil)
617-
}

web_test.go

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -107,15 +107,16 @@ type StructHandler struct {
107107
a string
108108
}
109109

110-
func (s *StructHandler) Method() string {
110+
111+
func (s *StructHandler) method() string {
111112
return s.a
112113
}
113114

114-
func (s *StructHandler) Method2(ctx *Context) string {
115+
func (s *StructHandler) method2(ctx *Context) string {
115116
return s.a + ctx.Params["b"]
116117
}
117118

118-
func (s *StructHandler) Method3(ctx *Context, b string) string {
119+
func (s *StructHandler) method3(ctx *Context, b string) string {
119120
return s.a + b
120121
}
121122

@@ -170,10 +171,10 @@ func init() {
170171
return string(data)
171172
})
172173

173-
s := &StructHandler{"a"}
174-
Get("/methodhandler", MethodHandler(s, "Method"))
175-
Get("/methodhandler2", MethodHandler(s, "Method2"))
176-
Get("/methodhandler3/(.*)", MethodHandler(s, "Method3"))
174+
//s := &StructHandler{"a"}
175+
//Get("/methodhandler", MethodHandler(s, "method"))
176+
//Get("/methodhandler2", MethodHandler(s, "method2"))
177+
//Get("/methodhandler3/(.*)", MethodHandler(s, "method3"))
177178
}
178179

179180
var tests = []Test{
@@ -200,9 +201,9 @@ var tests = []Test{
200201
{"GET", "/fullparams?a=1&a=2&a=3", "", 200, "1,2,3"},
201202
{"GET", "/panic", "", 500, "Server Error"},
202203
{"GET", "/json?a=1&b=2", "", 200, `{"a":"1","b":"2"}`},
203-
{"GET", "/methodhandler", "", 200, `a`},
204-
{"GET", "/methodhandler2?b=b", "", 200, `ab`},
205-
{"GET", "/methodhandler3/b", "", 200, `ab`},
204+
//{"GET", "/methodhandler", "", 200, `a`},
205+
//{"GET", "/methodhandler2?b=b", "", 200, `ab`},
206+
//{"GET", "/methodhandler3/b", "", 200, `ab`},
206207
}
207208

208209
func buildTestRequest(method string, path string, body string, headers map[string][]string, cookies []*http.Cookie) *Request {
@@ -605,6 +606,7 @@ func TestFcgiChunks(t *testing.T) {
605606
}
606607

607608
func makeCookie(vals map[string]string) []*http.Cookie {
609+
608610
var cookies []*http.Cookie
609611
for k, v := range vals {
610612
c := &http.Cookie{

0 commit comments

Comments
 (0)