json_fixer/tests/
jsonfixer_tests.rs

1#[cfg(test)]
2mod tests {
3    use crate::JsonFixer;
4    use crate::JsonFixerConfig;
5    use crate::JsonFixerError;
6    use crate::jsonfixer::jsonfixer_error::SyntaxError;
7
8    /*
9     ************************** Remove whitespaces *************************
10     */
11
12    #[test]
13    fn test_empty_object() {
14        let input = "{}";
15        assert_eq!(JsonFixer::fix(input).unwrap(), "{}");
16    }
17
18    #[test]
19    fn test_empty_array() {
20        let input = "[]";
21        assert_eq!(JsonFixer::fix(input).unwrap(), "[]");
22    }
23
24    #[test]
25    fn test_basic_object() {
26        let input = r#"{"name":"John","age":30}"#;
27        assert_eq!(JsonFixer::fix(input).unwrap(), r#"{"name":"John","age":30}"#);
28    }
29
30    #[test]
31    fn test_basic_array() {
32        let input = r#"[1,2,3,4,5]"#;
33        assert_eq!(JsonFixer::fix(input).unwrap(), r#"[1,2,3,4,5]"#);
34    }
35
36    #[test]
37    fn test_nested_structures() {
38        let input = r#"{"users":[{"name":"John","age":30},{"name":"Jane","age":25}]}"#;
39        assert_eq!(JsonFixer::fix(input).unwrap(), input);
40    }
41
42    #[test]
43    fn test_whitespace() {
44        let input = r#"
45        {
46            "name": "John",
47            "age": 30
48        }
49        "#;
50        assert_eq!(JsonFixer::fix(input).unwrap(), r#"{"name":"John","age":30}"#);
51    }
52
53    #[test]
54    fn test_unquoted_keys() {
55        let input = r#"{name: "John", age: 30}"#;
56        assert_eq!(JsonFixer::fix(input).unwrap(), r#"{"name":"John","age":30}"#);
57    }
58
59    #[test]
60    fn test_single_quotes() {
61        let input = r#"{'name': 'John', 'age': 30}"#;
62        assert_eq!(JsonFixer::fix(input).unwrap(), r#"{"name":"John","age":30}"#);
63    }
64
65    #[test]
66    fn test_trailing_commas() {
67        let cases = vec![
68            (
69                r#"{"name": "John", "age": 30,}"#,
70                r#"{"name":"John","age":30}"#,
71            ),
72            (r#"[1, 2, 3,]"#, r#"[1,2,3]"#),
73            (r#"{"arr": [1, 2, 3,],}"#, r#"{"arr":[1,2,3]}"#),
74        ];
75
76        for (input, expected) in cases {
77            assert_eq!(JsonFixer::fix(input).unwrap(), expected);
78        }
79    }
80
81    #[test]
82    fn test_multiple_commas() {
83        let cases = vec![
84            (r#"[1,,,2,,,3]"#, r#"[1,2,3]"#),
85            (r#"{"a":1,,,"b":2,,,"c":3}"#, r#"{"a":1,"b":2,"c":3}"#),
86        ];
87
88        for (input, expected) in cases {
89            assert_eq!(JsonFixer::fix(input).unwrap(), expected);
90        }
91    }
92
93    #[test]
94    fn test_string_escapes() {
95        let input = r#""Hello \"hello\\nnew line\" ""#;
96        let expect = r#""Hello \"hello\nnew line\" ""#;
97        let output = JsonFixer::fix(input).unwrap();
98        println!("input : {:?}", input);
99        println!("expect : {:?}", expect);
100        println!("output : {:?}", output);
101        assert_eq!(output, expect);
102    }
103
104    #[test]
105    fn test_numbers() {
106        let cases = vec![
107            (r#"{"num1": .123}"#, r#"{"num1":0.123}"#),
108            (r#"{"num2": 123.}"#, r#"{"num2":123}"#),
109            (r#"{"num": 42}"#, r#"{"num":42}"#),
110            (r#"{"num": -42}"#, r#"{"num":-42}"#),
111            (r#"{"num": 3.14}"#, r#"{"num":3.14}"#),
112            (r#"{"num": -3.14}"#, r#"{"num":-3.14}"#),
113            (r#"{"num": 1e5}"#, r#"{"num":1e5}"#),
114            (r#"{"num": 1.23e-4}"#, r#"{"num":1.23e-4}"#),
115            (r#"{"num": -1.23e+4}"#, r#"{"num":-1.23e+4}"#),
116        ];
117
118        for input in cases {
119            let result = JsonFixer::fix(input.0);
120            // println!("Test Error2: {:?}" ,result);
121            assert_eq!(result.unwrap(), input.1);
122        }
123    }
124
125    #[test]
126    fn test_boolean_and_null() {
127        let input = r#"{"active": true, "verified": false, "data": null}"#;
128        let output = r#"{"active":true,"verified":false,"data":null}"#;
129        assert_eq!(JsonFixer::fix(input).unwrap(), output);
130    }
131
132    #[test]
133    fn test_error_unmatched_quotes() {
134        let input = r#"{"name": "John"#;
135        assert!(matches!(
136            JsonFixer::fix(input),
137            Err(JsonFixerError::Syntax(SyntaxError::UnmatchedQuotes(_)))
138        ));
139    }
140
141    #[test]
142    fn test_error_unexpected_end() {
143        let input = r#"{"name": "John", p"#;
144        let result = JsonFixer::fix(input);
145        //println!("Error : {:?}",result);
146        assert!(matches!(
147            result,
148            Err(JsonFixerError::Syntax(SyntaxError::UnexpectedEndOfInput(_)))
149        ));
150    }
151
152    #[test]
153    fn test_error_invalid_number() {
154        let cases = vec![
155            (r#"{"num3": 1.2.3}"#, r#"{"num3":1.2.3}"#),
156            (r#"{"num4": --123}"#, r#"{"num4":--123}"#),
157            (r#"{"num5": 1e}"#, r#"{"num5":1e}"#),
158        ];
159
160        for input in cases {
161            let result = JsonFixer::fix(input.0);
162
163            //println!("Test Error1: {:?}" ,result);
164            assert!(matches!(
165                result,
166                Err(JsonFixerError::Syntax(SyntaxError::InvalidNumber(_, _)))
167            ));
168        }
169    }
170
171    #[test]
172    fn test_error_unexpected_token() {
173        let input = r#"{"name" _: "John", "age": 30}"#; // Missing comma
174        let result = JsonFixer::fix(input);
175        //println!("Test Error0: {:?}" ,result);
176
177        assert!(matches!(
178            result,
179            Err(JsonFixerError::Syntax(SyntaxError::UnexpectedToken(_, _)))
180        ));
181    }
182    #[test]
183    fn test_fix_missing_comma() {
184        let input = r#"{"name": "John" "age": 30 "id": 0 }"#;
185        let output = r#"{"name":"John","age":30,"id":0}"#;
186        let result = JsonFixer::fix(input);
187
188        assert_eq!(result.unwrap(), output);
189    }
190
191    /*
192     ************************** Preserve *************************
193     */
194
195    #[test]
196    fn test_object_preserve() {
197        let inputs = vec![
198            ("{   }", "{   }"),
199            (
200                r#"{  
201            
202            }"#,
203                r#"{  
204            
205            }"#,
206            ),
207            (
208                r#"{  
209
210            }"#,
211                r#"{  
212
213            }"#,
214            ),
215            (
216                r#"{  
217                "key1": 30,
218            }"#,
219                r#"{  
220                "key1": 30
221            }"#,
222            ),
223            (
224                r#"{  
225                "key1": 30,
226                key2 : "value",
227                key3 : {
228                    other : 12,
229                    name : "hashdiese"
230                    numbers: [  1, 2, 
231                    3,
232                    ],
233                }
234            }"#,
235                r#"{  
236                "key1": 30,
237                "key2" : "value",
238                "key3" : {
239                    "other" : 12,
240                    "name" : "hashdiese",
241                    "numbers": [  1, 2, 
242                    3
243                    ]
244                }
245            }"#,
246            ),
247        ];
248
249        let mut config = JsonFixerConfig::default();
250        config.preserve = true;
251        //config.sort_keys = true;
252
253        for input in inputs {
254            let result = JsonFixer::fix_with_config(input.0, config.clone()).unwrap();
255            println!("Input     : {}", input.0);
256            println!("Expected  : {}", input.1);
257            println!("Output    : {}", result);
258            assert_eq!(result, input.1);
259        }
260    }
261
262    #[test]
263    fn test_object_unpreserve() {
264        let inputs = vec![
265            ("{   }", "{}"),
266            (
267                r#"{  
268            
269            }"#,
270                r#"{}"#,
271            ),
272            (
273                r#"{  
274
275            }"#,
276                r#"{}"#,
277            ),
278            (
279                r#"{  
280                "key1": 30,
281            }"#,
282                r#"{"key1":30}"#,
283            ),
284            (
285                r#"{  
286                "key1": 30,
287                key2 : "value",
288                key3 : {
289                    other : 12,
290                    name : "hashdiese"
291                    numbers: [  1, 2, 
292                    3,
293                    ],
294                }
295            }"#,
296                r#"{"key1":30,"key2":"value","key3":{"other":12,"name":"hashdiese","numbers":[1,2,3]}}"#,
297            ),
298        ];
299
300        let mut config = JsonFixerConfig::default();
301        config.preserve = false;
302        config.sort_keys = false;
303
304        for input in inputs {
305            let result = JsonFixer::fix_with_config(input.0, config.clone()).unwrap();
306            println!("Input     : {}", input.0);
307            println!("Expected  : {}", input.1);
308            println!("Output    : {}", result);
309            assert_eq!(result, input.1);
310        }
311    }
312
313    #[test]
314    fn test_object_space_between() {
315        let inputs = vec![
316            ("{   }", "{}"),
317            (
318                r#"{  
319            
320            }"#,
321                r#"{}"#,
322            ),
323            (
324                r#"{  
325
326            }"#,
327                r#"{}"#,
328            ),
329            (
330                r#"{  
331                "key1": 30,
332            }"#,
333                r#"{ "key1": 30 }"#,
334            ),
335            (
336                r#"{  
337                "key1": 30,
338                key2 : "value",
339                key3 : {
340                    other : 12,
341                    name : "hashdiese"
342                    numbers: [  1, 2, 
343                    3,
344                    ],
345                }
346            }"#,
347                r#"{ "key1": 30, "key2": "value", "key3": { "other": 12, "name": "hashdiese", "numbers": [ 1, 2, 3 ] } }"#,
348            ),
349        ];
350
351        let mut config = JsonFixerConfig::default();
352        config.preserve = false;
353        config.sort_keys = false;
354        config.space_between = true;
355
356        for input in inputs {
357            let result = JsonFixer::fix_with_config(input.0, config.clone()).unwrap();
358            println!("Input     : {}", input.0);
359            println!("Expected  : {}", input.1);
360            println!("Output    : {}", result);
361            assert_eq!(result, input.1);
362        }
363    }
364    #[test]
365    fn test_object_pretty() {
366        let inputs = vec![
367            ("{   }", "{}"),
368            (
369                r#"{  
370            
371            }"#,
372                r#"{}"#,
373            ),
374            (
375                r#"{  
376
377            }"#,
378                r#"{}"#,
379            ),
380            (
381                r#"  {  
382                "key1": 30,
383            }  "#,
384                r#"{
385    "key1": 30
386}"#,
387            ),
388            (
389                r#"{  
390                "key1": 30,
391                key2 : "value",
392                key3 : {
393                    other : 12,
394                    name : "hashdiese"
395                    numbers: [  1, 2, 
396                    3,
397                    ],
398                }
399            }"#,
400                r#"{
401    "key1": 30,
402    "key2": "value",
403    "key3": {
404        "other": 12,
405        "name": "hashdiese",
406        "numbers": [
407            1,
408            2,
409            3
410        ]
411    }
412}"#,
413            ),
414        ];
415
416        let mut config = JsonFixerConfig::default();
417        config.preserve = false;
418        config.sort_keys = false;
419        config.space_between = false;
420        config.beautify = true;
421        config.indent_size = 4;
422
423        for input in inputs {
424            let result = JsonFixer::fix_with_config(input.0, config.clone()).unwrap();
425            println!("Input     : {}", input.0);
426            println!("Expected  : {}", input.1);
427            println!("Output    : {}", result);
428            assert_eq!(result, input.1);
429        }
430    }
431}