1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.commons.codec.net;
19
20 import static org.junit.jupiter.api.Assertions.assertEquals;
21 import static org.junit.jupiter.api.Assertions.assertNull;
22 import static org.junit.jupiter.api.Assertions.assertThrows;
23
24 import java.nio.charset.StandardCharsets;
25
26 import org.apache.commons.codec.CharEncoding;
27 import org.apache.commons.codec.DecoderException;
28 import org.apache.commons.codec.EncoderException;
29 import org.junit.jupiter.api.Test;
30
31
32
33
34 public class URLCodecTest {
35
36 static final int SWISS_GERMAN_STUFF_UNICODE[] = { 0x47, 0x72, 0xFC, 0x65, 0x7A, 0x69, 0x5F, 0x7A, 0xE4, 0x6D, 0xE4 };
37
38 static final int RUSSIAN_STUFF_UNICODE[] = { 0x412, 0x441, 0x435, 0x43C, 0x5F, 0x43F, 0x440, 0x438, 0x432, 0x435, 0x442 };
39
40 private String constructString(final int[] unicodeChars) {
41 final StringBuilder buffer = new StringBuilder();
42 if (unicodeChars != null) {
43 for (final int unicodeChar : unicodeChars) {
44 buffer.append((char) unicodeChar);
45 }
46 }
47 return buffer.toString();
48 }
49
50 @Test
51 public void testBasicEncodeDecode() throws Exception {
52 final URLCodec urlCodec = new URLCodec();
53 final String plain = "Hello there!";
54 final String encoded = urlCodec.encode(plain);
55 assertEquals("Hello+there%21", encoded, "Basic URL encoding test");
56 assertEquals(plain, urlCodec.decode(encoded), "Basic URL decoding test");
57 this.validateState(urlCodec);
58 }
59
60 @Test
61 public void testDecodeInvalid() throws Exception {
62 final URLCodec urlCodec = new URLCodec();
63 assertThrows(DecoderException.class, () -> urlCodec.decode("%"));
64 assertThrows(DecoderException.class, () -> urlCodec.decode("%A"));
65
66 assertThrows(DecoderException.class, () -> urlCodec.decode("%WW"));
67
68 assertThrows(DecoderException.class, () -> urlCodec.decode("%0W"));
69 this.validateState(urlCodec);
70 }
71
72 @Test
73 public void testDecodeInvalidContent() throws DecoderException {
74 final String ch_msg = constructString(SWISS_GERMAN_STUFF_UNICODE);
75 final URLCodec urlCodec = new URLCodec();
76 final byte[] input = ch_msg.getBytes(StandardCharsets.ISO_8859_1);
77 final byte[] output = urlCodec.decode(input);
78 assertEquals(input.length, output.length);
79 for (int i = 0; i < input.length; i++) {
80 assertEquals(input[i], output[i]);
81 }
82 this.validateState(urlCodec);
83 }
84
85 @Test
86 public void testDecodeObjects() throws Exception {
87 final URLCodec urlCodec = new URLCodec();
88 final String plain = "Hello+there%21";
89 String decoded = (String) urlCodec.decode((Object) plain);
90 assertEquals("Hello there!", decoded, "Basic URL decoding test");
91 final byte[] plainBA = plain.getBytes(StandardCharsets.UTF_8);
92 final byte[] decodedBA = (byte[]) urlCodec.decode((Object) plainBA);
93 decoded = new String(decodedBA);
94 assertEquals("Hello there!", decoded, "Basic URL decoding test");
95 final Object result = urlCodec.decode((Object) null);
96
97 assertNull(result, "Decoding a null Object should return null");
98
99 assertThrows(DecoderException.class, () -> urlCodec.decode(Double.valueOf(3.0d)), "Trying to url encode a Double object should cause an exception.");
100 this.validateState(urlCodec);
101 }
102
103 @Test
104 public void testDecodeStringWithNull() throws Exception {
105 final URLCodec urlCodec = new URLCodec();
106 final String test = null;
107 final String result = urlCodec.decode(test, "charset");
108 assertNull(result, "Result should be null");
109 }
110
111 @Test
112 public void testDecodeWithNullArray() throws Exception {
113 final byte[] plain = null;
114 final byte[] result = URLCodec.decodeUrl(plain);
115 assertNull(result, "Result should be null");
116 }
117
118 @Test
119 public void testDefaultEncoding() throws Exception {
120 final String plain = "Hello there!";
121 final URLCodec urlCodec = new URLCodec("UnicodeBig");
122 urlCodec.encode(plain);
123 final String encoded1 = urlCodec.encode(plain, "UnicodeBig");
124 final String encoded2 = urlCodec.encode(plain);
125 assertEquals(encoded1, encoded2);
126 this.validateState(urlCodec);
127 }
128
129 @Test
130 public void testEncodeDecodeNull() throws Exception {
131 final URLCodec urlCodec = new URLCodec();
132 assertNull(urlCodec.encode((String) null), "Null string URL encoding test");
133 assertNull(urlCodec.decode((String) null), "Null string URL decoding test");
134 this.validateState(urlCodec);
135 }
136
137 @Test
138 public void testEncodeNull() throws Exception {
139 final URLCodec urlCodec = new URLCodec();
140 final byte[] plain = null;
141 final byte[] encoded = urlCodec.encode(plain);
142 assertNull(encoded, "Encoding a null string should return null");
143 this.validateState(urlCodec);
144 }
145
146 @Test
147 public void testEncodeObjects() throws Exception {
148 final URLCodec urlCodec = new URLCodec();
149 final String plain = "Hello there!";
150 String encoded = (String) urlCodec.encode((Object) plain);
151 assertEquals("Hello+there%21", encoded, "Basic URL encoding test");
152
153 final byte[] plainBA = plain.getBytes(StandardCharsets.UTF_8);
154 final byte[] encodedBA = (byte[]) urlCodec.encode((Object) plainBA);
155 encoded = new String(encodedBA);
156 assertEquals("Hello+there%21", encoded, "Basic URL encoding test");
157
158 final Object result = urlCodec.encode((Object) null);
159 assertNull(result, "Encoding a null Object should return null");
160
161 assertThrows(EncoderException.class, () -> urlCodec.encode(Double.valueOf(3.0d)), "Trying to url encode a Double object should cause an exception.");
162 this.validateState(urlCodec);
163 }
164
165 @Test
166 public void testEncodeStringWithNull() throws Exception {
167 final URLCodec urlCodec = new URLCodec();
168 final String test = null;
169 final String result = urlCodec.encode(test, "charset");
170 assertNull(result, "Result should be null");
171 }
172
173 @Test
174 public void testEncodeUrlWithNullBitSet() throws Exception {
175 final URLCodec urlCodec = new URLCodec();
176 final String plain = "Hello there!";
177 final String encoded = new String(URLCodec.encodeUrl(null, plain.getBytes(StandardCharsets.UTF_8)));
178 assertEquals("Hello+there%21", encoded, "Basic URL encoding test");
179 assertEquals(plain, urlCodec.decode(encoded), "Basic URL decoding test");
180 this.validateState(urlCodec);
181 }
182
183 @Test
184 public void testInvalidEncoding() {
185 final URLCodec urlCodec = new URLCodec("NONSENSE");
186 final String plain = "Hello there!";
187 assertThrows(EncoderException.class, () -> urlCodec.encode(plain), "We set the encoding to a bogus NONSENSE value");
188 assertThrows(DecoderException.class, () -> urlCodec.decode(plain), "We set the encoding to a bogus NONSENSE value");
189 this.validateState(urlCodec);
190 }
191
192 @Test
193 public void testSafeCharEncodeDecode() throws Exception {
194 final URLCodec urlCodec = new URLCodec();
195 final String plain = "abc123_-.*";
196 final String encoded = urlCodec.encode(plain);
197 assertEquals(plain, encoded, "Safe chars URL encoding test");
198 assertEquals(plain, urlCodec.decode(encoded), "Safe chars URL decoding test");
199 this.validateState(urlCodec);
200 }
201
202 @Test
203 public void testUnsafeEncodeDecode() throws Exception {
204 final URLCodec urlCodec = new URLCodec();
205 final String plain = "~!@#$%^&()+{}\"\\;:`,/[]";
206 final String encoded = urlCodec.encode(plain);
207 assertEquals("%7E%21%40%23%24%25%5E%26%28%29%2B%7B%7D%22%5C%3B%3A%60%2C%2F%5B%5D", encoded, "Unsafe chars URL encoding test");
208 assertEquals(plain, urlCodec.decode(encoded), "Unsafe chars URL decoding test");
209 this.validateState(urlCodec);
210 }
211
212 @Test
213 public void testUTF8RoundTrip() throws Exception {
214
215 final String ru_msg = constructString(RUSSIAN_STUFF_UNICODE);
216 final String ch_msg = constructString(SWISS_GERMAN_STUFF_UNICODE);
217
218 final URLCodec urlCodec = new URLCodec();
219 this.validateState(urlCodec);
220
221 assertEquals("%D0%92%D1%81%D0%B5%D0%BC_%D0%BF%D1%80%D0%B8%D0%B2%D0%B5%D1%82", urlCodec.encode(ru_msg, CharEncoding.UTF_8));
222 assertEquals("Gr%C3%BCezi_z%C3%A4m%C3%A4", urlCodec.encode(ch_msg, CharEncoding.UTF_8));
223
224 assertEquals(ru_msg, urlCodec.decode(urlCodec.encode(ru_msg, CharEncoding.UTF_8), CharEncoding.UTF_8));
225 assertEquals(ch_msg, urlCodec.decode(urlCodec.encode(ch_msg, CharEncoding.UTF_8), CharEncoding.UTF_8));
226 this.validateState(urlCodec);
227 }
228
229 private void validateState(final URLCodec urlCodec) {
230
231 }
232 }