url_test.go (4026B)
1 // Copyright 2011 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
4
5 //go:build go1.13 && !windows
6 // +build go1.13,!windows
7
8 package template
9
10 import (
11 "testing"
12 )
13
14 func TestURLNormalizer(t *testing.T) {
15 tests := []struct {
16 url, want string
17 }{
18 {"", ""},
19 {
20 "http://example.com:80/foo/bar?q=foo%20&bar=x+y#frag",
21 "http://example.com:80/foo/bar?q=foo%20&bar=x+y#frag",
22 },
23 {" ", "%20"},
24 {"%7c", "%7c"},
25 {"%7C", "%7C"},
26 {"%2", "%252"},
27 {"%", "%25"},
28 {"%z", "%25z"},
29 {"/foo|bar/%5c\u1234", "/foo%7cbar/%5c%e1%88%b4"},
30 }
31 for _, test := range tests {
32 if got := urlNormalizer(test.url); test.want != got {
33 t.Errorf("%q: want\n\t%q\nbut got\n\t%q", test.url, test.want, got)
34 }
35 if test.want != urlNormalizer(test.want) {
36 t.Errorf("not idempotent: %q", test.want)
37 }
38 }
39 }
40
41 func TestURLFilters(t *testing.T) {
42 input := ("\x00\x01\x02\x03\x04\x05\x06\x07\x08\t\n\x0b\x0c\r\x0e\x0f" +
43 "\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f" +
44 ` !"#$%&'()*+,-./` +
45 `0123456789:;<=>?` +
46 `@ABCDEFGHIJKLMNO` +
47 `PQRSTUVWXYZ[\]^_` +
48 "`abcdefghijklmno" +
49 "pqrstuvwxyz{|}~\x7f" +
50 "\u00A0\u0100\u2028\u2029\ufeff\U0001D11E")
51
52 tests := []struct {
53 name string
54 escaper func(...any) string
55 escaped string
56 }{
57 {
58 "urlEscaper",
59 urlEscaper,
60 "%00%01%02%03%04%05%06%07%08%09%0a%0b%0c%0d%0e%0f" +
61 "%10%11%12%13%14%15%16%17%18%19%1a%1b%1c%1d%1e%1f" +
62 "%20%21%22%23%24%25%26%27%28%29%2a%2b%2c-.%2f" +
63 "0123456789%3a%3b%3c%3d%3e%3f" +
64 "%40ABCDEFGHIJKLMNO" +
65 "PQRSTUVWXYZ%5b%5c%5d%5e_" +
66 "%60abcdefghijklmno" +
67 "pqrstuvwxyz%7b%7c%7d~%7f" +
68 "%c2%a0%c4%80%e2%80%a8%e2%80%a9%ef%bb%bf%f0%9d%84%9e",
69 },
70 {
71 "urlNormalizer",
72 urlNormalizer,
73 "%00%01%02%03%04%05%06%07%08%09%0a%0b%0c%0d%0e%0f" +
74 "%10%11%12%13%14%15%16%17%18%19%1a%1b%1c%1d%1e%1f" +
75 "%20!%22#$%25&%27%28%29*+,-./" +
76 "0123456789:;%3c=%3e?" +
77 "@ABCDEFGHIJKLMNO" +
78 "PQRSTUVWXYZ[%5c]%5e_" +
79 "%60abcdefghijklmno" +
80 "pqrstuvwxyz%7b%7c%7d~%7f" +
81 "%c2%a0%c4%80%e2%80%a8%e2%80%a9%ef%bb%bf%f0%9d%84%9e",
82 },
83 }
84
85 for _, test := range tests {
86 if s := test.escaper(input); s != test.escaped {
87 t.Errorf("%s: want\n\t%q\ngot\n\t%q", test.name, test.escaped, s)
88 continue
89 }
90 }
91 }
92
93 func TestSrcsetFilter(t *testing.T) {
94 tests := []struct {
95 name string
96 input string
97 want string
98 }{
99 {
100 "one ok",
101 "http://example.com/img.png",
102 "http://example.com/img.png",
103 },
104 {
105 "one ok with metadata",
106 " /img.png 200w",
107 " /img.png 200w",
108 },
109 {
110 "one bad",
111 "javascript:alert(1) 200w",
112 "#ZgotmplZ",
113 },
114 {
115 "two ok",
116 "foo.png, bar.png",
117 "foo.png, bar.png",
118 },
119 {
120 "left bad",
121 "javascript:alert(1), /foo.png",
122 "#ZgotmplZ, /foo.png",
123 },
124 {
125 "right bad",
126 "/bogus#, javascript:alert(1)",
127 "/bogus#,#ZgotmplZ",
128 },
129 }
130
131 for _, test := range tests {
132 if got := srcsetFilterAndEscaper(test.input); got != test.want {
133 t.Errorf("%s: srcsetFilterAndEscaper(%q) want %q != %q", test.name, test.input, test.want, got)
134 }
135 }
136 }
137
138 func BenchmarkURLEscaper(b *testing.B) {
139 for i := 0; i < b.N; i++ {
140 urlEscaper("http://example.com:80/foo?q=bar%20&baz=x+y#frag")
141 }
142 }
143
144 func BenchmarkURLEscaperNoSpecials(b *testing.B) {
145 for i := 0; i < b.N; i++ {
146 urlEscaper("TheQuickBrownFoxJumpsOverTheLazyDog.")
147 }
148 }
149
150 func BenchmarkURLNormalizer(b *testing.B) {
151 for i := 0; i < b.N; i++ {
152 urlNormalizer("The quick brown fox jumps over the lazy dog.\n")
153 }
154 }
155
156 func BenchmarkURLNormalizerNoSpecials(b *testing.B) {
157 for i := 0; i < b.N; i++ {
158 urlNormalizer("http://example.com:80/foo?q=bar%20&baz=x+y#frag")
159 }
160 }
161
162 func BenchmarkSrcsetFilter(b *testing.B) {
163 for i := 0; i < b.N; i++ {
164 srcsetFilterAndEscaper(" /foo/bar.png 200w, /baz/boo(1).png")
165 }
166 }
167
168 func BenchmarkSrcsetFilterNoSpecials(b *testing.B) {
169 for i := 0; i < b.N; i++ {
170 srcsetFilterAndEscaper("http://example.com:80/foo?q=bar%20&baz=x+y#frag")
171 }
172 }