View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.juneau.uon;
18  
19  import static org.apache.juneau.commons.utils.CollectionUtils.*;
20  import static org.junit.jupiter.api.Assertions.*;
21  
22  import org.apache.juneau.collections.*;
23  import org.junit.jupiter.api.*;
24  
25  class UonSerializer_Test {
26  
27  	static UonSerializer s = UonSerializer.DEFAULT_ENCODING;
28  	static UonSerializer su = UonSerializer.DEFAULT;
29  	static UonSerializer sr = UonSerializer.DEFAULT_READABLE;
30  
31  	//====================================================================================================
32  	// Basic test
33  	//====================================================================================================
34  	@Test void a01_basic() throws Exception {
35  		// Simple string
36  		// Top level
37  		var t = (Object)"a";
38  		assertEquals("a", s.serialize(t));
39  		assertEquals("a", su.serialize(t));
40  		assertEquals("a", sr.serialize(t));
41  
42  		// 2nd level
43  		t = JsonMap.ofJson("{a:'a'}");
44  		assertEquals("(a=a)", s.serialize(t));
45  		assertEquals("(a=a)", su.serialize(t));
46  		assertEquals("(\n\ta=a\n)", sr.serialize(t));
47  
48  		// Simple map
49  		// Top level
50  		t = JsonMap.ofJson("{a:'b',c:123,d:false,e:true,f:null}");
51  		assertEquals("(a=b,c=123,d=false,e=true,f=null)", s.serialize(t));
52  		assertEquals("(a=b,c=123,d=false,e=true,f=null)", su.serialize(t));
53  		assertEquals("(\n\ta=b,\n\tc=123,\n\td=false,\n\te=true,\n\tf=null\n)", sr.serialize(t));
54  
55  		// 2nd level
56  		t = JsonMap.ofJson("{a:{a:'b',c:123,d:false,e:true,f:null}}");
57  		assertEquals("(a=(a=b,c=123,d=false,e=true,f=null))", s.serialize(t));
58  		assertEquals("(a=(a=b,c=123,d=false,e=true,f=null))", su.serialize(t));
59  		assertEquals("(\n\ta=(\n\t\ta=b,\n\t\tc=123,\n\t\td=false,\n\t\te=true,\n\t\tf=null\n\t)\n)", sr.serialize(t));
60  
61  		// Simple map with primitives as literals
62  		t = JsonMap.ofJson("{a:'b',c:'123',d:'false',e:'true',f:'null'}");
63  		assertEquals("(a=b,c='123',d='false',e='true',f='null')", s.serialize(t));
64  		assertEquals("(a=b,c='123',d='false',e='true',f='null')", su.serialize(t));
65  		assertEquals("(\n\ta=b,\n\tc='123',\n\td='false',\n\te='true',\n\tf='null'\n)", sr.serialize(t));
66  
67  		// null
68  		// Note that serializeParams is always encoded.
69  		// Top level
70  		t = null;
71  		assertEquals("null", s.serialize(t));
72  		assertEquals("null", su.serialize(t));
73  		assertEquals("null", sr.serialize(t));
74  
75  		// 2nd level
76  		t = JsonMap.ofJson("{null:null}");
77  		assertEquals("(null=null)", s.serialize(t));
78  		assertEquals("(null=null)", su.serialize(t));
79  		assertEquals("(\n\tnull=null\n)", sr.serialize(t));
80  
81  		// 3rd level
82  		t = JsonMap.ofJson("{null:{null:null}}");
83  		assertEquals("(null=(null=null))", s.serialize(t));
84  		assertEquals("(null=(null=null))", su.serialize(t));
85  		assertEquals("(\n\tnull=(\n\t\tnull=null\n\t)\n)", sr.serialize(t));
86  
87  		// Empty array
88  		// Top level
89  		t = new String[0];
90  		assertEquals("@()", s.serialize(t));
91  		assertEquals("@()", su.serialize(t));
92  		assertEquals("@()", sr.serialize(t));
93  
94  		// 2nd level in map
95  		t = JsonMap.ofJson("{x:[]}");
96  		assertEquals("(x=@())", s.serialize(t));
97  		assertEquals("(x=@())", su.serialize(t));
98  		assertEquals("(\n\tx=@()\n)", sr.serialize(t));
99  
100 		// Empty 2 dimensional array
101 		t = new String[1][0];
102 		assertEquals("@(@())", s.serialize(t));
103 		assertEquals("@(@())", su.serialize(t));
104 		assertEquals("@(\n\t@()\n)", sr.serialize(t));
105 
106 		// Array containing empty string
107 		// Top level
108 		t = a("");
109 		assertEquals("@('')", s.serialize(t));
110 		assertEquals("@('')", su.serialize(t));
111 		assertEquals("@(\n\t''\n)", sr.serialize(t));
112 
113 		// 2nd level
114 		t = JsonMap.ofJson("{x:['']}");
115 		assertEquals("(x=@(''))", s.serialize(t));
116 		assertEquals("(x=@(''))", su.serialize(t));
117 		assertEquals("(\n\tx=@(\n\t\t''\n\t)\n)", sr.serialize(t));
118 
119 		// Array containing 3 empty strings
120 		t = a("","","");
121 		assertEquals("@('','','')", s.serialize(t));
122 		assertEquals("@('','','')", su.serialize(t));
123 		assertEquals("@(\n\t'',\n\t'',\n\t''\n)", sr.serialize(t));
124 
125 		// String containing \u0000
126 		// Top level
127 		t = "\u0000";
128 		assertEquals("%00", s.serialize(t));
129 		assertEquals("\u0000", su.serialize(t));
130 		assertEquals("\u0000", sr.serialize(t));
131 
132 		// 2nd level
133 		t = JsonMap.ofJson("{'\u0000':'\u0000'}");
134 		assertEquals("(%00=%00)", s.serialize(t));
135 		assertEquals("(\u0000=\u0000)", su.serialize(t));
136 		assertEquals("(\n\t\u0000=\u0000\n)", sr.serialize(t));
137 
138 		// Boolean
139 		// Top level
140 		t = false;
141 		assertEquals("false", s.serialize(t));
142 		assertEquals("false", su.serialize(t));
143 		assertEquals("false", sr.serialize(t));
144 
145 		// 2nd level
146 		t = JsonMap.ofJson("{x:false}");
147 		assertEquals("(x=false)", s.serialize(t));
148 		assertEquals("(x=false)", su.serialize(t));
149 		assertEquals("(\n\tx=false\n)", sr.serialize(t));
150 
151 		// Number
152 		// Top level
153 		t = 123;
154 		assertEquals("123", s.serialize(t));
155 		assertEquals("123", su.serialize(t));
156 		assertEquals("123", sr.serialize(t));
157 
158 		// 2nd level
159 		t = JsonMap.ofJson("{x:123}");
160 		assertEquals("(x=123)", s.serialize(t));
161 		assertEquals("(x=123)", su.serialize(t));
162 		assertEquals("(\n\tx=123\n)", sr.serialize(t));
163 
164 		// Unencoded chars
165 		// Top level
166 		t = "x;/?:@-_.!*'";
167 		assertEquals("x;/?:@-_.!*~'", s.serialize(t));
168 		assertEquals("x;/?:@-_.!*~'", su.serialize(t));
169 		assertEquals("x;/?:@-_.!*~'", sr.serialize(t));
170 
171 		// 2nd level
172 		t = JsonMap.ofJson("{x:'x;/?:@-_.!*\\''}");
173 		assertEquals("(x=x;/?:@-_.!*~')", s.serialize(t));
174 		assertEquals("(x=x;/?:@-_.!*~')", su.serialize(t));
175 		assertEquals("(\n\tx=x;/?:@-_.!*~'\n)", sr.serialize(t));
176 
177 		// Encoded chars
178 		// Top level
179 		t = "x{}|\\^[]`<>#%\"&+";
180 		assertEquals("x%7B%7D%7C%5C%5E%5B%5D%60%3C%3E%23%25%22%26%2B", s.serialize(t));
181 		assertEquals("x{}|\\^[]`<>#%\"&+", su.serialize(t));
182 		assertEquals("x{}|\\^[]`<>#%\"&+", sr.serialize(t));
183 
184 		// 2nd level
185 		t = JsonMap.ofJson("{'x{}|\\\\^[]`<>#%\"&+':'x{}|\\\\^[]`<>#%\"&+'}");
186 		assertEquals("(x%7B%7D%7C%5C%5E%5B%5D%60%3C%3E%23%25%22%26%2B=x%7B%7D%7C%5C%5E%5B%5D%60%3C%3E%23%25%22%26%2B)", s.serialize(t));
187 		assertEquals("(x{}|\\^[]`<>#%\"&+=x{}|\\^[]`<>#%\"&+)", su.serialize(t));
188 		assertEquals("(\n\tx{}|\\^[]`<>#%\"&+=x{}|\\^[]`<>#%\"&+\n)", sr.serialize(t));
189 
190 		// Escaped chars
191 		// Top level
192 		t = "x$,()~";
193 		assertEquals("'x$,()~~'", s.serialize(t));
194 		assertEquals("'x$,()~~'", su.serialize(t));
195 		assertEquals("'x$,()~~'", sr.serialize(t));
196 
197 		// 2nd level
198 		// Note behavior on serializeParams() is different since 2nd-level is top level.
199 		t = JsonMap.ofJson("{'x$,()~':'x$,()~'}");
200 		assertEquals("('x$,()~~'='x$,()~~')", s.serialize(t));
201 		assertEquals("('x$,()~~'='x$,()~~')", su.serialize(t));
202 		assertEquals("(\n\t'x$,()~~'='x$,()~~'\n)", sr.serialize(t));
203 
204 		// 3rd level
205 		// Note behavior on serializeParams().
206 		t = JsonMap.ofJson("{'x$,()~':{'x$,()~':'x$,()~'}}");
207 		assertEquals("('x$,()~~'=('x$,()~~'='x$,()~~'))", s.serialize(t));
208 		assertEquals("('x$,()~~'=('x$,()~~'='x$,()~~'))", su.serialize(t));
209 		assertEquals("(\n\t'x$,()~~'=(\n\t\t'x$,()~~'='x$,()~~'\n\t)\n)", sr.serialize(t));
210 
211 		// Equals sign
212 		// Gets encoded at top level, and encoded+escaped at 2nd level.
213 		// Top level
214 		t = "x=";
215 		assertEquals("'x='", s.serialize(t));
216 		assertEquals("'x='", su.serialize(t));
217 		assertEquals("'x='", sr.serialize(t));
218 
219 		// 2nd level
220 		t = JsonMap.ofJson("{'x=':'x='}");
221 		assertEquals("('x='='x=')", s.serialize(t));
222 		assertEquals("('x='='x=')", su.serialize(t));
223 		assertEquals("(\n\t'x='='x='\n)", sr.serialize(t));
224 
225 		// 3rd level
226 		t = JsonMap.ofJson("{'x=':{'x=':'x='}}");
227 		assertEquals("('x='=('x='='x='))", s.serialize(t));
228 		assertEquals("('x='=('x='='x='))", su.serialize(t));
229 		assertEquals("(\n\t'x='=(\n\t\t'x='='x='\n\t)\n)", sr.serialize(t));
230 
231 		// String starting with parenthesis
232 		// Top level
233 		t = "()";
234 		assertEquals("'()'", s.serialize(t));
235 		assertEquals("'()'", su.serialize(t));
236 		assertEquals("'()'", sr.serialize(t));
237 
238 		// 2nd level
239 		t = JsonMap.ofJson("{'()':'()'}");
240 		assertEquals("('()'='()')", s.serialize(t));
241 		assertEquals("('()'='()')", su.serialize(t));
242 		assertEquals("(\n\t'()'='()'\n)", sr.serialize(t));
243 
244 		// String starting with $
245 		// Top level
246 		t = "$a";
247 		assertEquals("$a", s.serialize(t));
248 		assertEquals("$a", su.serialize(t));
249 		assertEquals("$a", sr.serialize(t));
250 
251 		// 2nd level
252 		t = JsonMap.ofJson("{$a:'$a'}");
253 		assertEquals("($a=$a)", s.serialize(t));
254 		assertEquals("($a=$a)", su.serialize(t));
255 		assertEquals("(\n\t$a=$a\n)", sr.serialize(t));
256 
257 		// Blank string
258 		// Top level
259 		t = "";
260 		assertEquals("''", s.serialize(t));
261 		assertEquals("''", su.serialize(t));
262 		assertEquals("''", sr.serialize(t));
263 
264 		// 2nd level
265 		t = JsonMap.ofJson("{'':''}");
266 		assertEquals("(''='')", s.serialize(t));
267 		assertEquals("(''='')", su.serialize(t));
268 		assertEquals("(\n\t''=''\n)", sr.serialize(t));
269 
270 		// 3rd level
271 		t = JsonMap.ofJson("{'':{'':''}}");
272 		assertEquals("(''=(''=''))", s.serialize(t));
273 		assertEquals("(''=(''=''))", su.serialize(t));
274 		assertEquals("(\n\t''=(\n\t\t''=''\n\t)\n)", sr.serialize(t));
275 
276 		// Newline character
277 		// Top level
278 		t = "\n";
279 		assertEquals("'%0A'", s.serialize(t));
280 		assertEquals("'\n'", su.serialize(t));
281 		assertEquals("'\n'", sr.serialize(t));
282 
283 		// 2nd level
284 		t = JsonMap.ofJson("{'\n':'\n'}");
285 		assertEquals("('%0A'='%0A')", s.serialize(t));
286 		assertEquals("('\n'='\n')", su.serialize(t));
287 		assertEquals("(\n\t'\n'='\n'\n)", sr.serialize(t));
288 
289 		// 3rd level
290 		t = JsonMap.ofJson("{'\n':{'\n':'\n'}}");
291 		assertEquals("('%0A'=('%0A'='%0A'))", s.serialize(t));
292 		assertEquals("('\n'=('\n'='\n'))", su.serialize(t));
293 		assertEquals("(\n\t'\n'=(\n\t\t'\n'='\n'\n\t)\n)", sr.serialize(t));
294 	}
295 
296 	//====================================================================================================
297 	// Unicode characters test
298 	//====================================================================================================
299 	@Test void a02_unicodeChars() throws Exception {
300 
301 		// 2-byte UTF-8 character
302 		// Top level
303 		var t = (Object)"¢";
304 		assertEquals("%C2%A2", s.serialize(t));
305 		assertEquals("¢", su.serialize(t));
306 		assertEquals("¢", sr.serialize(t));
307 
308 		// 2nd level
309 		t = JsonMap.ofJson("{'¢':'¢'}");
310 		assertEquals("(%C2%A2=%C2%A2)", s.serialize(t));
311 		assertEquals("(¢=¢)", su.serialize(t));
312 		assertEquals("(\n\t¢=¢\n)", sr.serialize(t));
313 
314 		// 3rd level
315 		t = JsonMap.ofJson("{'¢':{'¢':'¢'}}");
316 		assertEquals("(%C2%A2=(%C2%A2=%C2%A2))", s.serialize(t));
317 		assertEquals("(¢=(¢=¢))", su.serialize(t));
318 		assertEquals("(\n\t¢=(\n\t\t¢=¢\n\t)\n)", sr.serialize(t));
319 
320 		// 3-byte UTF-8 character
321 		// Top level
322 		t = "€";
323 		assertEquals("%E2%82%AC", s.serialize(t));
324 		assertEquals("€", su.serialize(t));
325 		assertEquals("€", sr.serialize(t));
326 
327 		// 2nd level
328 		t = JsonMap.ofJson("{'€':'€'}");
329 		assertEquals("(%E2%82%AC=%E2%82%AC)", s.serialize(t));
330 		assertEquals("(€=€)", su.serialize(t));
331 		assertEquals("(\n\t€=€\n)", sr.serialize(t));
332 
333 		// 3rd level
334 		t = JsonMap.ofJson("{'€':{'€':'€'}}");
335 		assertEquals("(%E2%82%AC=(%E2%82%AC=%E2%82%AC))", s.serialize(t));
336 		assertEquals("(€=(€=€))", su.serialize(t));
337 		assertEquals("(\n\t€=(\n\t\t€=€\n\t)\n)", sr.serialize(t));
338 
339 		// 4-byte UTF-8 character
340 		// Top level
341 		t = "𤭢";
342 		assertEquals("%F0%A4%AD%A2", s.serialize(t));
343 		assertEquals("𤭢", su.serialize(t));
344 		assertEquals("𤭢", sr.serialize(t));
345 
346 		// 2nd level
347 		t = JsonMap.ofJson("{'𤭢':'𤭢'}");
348 		assertEquals("(%F0%A4%AD%A2=%F0%A4%AD%A2)", s.serialize(t));
349 		assertEquals("(𤭢=𤭢)", su.serialize(t));
350 		assertEquals("(\n\t𤭢=𤭢\n)", sr.serialize(t));
351 
352 		// 3rd level
353 		t = JsonMap.ofJson("{'𤭢':{'𤭢':'𤭢'}}");
354 		assertEquals("(%F0%A4%AD%A2=(%F0%A4%AD%A2=%F0%A4%AD%A2))", s.serialize(t));
355 		assertEquals("(𤭢=(𤭢=𤭢))", su.serialize(t));
356 		assertEquals("(\n\t𤭢=(\n\t\t𤭢=𤭢\n\t)\n)", sr.serialize(t));
357 	}
358 }