1 // Copyright (c) 2023 Huawei Device Co., Ltd.
2 // Licensed under the Apache License, Version 2.0 (the "License");
3 // you may not use this file except in compliance with the License.
4 // You may obtain a copy of the License at
5 //
6 // http://www.apache.org/licenses/LICENSE-2.0
7 //
8 // Unless required by applicable law or agreed to in writing, software
9 // distributed under the License is distributed on an "AS IS" BASIS,
10 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 // See the License for the specific language governing permissions and
12 // limitations under the License.
13
14 #![allow(clippy::missing_safety_doc)]
15
16 use crate::*;
17 use core::ptr::{null_mut, slice_from_raw_parts};
18 use core::str::from_utf8_unchecked;
19 use libc::{c_char, c_double, c_int, c_longlong, c_void, strlen};
20 use std::ffi::CString;
21
22 /// Boolean value mapping.
23 const FALSE: c_int = 0;
24
25 /// Operation success or failure.
26 const SUCCESS: c_int = 1;
27 const FAILURE: c_int = 0;
28
29 /// Empty pointer of YlongJson*
30 const NULL_MUT_YLONG_JSON: *mut YlongJson = null_mut::<YlongJson>();
31 /// Empty pointer of char*
32 const NULL_MUT_CSTR: *mut c_char = null_mut::<c_char>();
33
34 /// A void* pointer is passed to C for use.
35 pub type YlongJson = c_void;
36
37 /// Parses a JSON text string.
38 /// Returns a JSON object on success and null on failure.
39 #[no_mangle]
ylong_json_parse( value: *mut c_char, err_msg: *mut *mut c_char, ) -> *mut YlongJson40 pub unsafe extern "C" fn ylong_json_parse(
41 value: *mut c_char,
42 err_msg: *mut *mut c_char,
43 ) -> *mut YlongJson {
44 // Using `ptr::slice_from_raw_parts` here dramatically
45 // reduces the cost of converting between char* and &[u8].
46 let len = strlen(value);
47 let slice = &*slice_from_raw_parts(value as *mut u8, len);
48
49 let value = match JsonValue::from_text(slice) {
50 Ok(v) => v,
51 Err(e) => {
52 // If an error occurs, writes error messages into err_msg.
53 *err_msg = CString::from_vec_unchecked(e.to_string().into_bytes()).into_raw();
54 return NULL_MUT_YLONG_JSON;
55 }
56 };
57
58 Box::into_raw(Box::from(value)) as *mut YlongJson
59 }
60
61 /// Frees a C string.
62 #[no_mangle]
ylong_json_free_string(string: *mut c_char)63 pub unsafe extern "C" fn ylong_json_free_string(string: *mut c_char) {
64 if string.is_null() {
65 return;
66 }
67
68 let _ = Box::from_raw(string);
69 }
70
71 /// Outputs a JSON object to a string in plain format.
72 /// Returns a C string on success and null on failure.
73 #[no_mangle]
ylong_json_print_unformatted(item: *const YlongJson) -> *mut c_char74 pub unsafe extern "C" fn ylong_json_print_unformatted(item: *const YlongJson) -> *mut c_char {
75 if item.is_null() {
76 return NULL_MUT_CSTR;
77 }
78
79 let value = &mut *(item as *mut JsonValue);
80
81 // Requests 256 bytes of memory in advance to improve output efficiency.
82 // Here we use `Vec::with_capacity(256)`, which performs better when `12 < string.len() < 256`.
83 // If here we use `Vec::new()`, it performs better when `string.len() < 32 || 256 > string.len()`
84 // In most cases, `12 < the average string.len() < 256`, so we use `Vec::with_capacity()`.
85 let mut vec = Vec::with_capacity(256);
86 if value.compact_encode(&mut vec).is_err() {
87 return NULL_MUT_CSTR;
88 }
89
90 CString::from_vec_unchecked(vec).into_raw()
91 }
92
93 /// Deletes a JSON object.
94 #[no_mangle]
ylong_json_delete(item: *mut YlongJson)95 pub unsafe extern "C" fn ylong_json_delete(item: *mut YlongJson) {
96 if item.is_null() {
97 return;
98 }
99
100 let _ = Box::from_raw(item as *mut JsonValue);
101 }
102
103 /// Duplicates a JSON object.
104 /// Return a new JSON object on success and null on failure.
105 #[no_mangle]
ylong_json_duplicate( item: *const YlongJson, recurse: c_int, ) -> *mut YlongJson106 pub unsafe extern "C" fn ylong_json_duplicate(
107 item: *const YlongJson,
108 recurse: c_int,
109 ) -> *mut YlongJson {
110 if item.is_null() {
111 return NULL_MUT_YLONG_JSON;
112 }
113
114 if recurse == FALSE {
115 let value = &*(item as *mut JsonValue);
116 let value_clone = match value {
117 JsonValue::Array(_) => JsonValue::Array(Array::new()),
118 JsonValue::Object(_) => JsonValue::Object(Object::new()),
119 x => x.clone(),
120 };
121 return Box::into_raw(Box::from(value_clone)) as *mut YlongJson;
122 }
123
124 let value = &*(item as *mut JsonValue);
125 Box::into_raw(Box::from(value.clone())) as *mut YlongJson
126 }
127
128 /// Creates a JSON null object and returns a new JSON null object.
129 #[no_mangle]
ylong_json_create_null() -> *mut YlongJson130 pub unsafe extern "C" fn ylong_json_create_null() -> *mut YlongJson {
131 Box::into_raw(Box::from(JsonValue::Null)) as *mut YlongJson
132 }
133
134 /// Checks whether a JSON object is null.
135 /// Returns a boolean value indicating whether the object is null.
136 #[no_mangle]
ylong_json_is_null(item: *mut YlongJson) -> c_int137 pub unsafe extern "C" fn ylong_json_is_null(item: *mut YlongJson) -> c_int {
138 if item.is_null() {
139 return FALSE;
140 }
141
142 let item = &*(item as *mut JsonValue);
143
144 item.is_null() as c_int
145 }
146
147 /// Creates a JSON boolean object.
148 #[no_mangle]
ylong_json_create_bool(boolean: c_int) -> *mut YlongJson149 pub unsafe extern "C" fn ylong_json_create_bool(boolean: c_int) -> *mut YlongJson {
150 // If it is equal to 0, the result is false. Otherwise it is true.
151 Box::into_raw(Box::from(JsonValue::Boolean(boolean != FALSE))) as *mut YlongJson
152 }
153
154 /// Checks whether a JSON object is a boolean.
155 #[no_mangle]
ylong_json_is_bool(item: *const YlongJson) -> c_int156 pub unsafe extern "C" fn ylong_json_is_bool(item: *const YlongJson) -> c_int {
157 if item.is_null() {
158 return FALSE;
159 }
160
161 let item = &*(item as *mut JsonValue);
162
163 item.is_boolean() as c_int
164 }
165
166 /// Gets the boolean value of a JSON boolean object.
167 /// Returns a boolean value on success and an error code on failure.
168 #[no_mangle]
ylong_json_get_value_from_bool( boolean: *const YlongJson, value: *mut c_int, ) -> c_int169 pub unsafe extern "C" fn ylong_json_get_value_from_bool(
170 boolean: *const YlongJson,
171 value: *mut c_int,
172 ) -> c_int {
173 if boolean.is_null() {
174 return FAILURE;
175 }
176
177 let boolean = &*(boolean as *mut JsonValue);
178 let boolean = match boolean.try_as_boolean() {
179 Ok(b) => b,
180 Err(_) => return FAILURE,
181 };
182 // For c_int value, true maps to 1, while false maps to 0.
183 *value = *boolean as c_int;
184 SUCCESS
185 }
186
187 /// Sets the boolean value of a JSON boolean object.
188 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
189 #[no_mangle]
ylong_json_set_value_to_bool( boolean: *mut YlongJson, value: c_int, ) -> c_int190 pub unsafe extern "C" fn ylong_json_set_value_to_bool(
191 boolean: *mut YlongJson,
192 value: c_int,
193 ) -> c_int {
194 if boolean.is_null() {
195 return FAILURE;
196 }
197
198 let boolean = &mut *(boolean as *mut JsonValue);
199 let boolean = match boolean.try_as_mut_boolean() {
200 Ok(b) => b,
201 Err(_) => return FAILURE,
202 };
203 // The *boolean is false if value is 0, and true if value is not 1.
204 *boolean = value != FALSE;
205 SUCCESS
206 }
207
208 /// Creates a JSON double number object.
209 /// Returns a pointer to the newly created JSON number.
210 #[no_mangle]
ylong_json_create_double_number(number: c_double) -> *mut YlongJson211 pub unsafe extern "C" fn ylong_json_create_double_number(number: c_double) -> *mut YlongJson {
212 Box::into_raw(Box::from(JsonValue::Number(Number::Float(number)))) as *mut YlongJson
213 }
214
215 /// Creates a JSON integer number object.
216 /// Returns a pointer to the newly created JSON number.
217 #[no_mangle]
ylong_json_create_int_number(number: c_longlong) -> *mut YlongJson218 pub unsafe extern "C" fn ylong_json_create_int_number(number: c_longlong) -> *mut YlongJson {
219 Box::into_raw(Box::from(JsonValue::Number(Number::Signed(number)))) as *mut YlongJson
220 }
221
222 /// Checks whether a JSON object is a number.
223 /// Returns a `c_int` where TRUE indicates that the item is a number, and FALSE indicates otherwise.
224 #[no_mangle]
ylong_json_is_number(item: *const YlongJson) -> c_int225 pub unsafe extern "C" fn ylong_json_is_number(item: *const YlongJson) -> c_int {
226 if item.is_null() {
227 return FALSE;
228 }
229
230 let item = &*(item as *mut JsonValue);
231 item.is_number() as c_int
232 }
233
234 /// Checks whether a JSON object is a double number.
235 /// Returns a `c_int` where TRUE indicates that the number is a double, and FALSE indicates otherwise.
236 #[no_mangle]
ylong_json_is_double_number(item: *const YlongJson) -> c_int237 pub unsafe extern "C" fn ylong_json_is_double_number(item: *const YlongJson) -> c_int {
238 if item.is_null() {
239 return FALSE;
240 }
241
242 let item = &*(item as *mut JsonValue);
243 match item.try_as_number() {
244 Ok(n) => matches!(n, Number::Float(_)) as c_int,
245 Err(_) => FALSE,
246 }
247 }
248
249 /// Checks whether a JSON object is an integer number.
250 /// Returns a `c_int` where TRUE indicates that the number is an integer, and FALSE indicates otherwise.
251 #[no_mangle]
ylong_json_is_int_number(item: *const YlongJson) -> c_int252 pub unsafe extern "C" fn ylong_json_is_int_number(item: *const YlongJson) -> c_int {
253 if item.is_null() {
254 return FALSE;
255 }
256
257 let item = &*(item as *mut JsonValue);
258 match item.try_as_number() {
259 Ok(n) => matches!(n, Number::Signed(_) | Number::Unsigned(_)) as c_int,
260 Err(_) => FALSE,
261 }
262 }
263
264 /// Gets the double value of a JSON number object.
265 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
266 #[no_mangle]
ylong_json_get_double_value_from_number( number: *const YlongJson, value: *mut c_double, ) -> c_int267 pub unsafe extern "C" fn ylong_json_get_double_value_from_number(
268 number: *const YlongJson,
269 value: *mut c_double,
270 ) -> c_int {
271 if number.is_null() {
272 return FAILURE;
273 }
274
275 let number = &*(number as *mut JsonValue);
276 let number = match number.try_as_number() {
277 Ok(n) => n,
278 Err(_) => return FAILURE,
279 };
280 // Coercing u64 or i64 to f64 may result in a loss of data accuracy.
281 match number {
282 Number::Float(f) => *value = *f as c_double,
283 Number::Unsigned(u) => *value = *u as c_double,
284 Number::Signed(i) => *value = *i as c_double,
285 }
286 SUCCESS
287 }
288
289 /// Gets the integer value of a JSON number object.
290 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
291 #[no_mangle]
ylong_json_get_int_value_from_number( number: *const YlongJson, value: *mut c_longlong, ) -> c_int292 pub unsafe extern "C" fn ylong_json_get_int_value_from_number(
293 number: *const YlongJson,
294 value: *mut c_longlong,
295 ) -> c_int {
296 if number.is_null() {
297 return FAILURE;
298 }
299
300 let number = &*(number as *mut JsonValue);
301 let number = match number.try_as_number() {
302 Ok(n) => n,
303 Err(_) => return FAILURE,
304 };
305 // Coercing u64 or i64 or f64 to i64 may result in a loss of data accuracy.
306 match number {
307 Number::Float(f) => *value = *f as c_longlong,
308 Number::Unsigned(u) => *value = *u as c_longlong,
309 Number::Signed(i) => *value = *i as c_longlong,
310 }
311 SUCCESS
312 }
313
314 /// Sets the double value of a JSON number object.
315 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
316 #[no_mangle]
ylong_json_set_double_value_to_number( number: *mut YlongJson, value: c_double, ) -> c_int317 pub unsafe extern "C" fn ylong_json_set_double_value_to_number(
318 number: *mut YlongJson,
319 value: c_double,
320 ) -> c_int {
321 if number.is_null() {
322 return FAILURE;
323 }
324
325 let number = &mut *(number as *mut JsonValue);
326 let number = match number.try_as_mut_number() {
327 Ok(n) => n,
328 Err(_) => return FAILURE,
329 };
330 *number = Number::Float(value);
331 SUCCESS
332 }
333
334 /// Sets the integer value of a JSON number object.
335 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
336 #[no_mangle]
ylong_json_set_int_value_to_number( number: *mut YlongJson, value: c_longlong, ) -> c_int337 pub unsafe extern "C" fn ylong_json_set_int_value_to_number(
338 number: *mut YlongJson,
339 value: c_longlong,
340 ) -> c_int {
341 if number.is_null() {
342 return FAILURE;
343 }
344
345 let number = &mut *(number as *mut JsonValue);
346 let number = match number.try_as_mut_number() {
347 Ok(n) => n,
348 Err(_) => return FAILURE,
349 };
350 *number = Number::Signed(value);
351 SUCCESS
352 }
353
354 /// Creates a `YlongJson` string from a given C-style string.
355 /// If the input string is null, it returns a null `YlongJson`.
356 #[no_mangle]
ylong_json_create_string(string: *const c_char) -> *mut YlongJson357 pub unsafe extern "C" fn ylong_json_create_string(string: *const c_char) -> *mut YlongJson {
358 if string.is_null() {
359 return NULL_MUT_YLONG_JSON;
360 }
361
362 let len = strlen(string);
363 let slice = &*slice_from_raw_parts(string as *mut u8, len);
364 let string = CString::from_vec_unchecked(slice.to_vec());
365 Box::into_raw(Box::from(JsonValue::String(string))) as *mut YlongJson
366 }
367
368 /// Checks if the `YlongJson` item is a string.
369 /// Returns `FALSE` if the item is null or not a string, and `TRUE` otherwise.
370 #[no_mangle]
ylong_json_is_string(item: *const YlongJson) -> c_int371 pub unsafe extern "C" fn ylong_json_is_string(item: *const YlongJson) -> c_int {
372 if item.is_null() {
373 return FALSE;
374 }
375
376 let item = &*(item as *mut JsonValue);
377 item.is_string() as c_int
378 }
379
380 /// The char* returned by this function differs from the original data,
381 /// meaning that any changes to this char* will not be reflected in the original data.
382 #[no_mangle]
ylong_json_get_value_from_string( string: *const YlongJson, value: *mut *mut c_char, ) -> c_int383 pub unsafe extern "C" fn ylong_json_get_value_from_string(
384 string: *const YlongJson,
385 value: *mut *mut c_char,
386 ) -> c_int {
387 if string.is_null() {
388 return FAILURE;
389 }
390
391 let string = &*(string as *mut JsonValue);
392 let string = match string.try_as_string() {
393 Ok(s) => s,
394 Err(_) => return FAILURE,
395 };
396 // If `c_adapter` feature is on, the pointer of the inner char arrays can be obtained directly,
397 // because the string pointer actually points to a `CString`
398 *value = string.as_ptr() as *mut c_char;
399 SUCCESS
400 }
401
402 /// Sets a `YlongJson` string to a given C-style string.
403 /// If the `YlongJson` string or the input string is null, it returns `FAILURE`.
404 #[no_mangle]
ylong_json_set_value_to_string( string: *mut YlongJson, value: *const c_char, ) -> c_int405 pub unsafe extern "C" fn ylong_json_set_value_to_string(
406 string: *mut YlongJson,
407 value: *const c_char,
408 ) -> c_int {
409 if string.is_null() || value.is_null() {
410 return FAILURE;
411 }
412
413 let string = &mut *(string as *mut JsonValue);
414 let string = match string.try_as_mut_string() {
415 Ok(s) => s,
416 Err(_) => return FAILURE,
417 };
418 let len = strlen(value);
419 let slice = &*slice_from_raw_parts(value as *mut u8, len);
420 *string = CString::from_vec_unchecked(slice.to_vec());
421 SUCCESS
422 }
423
424 /// Creates a `YlongJson` array.
425 #[no_mangle]
ylong_json_create_array() -> *mut YlongJson426 pub unsafe extern "C" fn ylong_json_create_array() -> *mut YlongJson {
427 Box::into_raw(Box::from(JsonValue::Array(Array::new()))) as *mut YlongJson
428 }
429
430 /// Checks if the `YlongJson` item is an array.
431 /// Returns `FALSE` if the item is null or not an array, and `TRUE` otherwise.
432 #[no_mangle]
ylong_json_is_array(item: *const YlongJson) -> c_int433 pub unsafe extern "C" fn ylong_json_is_array(item: *const YlongJson) -> c_int {
434 if item.is_null() {
435 return FALSE;
436 }
437
438 let item = &*(item as *mut JsonValue);
439 item.is_array() as c_int
440 }
441
442 /// Gets the size of a `YlongJson` array.
443 /// If the `YlongJson` array or the size is null, it returns `FAILURE`.
444 #[no_mangle]
ylong_json_get_array_size( array: *const YlongJson, size: *mut c_int, ) -> c_int445 pub unsafe extern "C" fn ylong_json_get_array_size(
446 array: *const YlongJson,
447 size: *mut c_int,
448 ) -> c_int {
449 if array.is_null() || size.is_null() {
450 return FAILURE;
451 }
452
453 let array = &*(array as *mut JsonValue);
454 let array = match array.try_as_array() {
455 Ok(a) => a,
456 Err(_) => return FAILURE,
457 };
458
459 *size = array.len() as c_int;
460 SUCCESS
461 }
462
463 /// Gets a `YlongJson` item from an array by index.
464 /// Returns null `YlongJson` if the array is null, the item doesn't exist, or any error occurs.
465 #[no_mangle]
ylong_json_get_array_item( array: *const YlongJson, index: c_int, ) -> *mut YlongJson466 pub unsafe extern "C" fn ylong_json_get_array_item(
467 array: *const YlongJson,
468 index: c_int,
469 ) -> *mut YlongJson {
470 if array.is_null() {
471 return NULL_MUT_YLONG_JSON;
472 }
473
474 let array_ref = &mut *(array as *mut JsonValue);
475 let array_ref = match array_ref.try_as_mut_array() {
476 Ok(a) => a,
477 Err(_) => return NULL_MUT_YLONG_JSON,
478 };
479
480 if index as usize >= array_ref.len() {
481 return NULL_MUT_YLONG_JSON;
482 }
483
484 array_ref.get_mut(index as usize).unwrap() as *mut JsonValue as *mut YlongJson
485 }
486
487 /// Adds a `YlongJson` item to an array.
488 /// Returns `FAILURE` if the array or the item is null, and `SUCCESS` otherwise.
489 #[no_mangle]
ylong_json_add_item_to_array( array: *mut YlongJson, item: *mut YlongJson, ) -> c_int490 pub unsafe extern "C" fn ylong_json_add_item_to_array(
491 array: *mut YlongJson,
492 item: *mut YlongJson,
493 ) -> c_int {
494 if array.is_null() || item.is_null() {
495 return FAILURE;
496 }
497
498 let array_ref = &mut *(array as *mut JsonValue);
499 let array_ref = match array_ref.try_as_mut_array() {
500 Ok(a) => a,
501 Err(_) => return FAILURE,
502 };
503
504 let value = Box::from_raw(item as *mut JsonValue);
505 array_ref.push(*value);
506
507 SUCCESS
508 }
509
510 /// Replaces a `YlongJson` item in an array by index with a new item.
511 /// Returns `FAILURE` if the array or the new item is null, the index is out of bounds, or any error occurs, and `SUCCESS` otherwise.
512 #[no_mangle]
ylong_json_replace_array_item_by_index( array: *mut YlongJson, index: c_int, new_item: *mut YlongJson, ) -> c_int513 pub unsafe extern "C" fn ylong_json_replace_array_item_by_index(
514 array: *mut YlongJson,
515 index: c_int,
516 new_item: *mut YlongJson,
517 ) -> c_int {
518 if array.is_null() || new_item.is_null() {
519 return FAILURE;
520 }
521
522 let array_ref = &mut *(array as *mut JsonValue);
523 let array_ref = match array_ref.try_as_mut_array() {
524 Ok(o) => o,
525 Err(_) => return FAILURE,
526 };
527
528 if let Some(value) = array_ref.get_mut(index as usize) {
529 let new_value = Box::from_raw(new_item as *mut JsonValue);
530
531 *value = *new_value;
532
533 return SUCCESS;
534 }
535 FAILURE
536 }
537
538 /// Removes a `YlongJson` item from an array by index.
539 /// Returns null `YlongJson` if the array is null, the item doesn't exist, or any error occurs.
540 #[no_mangle]
ylong_json_remove_array_item_by_index( array: *mut YlongJson, index: c_int, ) -> *mut YlongJson541 pub unsafe extern "C" fn ylong_json_remove_array_item_by_index(
542 array: *mut YlongJson,
543 index: c_int,
544 ) -> *mut YlongJson {
545 if array.is_null() {
546 return NULL_MUT_YLONG_JSON;
547 }
548
549 let array = &mut *(array as *mut JsonValue);
550 let array = match array.try_as_mut_array() {
551 Ok(a) => a,
552 Err(_) => return NULL_MUT_YLONG_JSON,
553 };
554
555 // Uses method 'remove' of Array, but not the method 'remove' of underlying data structure.
556 if let Some(v) = Array::remove(array, index as usize) {
557 return Box::into_raw(Box::new(v)) as *mut YlongJson;
558 }
559 NULL_MUT_YLONG_JSON
560 }
561
562 /// Deletes a `YlongJson` item from an array by index.
563 #[no_mangle]
ylong_json_delete_array_item_by_index( array: *mut YlongJson, index: c_int, )564 pub unsafe extern "C" fn ylong_json_delete_array_item_by_index(
565 array: *mut YlongJson,
566 index: c_int,
567 ) {
568 if array.is_null() {
569 return;
570 }
571
572 let array = &mut *(array as *mut JsonValue);
573 let array = match array.try_as_mut_array() {
574 Ok(a) => a,
575 Err(_) => return,
576 };
577 array.remove(index as usize);
578 }
579
580 /// In list_array mode, it is more efficient to get a node through this method and then delete it.
581 #[cfg(feature = "list_array")]
582 #[no_mangle]
ylong_json_get_array_node( array: *mut YlongJson, index: c_int, ) -> *mut YlongJson583 pub unsafe extern "C" fn ylong_json_get_array_node(
584 array: *mut YlongJson,
585 index: c_int,
586 ) -> *mut YlongJson {
587 if array.is_null() {
588 return NULL_MUT_YLONG_JSON;
589 }
590
591 let array_ref = &mut *(array as *mut JsonValue);
592 let array_ref = match array_ref.try_as_mut_array() {
593 Ok(a) => a,
594 Err(_) => return NULL_MUT_YLONG_JSON,
595 };
596
597 if index as usize >= array_ref.len() {
598 return NULL_MUT_YLONG_JSON;
599 }
600
601 let node = array_ref.get_node_mut(index as usize).unwrap();
602 node as *mut Node<JsonValue> as *mut YlongJson
603 }
604
605 /// Retrieves a `YlongJson` item from an array node.
606 #[cfg(feature = "list_array")]
607 #[no_mangle]
ylong_json_get_item_from_array_node( array_node: *mut YlongJson, ) -> *mut YlongJson608 pub unsafe extern "C" fn ylong_json_get_item_from_array_node(
609 array_node: *mut YlongJson,
610 ) -> *mut YlongJson {
611 if array_node.is_null() {
612 return NULL_MUT_YLONG_JSON;
613 }
614 let node = &mut *(array_node as *mut Node<JsonValue>);
615 node.get_element_mut() as *mut JsonValue as *mut YlongJson
616 }
617
618 /// Adds a `YlongJson` item to an array, then returns the node.
619 /// Returns null `YlongJson` if the array or the item is null.
620 #[cfg(feature = "list_array")]
621 #[no_mangle]
ylong_json_add_item_to_array_then_get_node( array: *mut YlongJson, item: *mut YlongJson, ) -> *mut YlongJson622 pub unsafe extern "C" fn ylong_json_add_item_to_array_then_get_node(
623 array: *mut YlongJson,
624 item: *mut YlongJson,
625 ) -> *mut YlongJson {
626 if array.is_null() || item.is_null() {
627 return NULL_MUT_YLONG_JSON;
628 }
629
630 let array_ref = &mut *(array as *mut JsonValue);
631 let array_ref = match array_ref.try_as_mut_array() {
632 Ok(a) => a,
633 Err(_) => return NULL_MUT_YLONG_JSON,
634 };
635
636 let value = Box::from_raw(item as *mut JsonValue);
637 array_ref.push(*value);
638
639 array_ref.last_node_mut().unwrap() as *mut Node<JsonValue> as *mut YlongJson
640 }
641
642 /// Replaces an item of an array node with a new item.
643 /// Returns `FAILURE` if the array node or the new item is null, and `SUCCESS` otherwise.
644 #[cfg(feature = "list_array")]
645 #[no_mangle]
ylong_json_replace_item_of_array_node( array_node: *mut YlongJson, new_item: *mut YlongJson, ) -> c_int646 pub unsafe extern "C" fn ylong_json_replace_item_of_array_node(
647 array_node: *mut YlongJson,
648 new_item: *mut YlongJson,
649 ) -> c_int {
650 if array_node.is_null() || new_item.is_null() {
651 return FAILURE;
652 }
653
654 let node = &mut *(array_node as *mut Node<JsonValue>);
655 let value = node.get_element_mut();
656
657 let new_value = Box::from_raw(new_item as *mut JsonValue);
658 *value = *new_value;
659 SUCCESS
660 }
661
662 /// Removes an array node.
663 #[cfg(feature = "list_array")]
664 #[no_mangle]
ylong_json_remove_array_node( array_node: *mut YlongJson, ) -> *mut YlongJson665 pub unsafe extern "C" fn ylong_json_remove_array_node(
666 array_node: *mut YlongJson,
667 ) -> *mut YlongJson {
668 if array_node.is_null() {
669 return NULL_MUT_YLONG_JSON;
670 }
671
672 let node = &mut *(array_node as *mut Node<JsonValue>);
673 Box::into_raw(Box::new(node.remove_self().unwrap())) as *mut YlongJson
674 }
675
676 /// Deletes an array node.
677 #[cfg(feature = "list_array")]
678 #[no_mangle]
ylong_json_delete_array_node(array_node: *mut YlongJson)679 pub unsafe extern "C" fn ylong_json_delete_array_node(array_node: *mut YlongJson) {
680 if array_node.is_null() {
681 return;
682 }
683
684 let node = &mut *(array_node as *mut Node<JsonValue>);
685 let _ = node.remove_self();
686 }
687
688 /// Creates a `YlongJson` object.
689 #[no_mangle]
ylong_json_create_object() -> *mut YlongJson690 pub unsafe extern "C" fn ylong_json_create_object() -> *mut YlongJson {
691 Box::into_raw(Box::from(JsonValue::Object(Object::new()))) as *mut YlongJson
692 }
693
694 /// Checks if the `YlongJson` item is an object.
695 /// Returns `FALSE` if the item is null or not an object, and `TRUE` otherwise.
696 #[no_mangle]
ylong_json_is_object(item: *const YlongJson) -> c_int697 pub unsafe extern "C" fn ylong_json_is_object(item: *const YlongJson) -> c_int {
698 if item.is_null() {
699 return FALSE;
700 }
701
702 let item = &*(item as *mut JsonValue);
703 item.is_object() as c_int
704 }
705
706 /// Gets the size of a `YlongJson` object.
707 /// If the `YlongJson` object or the size is null, it returns `FAILURE`.
708 #[no_mangle]
ylong_json_get_object_size( object: *mut YlongJson, size: *mut c_int, ) -> c_int709 pub unsafe extern "C" fn ylong_json_get_object_size(
710 object: *mut YlongJson,
711 size: *mut c_int,
712 ) -> c_int {
713 if object.is_null() || size.is_null() {
714 return FAILURE;
715 }
716
717 let object = &mut *(object as *mut JsonValue);
718 let object = match object.try_as_mut_object() {
719 Ok(o) => o,
720 Err(_) => return FAILURE,
721 };
722
723 *size = object.len() as c_int;
724 SUCCESS
725 }
726
727 /// Checks if a JSON object has a specific item.
728 /// Returns a `c_int` indicating whether the item exists (TRUE) or not (FALSE).
729 #[no_mangle]
ylong_json_has_object_item( object: *mut YlongJson, string: *const c_char, ) -> c_int730 pub unsafe extern "C" fn ylong_json_has_object_item(
731 object: *mut YlongJson,
732 string: *const c_char,
733 ) -> c_int {
734 if object.is_null() || string.is_null() {
735 return FALSE;
736 }
737
738 let object = &*(object as *mut JsonValue);
739 let object = match object.try_as_object() {
740 Ok(o) => o,
741 Err(_) => return FALSE,
742 };
743
744 // Using `ptr::slice_from_raw_parts` here dramatically
745 // reduces the cost of converting between char* and &[u8].
746 // Then use `from_utf8_unchecked` to further reduce cost.
747 let len = strlen(string);
748 let slice = &*slice_from_raw_parts(string as *mut u8, len);
749 let str = from_utf8_unchecked(slice);
750
751 object.contains_key(str) as c_int
752 }
753
754 /// Retrieves an item from a JSON object by key.
755 /// Returns a mutable pointer to the retrieved JSON item.
756 #[no_mangle]
ylong_json_get_object_item( object: *const YlongJson, string: *const c_char, ) -> *mut YlongJson757 pub unsafe extern "C" fn ylong_json_get_object_item(
758 object: *const YlongJson,
759 string: *const c_char,
760 ) -> *mut YlongJson {
761 // If object is empty, the search fails.
762 if object.is_null() || string.is_null() {
763 return NULL_MUT_YLONG_JSON;
764 }
765
766 let object_ref = &mut *(object as *mut JsonValue);
767
768 // If the type is not object, return err.
769 let object_ref = match object_ref.try_as_mut_object() {
770 Ok(o) => o,
771 Err(_) => return NULL_MUT_YLONG_JSON,
772 };
773
774 // Using `ptr::slice_from_raw_parts` here dramatically
775 // reduces the cost of converting between char* and &[u8].
776 // Then use `from_utf8_unchecked` to further reduce cost.
777 let len = strlen(string);
778 let slice = &*slice_from_raw_parts(string as *mut u8, len);
779 let index = from_utf8_unchecked(slice);
780
781 let target = match object_ref.get_mut(index) {
782 Some(v) => v,
783 None => return NULL_MUT_YLONG_JSON,
784 };
785 target as *mut JsonValue as *mut YlongJson
786 }
787
788 /// Adds an item to a JSON object.
789 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
790 #[no_mangle]
ylong_json_add_item_to_object( object: *mut YlongJson, string: *const c_char, item: *mut YlongJson, ) -> c_int791 pub unsafe extern "C" fn ylong_json_add_item_to_object(
792 object: *mut YlongJson,
793 string: *const c_char,
794 item: *mut YlongJson,
795 ) -> c_int {
796 // If object or string or item is empty, returns FAILED.
797 if object.is_null() || string.is_null() || item.is_null() {
798 return FAILURE;
799 }
800
801 let object_ref = &mut *(object as *mut JsonValue);
802 let object_ref = match object_ref.try_as_mut_object() {
803 Ok(o) => o,
804 Err(_) => return FAILURE,
805 };
806
807 // Using `ptr::slice_from_raw_parts` here dramatically
808 // reduces the cost of converting between char* and &[u8].
809 // Then use `from_utf8_unchecked` to further reduce cost.
810 let len = strlen(string);
811 let slice = &*slice_from_raw_parts(string as *mut u8, len);
812 let index = from_utf8_unchecked(slice);
813
814 let value = Box::from_raw(item as *mut JsonValue);
815
816 object_ref.insert(String::from(index), *value);
817
818 SUCCESS
819 }
820
821 /// Replaces an item in a JSON object by key.
822 /// Returns a `c_int` indicating whether the operation was successful (SUCCESS) or failed (FAILURE).
823 #[no_mangle]
ylong_json_replace_object_item_by_index( object: *mut YlongJson, index: *const c_char, new_item: *mut YlongJson, ) -> c_int824 pub unsafe extern "C" fn ylong_json_replace_object_item_by_index(
825 object: *mut YlongJson,
826 index: *const c_char,
827 new_item: *mut YlongJson,
828 ) -> c_int {
829 if object.is_null() || index.is_null() || new_item.is_null() {
830 return FAILURE;
831 }
832
833 let object_ref = &mut *(object as *mut JsonValue);
834 let object_ref = match object_ref.try_as_mut_object() {
835 Ok(o) => o,
836 Err(_) => return FAILURE,
837 };
838
839 // Using `ptr::slice_from_raw_parts` here dramatically
840 // reduces the cost of converting between char* and &[u8].
841 // Then use `from_utf8_unchecked` to further reduce cost.
842 let len = strlen(index);
843 let slice = &*slice_from_raw_parts(index as *mut u8, len);
844 let index = from_utf8_unchecked(slice);
845
846 if let Some(value) = object_ref.get_mut(index) {
847 let new_value = Box::from_raw(new_item as *mut JsonValue);
848
849 *value = *new_value;
850
851 return SUCCESS;
852 }
853
854 FAILURE
855 }
856
857 /// Removes an item in a JSON object by index.
858 /// Returns a new JSON object without the item if successful, NULL_MUT_YLONG_JSON otherwise.
859 #[no_mangle]
ylong_json_remove_object_item_by_index( object: *mut YlongJson, index: *const c_char, ) -> *mut YlongJson860 pub unsafe extern "C" fn ylong_json_remove_object_item_by_index(
861 object: *mut YlongJson,
862 index: *const c_char,
863 ) -> *mut YlongJson {
864 if object.is_null() || index.is_null() {
865 return NULL_MUT_YLONG_JSON;
866 }
867
868 let object = &mut *(object as *mut JsonValue);
869
870 // Using `ptr::slice_from_raw_parts` here dramatically
871 // reduces the cost of converting between char* and &[u8].
872 // Then use `from_utf8_unchecked` to further reduce cost.
873 let len = strlen(index);
874 let slice = &*slice_from_raw_parts(index as *mut u8, len);
875 let index = from_utf8_unchecked(slice);
876
877 if let Some(v) = object.remove(index) {
878 return Box::into_raw(Box::new(v)) as *mut YlongJson;
879 }
880 NULL_MUT_YLONG_JSON
881 }
882
883 /// Deletes an item in a JSON object by index.
884 /// Does not return a value.
885 #[no_mangle]
ylong_json_delete_object_item_by_index( object: *mut YlongJson, index: *const c_char, )886 pub unsafe extern "C" fn ylong_json_delete_object_item_by_index(
887 object: *mut YlongJson,
888 index: *const c_char,
889 ) {
890 if object.is_null() || index.is_null() {
891 return;
892 }
893
894 let object = &mut *(object as *mut JsonValue);
895
896 // Using ptr::slice_from_raw_parts here dramatically
897 // reduces the cost of converting between char* and &[u8].
898 // Then use from_utf8_unchecked to further reduce cost.
899 let len = strlen(index);
900 let slice = &*slice_from_raw_parts(index as *mut u8, len);
901 let index = from_utf8_unchecked(slice);
902
903 object.remove(index);
904 }
905
906 /// Gets all items from a JSON object.
907 /// Returns SUCCESS if the operation is successful, FAILURE otherwise.
908 #[no_mangle]
ylong_json_get_all_object_items( object: *mut YlongJson, key: *mut *mut c_char, value: *mut *mut YlongJson, len: *mut c_int, ) -> c_int909 pub unsafe extern "C" fn ylong_json_get_all_object_items(
910 object: *mut YlongJson,
911 key: *mut *mut c_char,
912 value: *mut *mut YlongJson,
913 len: *mut c_int,
914 ) -> c_int {
915 if object.is_null() || key.is_null() || value.is_null() || len.is_null() {
916 return FAILURE;
917 }
918
919 let object = &mut *(object as *mut JsonValue);
920 let object = match object.try_as_mut_object() {
921 Ok(o) => o,
922 Err(_) => return FAILURE,
923 };
924
925 for (n, (k, v)) in object.iter_mut().enumerate() {
926 // k.clone ().into_bytes() is more efficient than k.as_bytes ().to_vec().
927 let k = CString::from_vec_unchecked(k.clone().into_bytes()).into_raw();
928 let v = v as *mut JsonValue as *mut YlongJson;
929 *(key.add(n)) = k;
930 *(value.add(n)) = v;
931 }
932 *len = object.len() as c_int;
933 SUCCESS
934 }
935
936 /// Applies a function to each item in a JSON object.
937 /// Returns SUCCESS if the operation is successful, FAILURE otherwise.
938 #[no_mangle]
ylong_json_for_each_object_item( object: *mut YlongJson, func: unsafe extern "C" fn(*mut YlongJson), ) -> c_int939 pub unsafe extern "C" fn ylong_json_for_each_object_item(
940 object: *mut YlongJson,
941 func: unsafe extern "C" fn(*mut YlongJson),
942 ) -> c_int {
943 if object.is_null() {
944 return FAILURE;
945 }
946
947 let object = &mut *(object as *mut JsonValue);
948 let object = match object.try_as_mut_object() {
949 Ok(o) => o,
950 Err(_) => return FAILURE,
951 };
952
953 object.iter_mut().for_each(|(_k, v)| {
954 let value = v as *mut JsonValue as *mut YlongJson;
955 func(value);
956 });
957 SUCCESS
958 }
959
960 /// Gets an object node from a JSON object by key.
961 /// Returns a pointer to the object node if successful, NULL_MUT_YLONG_JSON otherwise.
962 #[cfg(feature = "list_object")]
963 #[no_mangle]
ylong_json_get_object_node( object: *const YlongJson, string: *const c_char, ) -> *mut YlongJson964 pub unsafe extern "C" fn ylong_json_get_object_node(
965 object: *const YlongJson,
966 string: *const c_char,
967 ) -> *mut YlongJson {
968 // If object is empty, the search fails.
969 if object.is_null() || string.is_null() {
970 return NULL_MUT_YLONG_JSON;
971 }
972
973 let object_ref = &mut *(object as *mut JsonValue);
974
975 // If the type is not object, returns err.
976 let object_ref = match object_ref.try_as_mut_object() {
977 Ok(o) => o,
978 Err(_) => return NULL_MUT_YLONG_JSON,
979 };
980
981 // Using `ptr::slice_from_raw_parts` here dramatically
982 // reduces the cost of converting between char* and &[u8].
983 // Then use `from_utf8_unchecked` to further reduce cost.
984 let len = strlen(string);
985 let slice = &*slice_from_raw_parts(string as *mut u8, len);
986 let index = from_utf8_unchecked(slice);
987
988 // When using list to get a node, the return value points to the memory is CursorMut<JsonValue>.
989 let target = match object_ref.get_node_mut(index) {
990 Some(v) => v,
991 None => return NULL_MUT_YLONG_JSON,
992 };
993 target as *mut Node<(String, JsonValue)> as *mut YlongJson
994 }
995
996 /// Gets an item from an object node.
997 /// Returns a pointer to the item if successful, NULL_MUT_YLONG_JSON otherwise.
998 #[cfg(feature = "list_object")]
999 #[no_mangle]
ylong_json_get_item_from_object_node( object_node: *mut YlongJson, ) -> *mut YlongJson1000 pub unsafe extern "C" fn ylong_json_get_item_from_object_node(
1001 object_node: *mut YlongJson,
1002 ) -> *mut YlongJson {
1003 if object_node.is_null() {
1004 return NULL_MUT_YLONG_JSON;
1005 }
1006
1007 let node = &mut *(object_node as *mut Node<(String, JsonValue)>);
1008 (&mut node.get_element_mut().1) as *mut JsonValue as *mut YlongJson
1009 }
1010
1011 /// Adds an item to a JSON object, then returns a pointer to the object node.
1012 /// Returns a pointer to the object node if successful, NULL_MUT_YLONG_JSON otherwise.
1013 #[cfg(feature = "list_object")]
1014 #[no_mangle]
ylong_json_add_item_to_object_then_get_node( object: *mut YlongJson, string: *const c_char, item: *mut YlongJson, ) -> *mut YlongJson1015 pub unsafe extern "C" fn ylong_json_add_item_to_object_then_get_node(
1016 object: *mut YlongJson,
1017 string: *const c_char,
1018 item: *mut YlongJson,
1019 ) -> *mut YlongJson {
1020 // If object or item is empty, returns NULL_MUT_YLONG_JSON.
1021 if object.is_null() || string.is_null() || item.is_null() {
1022 return NULL_MUT_YLONG_JSON;
1023 }
1024
1025 let object_ref = &mut *(object as *mut JsonValue);
1026 let object_ref = match object_ref.try_as_mut_object() {
1027 Ok(v) => v,
1028 Err(_) => return NULL_MUT_YLONG_JSON,
1029 };
1030
1031 // Using `ptr::slice_from_raw_parts` here dramatically
1032 // reduces the cost of converting between char* and &[u8].
1033 // Then use `from_utf8_unchecked` to further reduce cost.
1034 let len = strlen(string);
1035 let slice = &*slice_from_raw_parts(string as *mut u8, len);
1036 let string = from_utf8_unchecked(slice);
1037
1038 let value = Box::from_raw(item as *mut JsonValue);
1039 object_ref.insert(String::from(string), *value);
1040
1041 let target = object_ref.last_node_mut().unwrap();
1042 target as *mut Node<(String, JsonValue)> as *mut YlongJson
1043 }
1044
1045 /// Replaces an item in an object node.
1046 /// Returns SUCCESS if the operation is successful, FAILURE otherwise.
1047 #[cfg(feature = "list_object")]
1048 #[no_mangle]
ylong_json_replace_item_of_object_node( object_node: *mut YlongJson, new_item: *mut YlongJson, ) -> c_int1049 pub unsafe extern "C" fn ylong_json_replace_item_of_object_node(
1050 object_node: *mut YlongJson,
1051 new_item: *mut YlongJson,
1052 ) -> c_int {
1053 if object_node.is_null() || new_item.is_null() {
1054 return FAILURE;
1055 }
1056
1057 let node = &mut *(object_node as *mut Node<(String, JsonValue)>);
1058 let (_, value) = node.get_element_mut();
1059 let new_value = Box::from_raw(new_item as *mut JsonValue);
1060 *value = *new_value;
1061
1062 SUCCESS
1063 }
1064
1065 /// Removes an object node.
1066 /// Returns a pointer to the removed item if successful, NULL_MUT_YLONG_JSON otherwise.
1067 #[cfg(feature = "list_object")]
1068 #[no_mangle]
ylong_json_remove_object_node( object_node: *mut YlongJson, ) -> *mut YlongJson1069 pub unsafe extern "C" fn ylong_json_remove_object_node(
1070 object_node: *mut YlongJson,
1071 ) -> *mut YlongJson {
1072 if object_node.is_null() {
1073 return NULL_MUT_YLONG_JSON;
1074 }
1075
1076 let node = &mut *(object_node as *mut Node<(String, JsonValue)>);
1077 Box::into_raw(Box::new(node.remove_self().unwrap().1)) as *mut YlongJson
1078 }
1079
1080 /// Deletes a node from a JSON object.
1081 #[cfg(feature = "list_object")]
1082 #[no_mangle]
ylong_json_delete_object_node(object_node: *mut YlongJson)1083 pub unsafe extern "C" fn ylong_json_delete_object_node(object_node: *mut YlongJson) {
1084 if object_node.is_null() {
1085 return;
1086 }
1087
1088 let node = &mut *(object_node as *mut Node<(String, JsonValue)>);
1089 let _ = node.remove_self();
1090 }
1091
1092 #[cfg(test)]
1093 mod ut_adapter {
1094 use crate::*;
1095 use libc::*;
1096 use std::ffi::{CStr, CString};
1097 use std::mem::size_of;
1098 use std::ptr::{null, null_mut};
1099
1100 const JSON_TEXT: &str = r#"
1101 {
1102 "null": null,
1103 "true": true,
1104 "false": false,
1105 "number": 3.14,
1106 "string": "Hello World!",
1107 "array": [1, 2, 3],
1108 "object": {
1109 "key1": 1,
1110 "key2": 2,
1111 "key3": 3
1112 }
1113 }
1114 "#;
1115
str_to_c_char(str: &str) -> *mut c_char1116 unsafe fn str_to_c_char(str: &str) -> *mut c_char {
1117 CString::from_vec_unchecked(str.as_bytes().to_vec()).into_raw()
1118 }
1119
1120 /// UT test for `ylong_json_parse`.
1121 ///
1122 /// # Title
1123 /// ut_ylong_json_parse
1124 ///
1125 /// # Brief
1126 /// 1. Calls `ylong_json_parse` to generate a JsonValue as YlongJson*.
1127 /// 2. Checks if the test results are correct.
1128 #[test]
ut_ylong_json_parse()1129 fn ut_ylong_json_parse() {
1130 unsafe {
1131 // Passes in the correct syntax text string.
1132 let str = str_to_c_char(JSON_TEXT);
1133 let err = null_mut::<c_char>();
1134 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1135 // No error message.
1136 assert!(err.is_null());
1137 // The data structure is correct.
1138 assert!(!json.is_null());
1139
1140 // Destruction
1141 let _ = Box::from_raw(str);
1142 ylong_json_delete(json);
1143
1144 // Passes in the incorrect syntax text string.
1145 let str = str_to_c_char("{");
1146 let err = null_mut::<c_char>();
1147 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1148 // Here is an error message.
1149 assert!(!err.is_null());
1150 // No correct syntax structure.
1151 assert!(json.is_null());
1152
1153 // Destruction
1154 ylong_json_free_string(err);
1155 let _ = Box::from_raw(str);
1156 ylong_json_delete(json);
1157 }
1158 }
1159
1160 //noinspection SpellCheckingInspection
1161 //noinspection ALL
1162 /// UT test for `ylong_json_free_string`.
1163 ///
1164 /// # Title
1165 /// ut_ylong_json_free_string
1166 ///
1167 /// # Brief
1168 /// 1. Calls `ylong_json_free_string` to free a YlongJson*(`C` string).
1169 /// 2. Checks if the test results are correct.
1170 #[test]
ut_ylong_json_free_string()1171 fn ut_ylong_json_free_string() {
1172 unsafe {
1173 // Null ptr scene, if the process does not exit abnormally, it is successful.
1174 let string = null_mut();
1175 ylong_json_free_string(string);
1176
1177 let str = str_to_c_char(JSON_TEXT);
1178 let err = null_mut::<c_char>();
1179 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1180 assert!(err.is_null());
1181 assert!(!json.is_null());
1182
1183 // The char* generated by `ylong_json_print_unformatted` needs
1184 // to be destructed by calling `ylong_json_free_string`.
1185 let result = ylong_json_print_unformatted(json);
1186 ylong_json_free_string(result);
1187
1188 // Destruction
1189 let _ = Box::from_raw(str);
1190 ylong_json_delete(json);
1191 }
1192 }
1193
1194 /// UT test for `ylong_json_print_unformatted`.
1195 ///
1196 /// # Title
1197 /// ut_ylong_json_print_unformatted
1198 ///
1199 /// # Brief
1200 /// 1. Calls `ylong_json_print_unformatted` to print the value as `C` string.
1201 /// 2. Checks if the test results are correct.
1202 #[test]
ut_ylong_json_print_unformatted()1203 fn ut_ylong_json_print_unformatted() {
1204 unsafe {
1205 // Null ptr
1206 let json = null_mut();
1207 assert!(ylong_json_print_unformatted(json).is_null());
1208
1209 // Correct scene
1210 let str = str_to_c_char("{\"array\":[1,2,3]}");
1211 let err = null_mut::<c_char>();
1212 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1213 assert!(err.is_null());
1214 assert!(!json.is_null());
1215
1216 let result = ylong_json_print_unformatted(json);
1217 let result = CString::from_raw(result).into_string().unwrap();
1218 assert_eq!(result, "{\"array\":[1,2,3]}");
1219
1220 // Destruction
1221 let _ = Box::from_raw(str);
1222 ylong_json_delete(json);
1223 }
1224 }
1225
1226 /// UT test for `ylong_json_delete`.
1227 ///
1228 /// # Title
1229 /// ut_ylong_json_delete
1230 ///
1231 /// # Brief
1232 /// 1. Calls `ylong_json_delete` to delete the value.
1233 /// 2. Checks if the test results are correct.
1234 #[test]
ut_ylong_json_delete()1235 fn ut_ylong_json_delete() {
1236 unsafe {
1237 // Null ptr scene, if the process does not exit abnormally, it is successful.
1238 let json = null_mut();
1239 ylong_json_delete(json);
1240
1241 // The YlongJson* generated by `ylong_json_parse` needs
1242 // to be destructed by calling `ylong_json_delete`.
1243 let str = str_to_c_char(JSON_TEXT);
1244 let err = null_mut::<c_char>();
1245 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1246 assert!(err.is_null());
1247 assert!(!json.is_null());
1248 let _ = Box::from_raw(str);
1249 ylong_json_delete(json);
1250
1251 // If the YlongJson* generated by the function starting with
1252 // `ylong_json_create` is not inserted into another YlongJson*,
1253 // YlongJson* needs to be destructed by calling `ylong_json_delete`.
1254 let null = ylong_json_create_null();
1255 ylong_json_delete(null);
1256 }
1257 }
1258
1259 /// UT test for `ylong_json_duplicate`.
1260 ///
1261 /// # Title
1262 /// ut_ylong_json_duplicate
1263 ///
1264 /// # Brief
1265 /// 1. Calls `ylong_json_duplicate` to clone the value.
1266 /// 2. Checks if the test results are correct.
1267 #[test]
ut_ylong_json_duplicate()1268 fn ut_ylong_json_duplicate() {
1269 unsafe {
1270 // Null ptr
1271 let json = null_mut();
1272 assert!(ylong_json_duplicate(json, 0).is_null());
1273
1274 // Null ptr
1275 let json = null_mut();
1276 assert!(ylong_json_duplicate(json, 1).is_null());
1277
1278 let str = str_to_c_char(JSON_TEXT);
1279 let err = null_mut::<c_char>();
1280 let json = ylong_json_parse(str, &err as *const *mut c_char as *mut *mut c_char);
1281 assert!(err.is_null());
1282 assert!(!json.is_null());
1283
1284 // If recurse is 0, does not clone recursively.
1285 let duplicate = ylong_json_duplicate(json, 0);
1286 let result = ylong_json_print_unformatted(duplicate);
1287 let result = CString::from_raw(result).into_string().unwrap();
1288 assert_eq!(result, "{}");
1289 // Destruction
1290 let _ = Box::from_raw(str);
1291 ylong_json_delete(duplicate);
1292
1293 // If recurse is not 0, do recursive cloning.
1294 let duplicate = ylong_json_duplicate(json, 1);
1295 let result = ylong_json_print_unformatted(duplicate);
1296 let result = CString::from_raw(result).into_string().unwrap();
1297 let origin = ylong_json_print_unformatted(json);
1298 let origin = CString::from_raw(origin).into_string().unwrap();
1299 // The json address value is not equal to duplicate,
1300 // which means it is a different instance.
1301 assert_ne!(duplicate, json);
1302 // But the output is the same.
1303 assert_eq!(result, origin);
1304 // Destruction
1305 ylong_json_delete(duplicate);
1306 ylong_json_delete(json);
1307 }
1308 }
1309
1310 /// UT test for `ylong_json_create_null`.
1311 ///
1312 /// # Title
1313 /// ut_ylong_json_create_null
1314 ///
1315 /// # Brief
1316 /// 1. Calls `ylong_json_create_null` to create a null.
1317 /// 2. Checks if the test results are correct.
1318 #[test]
ut_ylong_json_create_null()1319 fn ut_ylong_json_create_null() {
1320 unsafe {
1321 let null = ylong_json_create_null();
1322 assert_eq!(ylong_json_is_null(null), 1);
1323 ylong_json_delete(null);
1324 }
1325 }
1326
1327 /// UT test for `ylong_json_is_null`.
1328 ///
1329 /// # Title
1330 /// ut_ylong_json_is_null
1331 ///
1332 /// # Brief
1333 /// 1. Calls `ylong_json_is_null` to determine whether the underlying structure is null.
1334 /// 2. Checks if the test results are correct.
1335 #[test]
ut_ylong_json_is_null()1336 fn ut_ylong_json_is_null() {
1337 unsafe {
1338 // Null ptr
1339 let null = null_mut();
1340 assert_eq!(ylong_json_is_null(null), 0);
1341
1342 // If the underlying structure is Null, returns true.
1343 let null = ylong_json_create_null();
1344 assert_eq!(ylong_json_is_null(null), 1);
1345 ylong_json_delete(null);
1346
1347 // Else returns false.
1348 let bool = ylong_json_create_bool(0xffff);
1349 assert_eq!(ylong_json_is_null(bool), 0);
1350 ylong_json_delete(bool);
1351 }
1352 }
1353
1354 /// UT test for `ylong_json_create_bool`.
1355 ///
1356 /// # Title
1357 /// ut_ylong_json_create_bool
1358 ///
1359 /// # Brief
1360 /// 1. Calls `ylong_json_create_bool` to create a bool.
1361 /// 2. Checks if the test results are correct.
1362 #[test]
ut_ylong_json_create_bool()1363 fn ut_ylong_json_create_bool() {
1364 unsafe {
1365 // Creates true.
1366 let bool = ylong_json_create_bool(0xffff);
1367 let mut val = 0;
1368 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int);
1369 assert_eq!(val, 1);
1370 ylong_json_delete(bool);
1371
1372 // Creates false.
1373 let bool = ylong_json_create_bool(0);
1374 let mut val = 1;
1375 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int);
1376 assert_eq!(val, 0);
1377 ylong_json_delete(bool);
1378 }
1379 }
1380
1381 /// UT test for `ylong_json_is_bool`.
1382 ///
1383 /// # Title
1384 /// ut_ylong_json_is_bool
1385 ///
1386 /// # Brief
1387 /// 1. Calls `ylong_json_is_bool` to determine whether the underlying structure is bool.
1388 /// 2. Checks if the test results are correct.
1389 #[test]
ut_ylong_json_is_bool()1390 fn ut_ylong_json_is_bool() {
1391 unsafe {
1392 // Null ptr
1393 let bool = null_mut();
1394 assert_eq!(ylong_json_is_bool(bool), 0);
1395
1396 // True
1397 let bool = ylong_json_create_bool(0xffff);
1398 assert_eq!(ylong_json_is_bool(bool), 1);
1399 ylong_json_delete(bool);
1400
1401 // False
1402 let bool = ylong_json_create_bool(0);
1403 assert_eq!(ylong_json_is_bool(bool), 1);
1404 ylong_json_delete(bool);
1405
1406 // Non-bool case
1407 let null = ylong_json_create_null();
1408 assert_eq!(ylong_json_is_bool(null), 0);
1409 ylong_json_delete(null);
1410 }
1411 }
1412
1413 /// UT test for `ylong_json_get_value_from_bool`.
1414 ///
1415 /// # Title
1416 /// ut_ylong_json_get_value_from_bool
1417 ///
1418 /// # Brief
1419 /// 1. Calls `ylong_json_get_value_from_bool` to get value from bool.
1420 /// 2. Checks if the test results are correct.
1421 #[test]
ut_ylong_json_get_value_from_bool()1422 fn ut_ylong_json_get_value_from_bool() {
1423 unsafe {
1424 // Null ptr
1425 let bool = null_mut();
1426 let mut val = 0i32;
1427 assert_eq!(
1428 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int),
1429 0
1430 );
1431
1432 let bool = ylong_json_create_bool(0xffff);
1433 let mut val = 0;
1434 assert_eq!(
1435 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int),
1436 1
1437 );
1438 assert_eq!(val, 1);
1439 ylong_json_delete(bool);
1440
1441 let null = ylong_json_create_null();
1442 let mut val = 0;
1443 assert_eq!(
1444 ylong_json_get_value_from_bool(null, &mut val as *mut c_int),
1445 0
1446 );
1447 ylong_json_delete(null);
1448 }
1449 }
1450
1451 /// UT test for `ylong_json_set_value_to_bool`.
1452 ///
1453 /// # Title
1454 /// ut_ylong_json_set_value_to_bool
1455 ///
1456 /// # Brief
1457 /// 1. Calls `ylong_json_set_value_to_bool` to set value to bool.
1458 /// 2. Checks if the test results are correct.
1459 #[test]
ut_ylong_json_set_value_to_bool()1460 fn ut_ylong_json_set_value_to_bool() {
1461 unsafe {
1462 // Null ptr
1463 let bool = null_mut();
1464 assert_eq!(ylong_json_set_value_to_bool(bool, 1), 0);
1465
1466 let bool = ylong_json_create_bool(0xffff);
1467 let mut val = 0;
1468 assert_eq!(
1469 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int),
1470 1
1471 );
1472 assert_eq!(val, 1);
1473
1474 assert_eq!(ylong_json_set_value_to_bool(bool, 0), 1);
1475 assert_eq!(
1476 ylong_json_get_value_from_bool(bool, &mut val as *mut c_int),
1477 1
1478 );
1479 assert_eq!(val, 0);
1480 ylong_json_delete(bool);
1481
1482 let null = ylong_json_create_null();
1483 assert_eq!(ylong_json_set_value_to_bool(null, 0), 0);
1484 ylong_json_delete(null);
1485 }
1486 }
1487
1488 /// UT test for `ylong_json_create_double_number`.
1489 ///
1490 /// # Title
1491 /// ut_ylong_json_create_double_number
1492 ///
1493 /// # Brief
1494 /// 1. Calls `ylong_json_create_double_number` to create a double number.
1495 /// 2. Checks if the test results are correct.
1496 #[test]
ut_ylong_json_create_double_number()1497 fn ut_ylong_json_create_double_number() {
1498 unsafe {
1499 let double = ylong_json_create_double_number(3.24);
1500 let mut number = 0f64;
1501 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double);
1502 assert_eq!(number, 3.24);
1503 ylong_json_delete(double);
1504 }
1505 }
1506
1507 /// UT test for `ylong_json_create_int_number`.
1508 ///
1509 /// # Title
1510 /// ut_ylong_json_create_int_number
1511 ///
1512 /// # Brief
1513 /// 1. Calls `ylong_json_create_int_number` to create a int number.
1514 /// 2. Checks if the test results are correct.
1515 #[test]
ut_ylong_json_create_int_number()1516 fn ut_ylong_json_create_int_number() {
1517 unsafe {
1518 let int = ylong_json_create_int_number(0xffff);
1519 let mut number = 0i64;
1520 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong);
1521 assert_eq!(number, 0xffff);
1522 ylong_json_delete(int);
1523 }
1524 }
1525
1526 /// UT test for `ylong_json_is_number`.
1527 ///
1528 /// # Title
1529 /// ut_ylong_json_is_number
1530 ///
1531 /// # Brief
1532 /// 1. Calls `ylong_json_is_number` to determine whether the value is number.
1533 /// 2. Checks if the test results are correct.
1534 #[test]
ut_ylong_json_is_number()1535 fn ut_ylong_json_is_number() {
1536 unsafe {
1537 // Null ptr
1538 let number = null_mut();
1539 assert_eq!(ylong_json_is_number(number), 0);
1540
1541 let int = ylong_json_create_int_number(1i64);
1542 assert_eq!(ylong_json_is_number(int), 1);
1543 ylong_json_delete(int);
1544
1545 let double = ylong_json_create_double_number(3.24);
1546 assert_eq!(ylong_json_is_number(double), 1);
1547 ylong_json_delete(double);
1548
1549 let null = ylong_json_create_null();
1550 assert_eq!(ylong_json_is_number(null), 0);
1551 ylong_json_delete(null);
1552 }
1553 }
1554
1555 /// UT test for `ylong_json_is_double_number`.
1556 ///
1557 /// # Title
1558 /// ut_ylong_json_is_double_number
1559 ///
1560 /// # Brief
1561 /// 1. Calls `ylong_json_is_double_number` to determine whether the value is double number.
1562 /// 2. Checks if the test results are correct.
1563 #[test]
ut_ylong_json_is_double_number()1564 fn ut_ylong_json_is_double_number() {
1565 unsafe {
1566 // Null ptr
1567 let double = null_mut();
1568 assert_eq!(ylong_json_is_double_number(double), 0);
1569
1570 let int = ylong_json_create_int_number(1i64);
1571 assert_eq!(ylong_json_is_double_number(int), 0);
1572 ylong_json_delete(int);
1573
1574 let double = ylong_json_create_double_number(3.24);
1575 assert_eq!(ylong_json_is_double_number(double), 1);
1576 ylong_json_delete(double);
1577
1578 let null = ylong_json_create_null();
1579 assert_eq!(ylong_json_is_double_number(null), 0);
1580 ylong_json_delete(null);
1581 }
1582 }
1583
1584 /// UT test for `ylong_json_is_int_number`.
1585 ///
1586 /// # Title
1587 /// ut_ylong_json_is_int_number
1588 ///
1589 /// # Brief
1590 /// 1. Calls `ylong_json_is_int_number` to determine whether the value is int number.
1591 /// 2. Checks if the test results are correct.
1592 #[test]
ut_ylong_json_is_int_number()1593 fn ut_ylong_json_is_int_number() {
1594 unsafe {
1595 // Null ptr
1596 let int = null_mut();
1597 assert_eq!(ylong_json_is_int_number(int), 0);
1598
1599 let int = ylong_json_create_int_number(1i64);
1600 assert_eq!(ylong_json_is_int_number(int), 1);
1601 ylong_json_delete(int);
1602
1603 let double = ylong_json_create_double_number(3.24);
1604 assert_eq!(ylong_json_is_int_number(double), 0);
1605 ylong_json_delete(double);
1606
1607 let null = ylong_json_create_null();
1608 assert_eq!(ylong_json_is_int_number(null), 0);
1609 ylong_json_delete(null);
1610 }
1611 }
1612
1613 /// UT test for `ylong_json_get_double_value_from_number`.
1614 ///
1615 /// # Title
1616 /// ut_ylong_json_get_double_value_from_number
1617 ///
1618 /// # Brief
1619 /// 1. Calls `ylong_json_get_double_value_from_number` to get double value from number.
1620 /// 2. Checks if the test results are correct.
1621 #[test]
ut_ylong_json_get_double_value_from_number()1622 fn ut_ylong_json_get_double_value_from_number() {
1623 unsafe {
1624 // Null ptr
1625 let double = null_mut();
1626 let mut number = 0f64;
1627 assert_eq!(
1628 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double),
1629 0
1630 );
1631
1632 let int = ylong_json_create_int_number(1i64);
1633 let mut number = 0f64;
1634 assert_eq!(
1635 ylong_json_get_double_value_from_number(int, &mut number as *mut c_double),
1636 1
1637 );
1638 assert_eq!(number, 1.0);
1639 ylong_json_delete(int);
1640
1641 let double = ylong_json_create_double_number(3.24);
1642 let mut number = 0f64;
1643 assert_eq!(
1644 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double),
1645 1
1646 );
1647 assert_eq!(number, 3.24);
1648 ylong_json_delete(double);
1649
1650 let null = ylong_json_create_null();
1651 let mut number = 0f64;
1652 assert_eq!(
1653 ylong_json_get_double_value_from_number(null, &mut number as *mut c_double),
1654 0
1655 );
1656 ylong_json_delete(null);
1657 }
1658 }
1659
1660 /// UT test for `ylong_json_get_int_value_from_number`.
1661 ///
1662 /// # Title
1663 /// ut_ylong_json_get_int_value_from_number
1664 ///
1665 /// # Brief
1666 /// 1. Calls `ylong_json_get_int_value_from_number` to get int value from number.
1667 /// 2. Checks if the test results are correct.
1668 #[test]
ut_ylong_json_get_int_value_from_number()1669 fn ut_ylong_json_get_int_value_from_number() {
1670 unsafe {
1671 // Null ptr
1672 let int = null_mut();
1673 let mut number = 0i64;
1674 assert_eq!(
1675 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong),
1676 0
1677 );
1678
1679 let int = ylong_json_create_int_number(1i64);
1680 let mut number = 0i64;
1681 assert_eq!(
1682 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong),
1683 1
1684 );
1685 assert_eq!(number, 1i64);
1686 ylong_json_delete(int);
1687
1688 let double = ylong_json_create_double_number(3.24);
1689 let mut number = 0i64;
1690 assert_eq!(
1691 ylong_json_get_int_value_from_number(double, &mut number as *mut c_longlong),
1692 1
1693 );
1694 assert_eq!(number, 3i64);
1695 ylong_json_delete(double);
1696
1697 let null = ylong_json_create_null();
1698 let mut number = 0i64;
1699 assert_eq!(
1700 ylong_json_get_int_value_from_number(null, &mut number as *mut c_longlong),
1701 0
1702 );
1703 ylong_json_delete(null);
1704 }
1705 }
1706
1707 /// UT test for `ylong_json_set_double_value_to_number`.
1708 ///
1709 /// # Title
1710 /// ut_ylong_json_set_double_value_to_number
1711 ///
1712 /// # Brief
1713 /// 1. Calls `ylong_json_set_double_value_to_number` to set double value to number.
1714 /// 2. Checks if the test results are correct.
1715 #[test]
ut_ylong_json_set_double_value_to_number()1716 fn ut_ylong_json_set_double_value_to_number() {
1717 unsafe {
1718 // Null ptr
1719 let number = null_mut();
1720 assert_eq!(ylong_json_set_double_value_to_number(number, 3.24), 0);
1721
1722 let double = ylong_json_create_double_number(3.24);
1723 let mut number = 0f64;
1724 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double);
1725 assert_eq!(number, 3.24);
1726 assert_eq!(ylong_json_set_double_value_to_number(double, 1.23), 1);
1727 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double);
1728 assert_eq!(number, 1.23);
1729 ylong_json_delete(double);
1730
1731 let int = ylong_json_create_int_number(1i64);
1732 let mut number = 0i64;
1733 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong);
1734 assert_eq!(number, 1i64);
1735 assert_eq!(ylong_json_set_double_value_to_number(int, 3.24), 1);
1736 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong);
1737 assert_eq!(number, 3i64);
1738 ylong_json_delete(int);
1739
1740 let null = ylong_json_create_null();
1741 assert_eq!(ylong_json_set_double_value_to_number(null, 3.24), 0);
1742 ylong_json_delete(null);
1743 }
1744 }
1745
1746 /// UT test for `ylong_json_set_int_value_to_number`.
1747 ///
1748 /// # Title
1749 /// ut_ylong_json_set_int_value_to_number
1750 ///
1751 /// # Brief
1752 /// 1. Calls `ylong_json_set_int_value_to_number` to set int value to number.
1753 /// 2. Checks if the test results are correct.
1754 #[test]
ut_ylong_json_set_int_value_to_number()1755 fn ut_ylong_json_set_int_value_to_number() {
1756 unsafe {
1757 // Null ptr
1758 let number = null_mut();
1759 assert_eq!(ylong_json_set_int_value_to_number(number, 1), 0);
1760
1761 let int = ylong_json_create_int_number(1i64);
1762 let mut number = 0i64;
1763 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong);
1764 assert_eq!(number, 1i64);
1765 assert_eq!(ylong_json_set_int_value_to_number(int, 3i64), 1);
1766 ylong_json_get_int_value_from_number(int, &mut number as *mut c_longlong);
1767 assert_eq!(number, 3i64);
1768 ylong_json_delete(int);
1769
1770 let double = ylong_json_create_double_number(3.24);
1771 let mut number = 0f64;
1772 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double);
1773 assert_eq!(number, 3.24);
1774 assert_eq!(ylong_json_set_int_value_to_number(double, 1), 1);
1775 ylong_json_get_double_value_from_number(double, &mut number as *mut c_double);
1776 assert_eq!(number, 1.0);
1777 ylong_json_delete(double);
1778
1779 let null = ylong_json_create_null();
1780 assert_eq!(ylong_json_set_int_value_to_number(null, 1), 0);
1781 ylong_json_delete(null);
1782 }
1783 }
1784
1785 /// UT test for `ylong_json_create_string`.
1786 ///
1787 /// # Title
1788 /// ut_ylong_json_create_string
1789 ///
1790 /// # Brief
1791 /// 1. Calls `ylong_json_create_string` to create a string from *mut c_char.
1792 /// 2. Checks if the test results are correct.
1793 #[test]
ut_ylong_json_create_string()1794 fn ut_ylong_json_create_string() {
1795 unsafe {
1796 // Null ptr
1797 let str = null();
1798 assert!(ylong_json_create_string(str).is_null());
1799
1800 let str = str_to_c_char("Hello World");
1801 let string = ylong_json_create_string(str);
1802 let mut content = null_mut();
1803 ylong_json_get_value_from_string(string, &mut content as *mut *mut c_char);
1804 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
1805 assert_eq!(result, "Hello World");
1806 // Destruction
1807 let _ = Box::from_raw(str);
1808 ylong_json_delete(string);
1809 }
1810 }
1811
1812 /// UT test for `ylong_json_is_string`.
1813 ///
1814 /// # Title
1815 /// ut_ylong_json_is_string
1816 ///
1817 /// # Brief
1818 /// 1. Calls `ylong_json_is_string` to determine whether the value is string.
1819 /// 2. Checks if the test results are correct.
1820 #[test]
ut_ylong_json_is_string()1821 fn ut_ylong_json_is_string() {
1822 unsafe {
1823 // Null ptr
1824 let string = null_mut();
1825 assert_eq!(ylong_json_is_string(string), 0);
1826
1827 let str = str_to_c_char("Hello World");
1828 let string = ylong_json_create_string(str);
1829 assert_eq!(ylong_json_is_string(string), 1);
1830 let _ = Box::from_raw(str);
1831 ylong_json_delete(string);
1832
1833 let null = ylong_json_create_null();
1834 assert_eq!(ylong_json_is_string(null), 0);
1835 ylong_json_delete(null);
1836 }
1837 }
1838
1839 /// UT test for `ylong_json_get_value_from_string`.
1840 ///
1841 /// # Title
1842 /// ut_ylong_json_get_value_from_string
1843 ///
1844 /// # Brief
1845 /// 1. Calls `ylong_json_get_value_from_string` to get value from string.
1846 /// 2. Checks if the test results are correct.
1847 #[test]
ut_ylong_json_get_value_from_string()1848 fn ut_ylong_json_get_value_from_string() {
1849 unsafe {
1850 // Null ptr
1851 let string = null_mut();
1852 let mut str = null_mut();
1853 assert_eq!(
1854 ylong_json_get_value_from_string(string, &mut str as *mut *mut c_char),
1855 0
1856 );
1857
1858 let str = str_to_c_char("Hello World");
1859 let string = ylong_json_create_string(str);
1860 let mut content = null_mut();
1861 assert_eq!(
1862 ylong_json_get_value_from_string(string, &mut content as *mut *mut c_char),
1863 1
1864 );
1865 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
1866 assert_eq!(result, "Hello World");
1867 let _ = Box::from_raw(str);
1868 ylong_json_delete(string);
1869
1870 let null = ylong_json_create_null();
1871 let mut content = null_mut();
1872 assert_eq!(
1873 ylong_json_get_value_from_string(null, &mut content as *mut *mut c_char),
1874 0
1875 );
1876 ylong_json_delete(null);
1877 }
1878 }
1879
1880 /// UT test for `ylong_json_set_value_to_string`.
1881 ///
1882 /// # Title
1883 /// ut_ylong_json_set_value_to_string
1884 ///
1885 /// # Brief
1886 /// 1. Calls `ylong_json_set_value_to_string` to set value to string.
1887 /// 2. Checks if the test results are correct.
1888 #[test]
ut_ylong_json_set_value_to_string()1889 fn ut_ylong_json_set_value_to_string() {
1890 unsafe {
1891 // Null ptr
1892 let string = null_mut();
1893 let str = str_to_c_char("Hello World");
1894 assert_eq!(ylong_json_set_value_to_string(string, str), 0);
1895 let _ = Box::from_raw(str);
1896
1897 // Null ptr
1898 let str = str_to_c_char("Hello World");
1899 let string = ylong_json_create_string(str);
1900 let _ = Box::from_raw(str);
1901 let str = null();
1902 assert_eq!(ylong_json_set_value_to_string(string, str), 0);
1903 ylong_json_delete(string);
1904
1905 let str = str_to_c_char("Hello World");
1906 let string = ylong_json_create_string(str);
1907 // Check if the original value is "Hello World".
1908 let mut content = null_mut();
1909 ylong_json_get_value_from_string(string, &mut content as *mut *mut c_char);
1910 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
1911 assert_eq!(result, "Hello World");
1912 let _ = Box::from_raw(str);
1913 // Use the function to set the content to "New String".
1914 let str = str_to_c_char("New String");
1915 assert_eq!(ylong_json_set_value_to_string(string, str), 1);
1916 // Check whether the Settings are successful.
1917 ylong_json_get_value_from_string(string, &mut content as *mut *mut c_char);
1918 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
1919 assert_eq!(result, "New String");
1920 let _ = Box::from_raw(str);
1921 ylong_json_delete(string);
1922
1923 let null = ylong_json_create_null();
1924 let str = str_to_c_char("New String");
1925 assert_eq!(ylong_json_set_value_to_string(null, str), 0);
1926 let _ = Box::from_raw(str);
1927 ylong_json_delete(null);
1928 }
1929 }
1930
1931 /// UT test for `ylong_json_create_array`.
1932 ///
1933 /// # Title
1934 /// ut_ylong_json_create_array
1935 ///
1936 /// # Brief
1937 /// 1. Calls `ylong_json_create_array` to create an array.
1938 /// 2. Checks if the test results are correct.
1939 #[test]
ut_ylong_json_create_array()1940 fn ut_ylong_json_create_array() {
1941 unsafe {
1942 let array = ylong_json_create_array();
1943 let result = ylong_json_print_unformatted(array);
1944 let result = CString::from_raw(result).into_string().unwrap();
1945 assert_eq!(result, "[]");
1946 ylong_json_delete(array);
1947 }
1948 }
1949
1950 /// UT test for `ut_ylong_json_is_array`.
1951 ///
1952 /// # Title
1953 /// ut_ylong_json_is_array
1954 ///
1955 /// # Brief
1956 /// 1. Calls `long_json_is_array` to determine whether the value is an array.
1957 /// 2. Checks if the test results are correct.
1958 #[test]
ut_ylong_json_is_array()1959 fn ut_ylong_json_is_array() {
1960 unsafe {
1961 // Null ptr
1962 let array = null_mut();
1963 assert_eq!(ylong_json_is_array(array), 0);
1964
1965 let array = ylong_json_create_array();
1966 assert_eq!(ylong_json_is_array(array), 1);
1967 ylong_json_delete(array);
1968
1969 let null = ylong_json_create_null();
1970 assert_eq!(ylong_json_is_array(null), 0);
1971 ylong_json_delete(null);
1972 }
1973 }
1974
1975 /// UT test for `ylong_json_get_array_size`.
1976 ///
1977 /// # Title
1978 /// ut_ylong_json_get_array_size
1979 ///
1980 /// # Brief
1981 /// 1. Calls `ylong_json_get_array_size` to get size of the array.
1982 /// 2. Checks if the test results are correct.
1983 #[test]
ut_ylong_json_get_array_size()1984 fn ut_ylong_json_get_array_size() {
1985 unsafe {
1986 // Null ptr
1987 let array = null_mut();
1988 let mut len = 0i32;
1989 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 0);
1990
1991 // Null ptr
1992 let array = ylong_json_create_array();
1993 let len = null_mut();
1994 assert_eq!(ylong_json_get_array_size(array, len), 0);
1995 ylong_json_delete(array);
1996
1997 let array = ylong_json_create_array();
1998 let mut len = 1i32;
1999 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2000 assert_eq!(len, 0);
2001 ylong_json_delete(array);
2002
2003 let null = ylong_json_create_null();
2004 let mut len = 1i32;
2005 assert_eq!(ylong_json_get_array_size(null, &mut len as *mut c_int), 0);
2006 ylong_json_delete(null);
2007 }
2008 }
2009
2010 /// UT test for `ylong_json_get_array_item`.
2011 ///
2012 /// # Title
2013 /// ut_ylong_json_get_array_item
2014 ///
2015 /// # Brief
2016 /// 1. Calls `ylong_json_get_array_item` to get an item of the array.
2017 /// 2. Checks if the test results are correct.
2018 #[test]
ut_ylong_json_get_array_item()2019 fn ut_ylong_json_get_array_item() {
2020 unsafe {
2021 // Null ptr
2022 let array = null_mut();
2023 assert!(ylong_json_get_array_item(array, 0).is_null());
2024
2025 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2026 let str = str_to_c_char(TEXT);
2027 let mut msg = null_mut();
2028 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2029 let _ = Box::from_raw(str);
2030 assert_eq!(ylong_json_is_array(array), 1);
2031
2032 let item0 = ylong_json_get_array_item(array, 0);
2033 assert_eq!(ylong_json_is_null(item0), 1);
2034
2035 let item1 = ylong_json_get_array_item(array, 1);
2036 assert_eq!(ylong_json_is_double_number(item1), 1);
2037 let mut number = 0f64;
2038 assert_eq!(
2039 ylong_json_get_double_value_from_number(item1, &mut number as *mut c_double),
2040 1
2041 );
2042 assert_eq!(number, 1.0);
2043
2044 let item2 = ylong_json_get_array_item(array, 2);
2045 assert_eq!(ylong_json_is_bool(item2), 1);
2046 let mut bool = 0i32;
2047 assert_eq!(
2048 ylong_json_get_value_from_bool(item2, &mut bool as *mut c_int),
2049 1
2050 );
2051 assert_eq!(bool, 1i32);
2052
2053 let item3 = ylong_json_get_array_item(array, 3);
2054 assert_eq!(ylong_json_is_string(item3), 1);
2055 let mut content = null_mut();
2056 assert_eq!(
2057 ylong_json_get_value_from_string(item3, &mut content as *mut *mut c_char),
2058 1
2059 );
2060 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
2061 assert_eq!(result, "Test");
2062
2063 assert!(ylong_json_get_array_item(array, 4).is_null());
2064
2065 ylong_json_delete(array);
2066
2067 let null = ylong_json_create_null();
2068 assert!(ylong_json_get_array_item(null, 0).is_null());
2069 ylong_json_delete(null);
2070 }
2071 }
2072
2073 /// UT test for `ylong_json_add_item_to_array`.
2074 ///
2075 /// # Title
2076 /// ut_ylong_json_add_item_to_array
2077 ///
2078 /// # Brief
2079 /// 1. Calls `ylong_json_add_item_to_array` to add an item to the array.
2080 /// 2. Checks if the test results are correct.
2081 #[test]
ut_ylong_json_add_item_to_array()2082 fn ut_ylong_json_add_item_to_array() {
2083 unsafe {
2084 // Null ptr
2085 let array = null_mut();
2086 let item = ylong_json_create_null();
2087 assert_eq!(ylong_json_add_item_to_array(array, item), 0);
2088 ylong_json_delete(item);
2089
2090 let array = ylong_json_create_array();
2091 let item = null_mut();
2092 assert_eq!(ylong_json_add_item_to_array(array, item), 0);
2093 ylong_json_delete(array);
2094
2095 let array = ylong_json_create_array();
2096 let null = ylong_json_create_null();
2097 assert_eq!(ylong_json_add_item_to_array(array, null), 1);
2098 let result = ylong_json_print_unformatted(array);
2099 let result = CString::from_raw(result).into_string().unwrap();
2100 assert_eq!(result, "[null]");
2101 ylong_json_delete(array);
2102
2103 let null = ylong_json_create_null();
2104 let null2 = ylong_json_create_null();
2105 assert_eq!(ylong_json_add_item_to_array(null, null2), 0);
2106 ylong_json_delete(null);
2107 ylong_json_delete(null2);
2108 }
2109 }
2110
2111 /// UT test for `ylong_json_replace_item_in_array`.
2112 ///
2113 /// # Title
2114 /// ut_ylong_json_replace_item_in_array
2115 ///
2116 /// # Brief
2117 /// 1. Calls `ylong_json_replace_item_in_array` to replace an item in the array.
2118 /// 2. Checks if the test results are correct.
2119 #[test]
ut_ylong_json_replace_item_in_array()2120 fn ut_ylong_json_replace_item_in_array() {
2121 unsafe {
2122 // Null ptr
2123 let array = null_mut();
2124 let item = ylong_json_create_null();
2125 assert_eq!(ylong_json_replace_array_item_by_index(array, 0, item), 0);
2126 ylong_json_delete(item);
2127
2128 // Null ptr
2129 let array = ylong_json_create_array();
2130 let item = null_mut();
2131 assert_eq!(ylong_json_replace_array_item_by_index(array, 0, item), 0);
2132 ylong_json_delete(array);
2133
2134 let array = ylong_json_create_array();
2135 let null = ylong_json_create_null();
2136 assert_eq!(ylong_json_add_item_to_array(array, null), 1);
2137 let result = ylong_json_print_unformatted(array);
2138 let result = CString::from_raw(result).into_string().unwrap();
2139 assert_eq!(result, "[null]");
2140 let replace = ylong_json_create_bool(1);
2141 assert_eq!(ylong_json_replace_array_item_by_index(array, 0, replace), 1);
2142 let result = ylong_json_print_unformatted(array);
2143 let result = CString::from_raw(result).into_string().unwrap();
2144 assert_eq!(result, "[true]");
2145 ylong_json_delete(array);
2146
2147 let null = ylong_json_create_null();
2148 let null2 = ylong_json_create_null();
2149 assert_eq!(ylong_json_replace_array_item_by_index(null, 0, null2), 0);
2150 ylong_json_delete(null);
2151 ylong_json_delete(null2);
2152 }
2153 }
2154
2155 /// UT test for `ylong_json_remove_array_item_by_index`.
2156 ///
2157 /// # Title
2158 /// ut_ylong_json_remove_array_item_by_index
2159 ///
2160 /// # Brief
2161 /// 1. Calls `ylong_json_remove_array_item_by_index` to remove an item in the array by index.
2162 /// (Uses the method 'remove' of Array.)
2163 /// 2. Checks if the test results are correct.
2164 #[test]
ut_ylong_json_remove_array_item_by_index()2165 fn ut_ylong_json_remove_array_item_by_index() {
2166 unsafe {
2167 // Null ptr
2168 let array = null_mut();
2169 assert!(ylong_json_remove_array_item_by_index(array, 0).is_null());
2170
2171 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2172 let str = str_to_c_char(TEXT);
2173 let mut msg = null_mut();
2174 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2175 let _ = Box::from_raw(str);
2176 let mut len = 0i32;
2177 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2178 assert_eq!(len, 4);
2179
2180 let item0 = ylong_json_remove_array_item_by_index(array, 0);
2181 assert_eq!(ylong_json_is_null(item0), 1);
2182 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2183 assert_eq!(len, 3);
2184 ylong_json_delete(item0);
2185
2186 let item3 = ylong_json_remove_array_item_by_index(array, 2);
2187 assert_eq!(ylong_json_is_string(item3), 1);
2188 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2189 assert_eq!(len, 2);
2190 ylong_json_delete(item3);
2191
2192 let item1 = ylong_json_remove_array_item_by_index(array, 0);
2193 assert_eq!(ylong_json_is_number(item1), 1);
2194 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2195 assert_eq!(len, 1);
2196 ylong_json_delete(item1);
2197
2198 let item2 = ylong_json_remove_array_item_by_index(array, 0);
2199 assert_eq!(ylong_json_is_bool(item2), 1);
2200 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2201 assert_eq!(len, 0);
2202 ylong_json_delete(item2);
2203 ylong_json_delete(array);
2204
2205 let null = ylong_json_create_null();
2206 let item = ylong_json_remove_array_item_by_index(null, 0);
2207 assert!(item.is_null());
2208 ylong_json_delete(null);
2209 }
2210 }
2211
2212 /// UT test for `ylong_json_delete_array_item_by_index`.
2213 ///
2214 /// # Title
2215 /// ut_ylong_json_delete_array_item_by_index
2216 ///
2217 /// # Brief
2218 /// 1. Calls `ylong_json_delete_array_item_by_index` to delete an item in the array by index.
2219 /// (Uses the method 'remove' of underlying data structure.)
2220 /// 2. Checks if the test results are correct.
2221 #[test]
ut_ylong_json_delete_array_item_by_index()2222 fn ut_ylong_json_delete_array_item_by_index() {
2223 unsafe {
2224 // Null ptr scene, if the process does not exit abnormally, it is successful.
2225 let array = null_mut();
2226 ylong_json_delete_array_item_by_index(array, 0);
2227
2228 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2229 let str = str_to_c_char(TEXT);
2230 let mut msg = null_mut();
2231 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2232 let mut len = 0i32;
2233 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2234 assert_eq!(len, 4);
2235
2236 ylong_json_delete_array_item_by_index(array, 0);
2237 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2238 assert_eq!(len, 3);
2239
2240 ylong_json_delete_array_item_by_index(array, 0);
2241 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2242 assert_eq!(len, 2);
2243
2244 ylong_json_delete_array_item_by_index(array, 0);
2245 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2246 assert_eq!(len, 1);
2247
2248 ylong_json_delete_array_item_by_index(array, 0);
2249 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2250 assert_eq!(len, 0);
2251
2252 let _ = Box::from_raw(str);
2253 ylong_json_delete(array);
2254
2255 let null = ylong_json_create_null();
2256 ylong_json_delete_array_item_by_index(null, 0);
2257 ylong_json_delete(null);
2258 }
2259 }
2260
2261 /// UT test for `ylong_json_get_array_node`.
2262 ///
2263 /// # Title
2264 /// ut_ylong_json_get_array_node
2265 ///
2266 /// # Brief
2267 /// 1. Calls `ylong_json_get_array_node` to get an array node.
2268 /// 2. Checks if the test results are correct.
2269 #[cfg(feature = "list_array")]
2270 #[test]
ut_ylong_json_get_array_node()2271 fn ut_ylong_json_get_array_node() {
2272 unsafe {
2273 // Null ptr
2274 let array = null_mut();
2275 assert!(ylong_json_get_array_node(array, 0).is_null());
2276
2277 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2278 let str = str_to_c_char(TEXT);
2279 let mut msg = null_mut();
2280 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2281 let _ = Box::from_raw(str);
2282 assert_eq!(ylong_json_is_array(array), 1);
2283
2284 let node0 = ylong_json_get_array_node(array, 0);
2285 assert!(!node0.is_null());
2286
2287 let node1 = ylong_json_get_array_node(array, 1);
2288 assert!(!node1.is_null());
2289
2290 let node2 = ylong_json_get_array_node(array, 2);
2291 assert!(!node2.is_null());
2292
2293 let node3 = ylong_json_get_array_node(array, 3);
2294 assert!(!node3.is_null());
2295
2296 let node4 = ylong_json_get_array_node(array, 4);
2297 assert!(node4.is_null());
2298
2299 ylong_json_delete(array);
2300
2301 let null = ylong_json_create_null();
2302 assert!(ylong_json_get_array_node(null, 0).is_null());
2303 ylong_json_delete(null);
2304 }
2305 }
2306
2307 /// UT test for `ylong_json_get_item_from_array_node`.
2308 ///
2309 /// # Title
2310 /// ut_ylong_json_get_item_from_array_node
2311 ///
2312 /// # Brief
2313 /// 1. Calls `ylong_json_get_item_from_array_node` to get the item of an array node.
2314 /// 2. Checks if the test results are correct.
2315 #[cfg(feature = "list_array")]
2316 #[test]
ut_ylong_json_get_item_from_array_node()2317 fn ut_ylong_json_get_item_from_array_node() {
2318 unsafe {
2319 // Null ptr
2320 let node = null_mut();
2321 assert!(ylong_json_get_array_node(node, 0).is_null());
2322
2323 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2324 let str = str_to_c_char(TEXT);
2325 let mut msg = null_mut();
2326 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2327 let _ = Box::from_raw(str);
2328 assert_eq!(ylong_json_is_array(array), 1);
2329
2330 let node0 = ylong_json_get_array_node(array, 0);
2331 assert!(!node0.is_null());
2332 let item0 = ylong_json_get_item_from_array_node(node0);
2333 assert_eq!(ylong_json_is_null(item0), 1);
2334
2335 let node1 = ylong_json_get_array_node(array, 1);
2336 assert!(!node1.is_null());
2337 let item1 = ylong_json_get_item_from_array_node(node1);
2338 let mut number = 0f64;
2339 assert_eq!(
2340 ylong_json_get_double_value_from_number(item1, &mut number as *mut c_double),
2341 1
2342 );
2343 assert_eq!(number, 1.0);
2344
2345 let node2 = ylong_json_get_array_node(array, 2);
2346 assert!(!node2.is_null());
2347 let item2 = ylong_json_get_item_from_array_node(node2);
2348 let mut bool = 0i32;
2349 assert_eq!(
2350 ylong_json_get_value_from_bool(item2, &mut bool as *mut c_int),
2351 1
2352 );
2353 assert_eq!(bool, 1i32);
2354
2355 let node3 = ylong_json_get_array_node(array, 3);
2356 assert!(!node3.is_null());
2357 let item3 = ylong_json_get_item_from_array_node(node3);
2358 let mut content = null_mut();
2359 assert_eq!(
2360 ylong_json_get_value_from_string(item3, &mut content as *mut *mut c_char),
2361 1
2362 );
2363 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
2364 assert_eq!(result, "Test");
2365
2366 ylong_json_delete(array);
2367 }
2368 }
2369
2370 /// UT test for `ylong_json_add_item_to_array_then_get_node`.
2371 ///
2372 /// # Title
2373 /// ut_ylong_json_add_item_to_array_then_get_node
2374 ///
2375 /// # Brief
2376 /// 1. Calls `ylong_json_add_item_to_array_then_get_node` to add an item to array and get the corresponding node.
2377 /// 2. Checks if the test results are correct.
2378 #[cfg(feature = "list_array")]
2379 #[test]
ut_ylong_json_add_item_to_array_then_get_node()2380 fn ut_ylong_json_add_item_to_array_then_get_node() {
2381 unsafe {
2382 // Null ptr
2383 let array = null_mut();
2384 let item = ylong_json_create_null();
2385 assert!(ylong_json_add_item_to_array_then_get_node(array, item).is_null());
2386 ylong_json_delete(item);
2387
2388 // Null ptr
2389 let array = ylong_json_create_array();
2390 let item = null_mut();
2391 assert!(ylong_json_add_item_to_array_then_get_node(array, item).is_null());
2392 ylong_json_delete(array);
2393
2394 let array = ylong_json_create_array();
2395 let null = ylong_json_create_null();
2396 let node0 = ylong_json_add_item_to_array_then_get_node(array, null);
2397 assert!(!node0.is_null());
2398 let mut len = 0i32;
2399 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2400 assert_eq!(len, 1);
2401 let item0 = ylong_json_get_item_from_array_node(node0);
2402 assert!(!item0.is_null());
2403 assert_eq!(ylong_json_is_null(item0), 1);
2404 let item0 = ylong_json_remove_array_node(node0);
2405 ylong_json_delete(item0);
2406 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2407 assert_eq!(len, 0);
2408 ylong_json_delete(array);
2409 }
2410 }
2411
2412 /// UT test for `ylong_json_replace_item_of_array_node`.
2413 ///
2414 /// # Title
2415 /// ut_ylong_json_replace_item_of_array_node
2416 ///
2417 /// # Brief
2418 /// 1. Calls `ylong_json_replace_item_of_array_node` to replace the item of an array node.
2419 /// 2. Checks if the test results are correct.
2420 #[cfg(feature = "list_array")]
2421 #[test]
ut_ylong_json_replace_item_of_array_node()2422 fn ut_ylong_json_replace_item_of_array_node() {
2423 unsafe {
2424 // Null ptr
2425 let node = null_mut();
2426 let item = ylong_json_create_null();
2427 assert_eq!(ylong_json_replace_item_of_array_node(node, item), 0);
2428 ylong_json_delete(item);
2429
2430 // Null ptr scene, if the process does not exit abnormally, it is successful.
2431 let array = ylong_json_create_array();
2432 let null = ylong_json_create_null();
2433 let node = ylong_json_add_item_to_array_then_get_node(array, null);
2434 let item = null_mut();
2435 assert_eq!(ylong_json_replace_item_of_array_node(node, item), 0);
2436 ylong_json_delete(array);
2437
2438 let array = ylong_json_create_array();
2439 let null = ylong_json_create_null();
2440 let node = ylong_json_add_item_to_array_then_get_node(array, null);
2441 let result = ylong_json_print_unformatted(array);
2442 let result = CString::from_raw(result).into_string().unwrap();
2443 assert_eq!(result, "[null]");
2444
2445 let bool = ylong_json_create_bool(1);
2446 assert_eq!(ylong_json_replace_item_of_array_node(node, bool), 1);
2447 let result = ylong_json_print_unformatted(array);
2448 let result = CString::from_raw(result).into_string().unwrap();
2449 assert_eq!(result, "[true]");
2450
2451 ylong_json_delete(array);
2452 }
2453 }
2454
2455 /// UT test for `ylong_json_remove_array_node`.
2456 ///
2457 /// # Title
2458 /// ut_ylong_json_remove_array_node
2459 ///
2460 /// # Brief
2461 /// 1. Calls `ylong_json_remove_array_node` to remove an array node.
2462 /// 2. Checks if the test results are correct.
2463 #[cfg(feature = "list_array")]
2464 #[test]
ut_ylong_json_remove_array_node()2465 fn ut_ylong_json_remove_array_node() {
2466 unsafe {
2467 // Null ptr
2468 let node = null_mut();
2469 assert!(ylong_json_remove_array_node(node).is_null());
2470
2471 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2472 let str = str_to_c_char(TEXT);
2473 let mut msg = null_mut();
2474 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2475 let _ = Box::from_raw(str);
2476 assert_eq!(ylong_json_is_array(array), 1);
2477 let mut len = 0i32;
2478 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2479 assert_eq!(len, 4);
2480
2481 let node0 = ylong_json_get_array_node(array, 0);
2482 assert!(!node0.is_null());
2483 let item0 = ylong_json_remove_array_node(node0);
2484 assert!(!item0.is_null());
2485 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2486 assert_eq!(len, 3);
2487 assert_eq!(ylong_json_is_null(item0), 1);
2488 ylong_json_delete(item0);
2489
2490 let node0 = ylong_json_get_array_node(array, 0);
2491 assert!(!node0.is_null());
2492 let item0 = ylong_json_remove_array_node(node0);
2493 assert!(!item0.is_null());
2494 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2495 assert_eq!(len, 2);
2496 let mut number = 0f64;
2497 assert_eq!(
2498 ylong_json_get_double_value_from_number(item0, &mut number as *mut c_double),
2499 1
2500 );
2501 assert_eq!(number, 1.0);
2502 ylong_json_delete(item0);
2503
2504 let node0 = ylong_json_get_array_node(array, 0);
2505 assert!(!node0.is_null());
2506 let item0 = ylong_json_remove_array_node(node0);
2507 assert!(!item0.is_null());
2508 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2509 assert_eq!(len, 1);
2510 let mut bool = 0i32;
2511 assert_eq!(
2512 ylong_json_get_value_from_bool(item0, &mut bool as *mut c_int),
2513 1
2514 );
2515 assert_eq!(bool, 1i32);
2516 ylong_json_delete(item0);
2517
2518 let node0 = ylong_json_get_array_node(array, 0);
2519 assert!(!node0.is_null());
2520 let item0 = ylong_json_remove_array_node(node0);
2521 assert!(!item0.is_null());
2522 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2523 assert_eq!(len, 0);
2524 let mut content = null_mut();
2525 assert_eq!(
2526 ylong_json_get_value_from_string(item0, &mut content as *mut *mut c_char),
2527 1
2528 );
2529 let result = String::from_utf8_unchecked(CStr::from_ptr(content).to_bytes().to_vec());
2530 assert_eq!(result, "Test");
2531 ylong_json_delete(item0);
2532
2533 ylong_json_delete(array);
2534 }
2535 }
2536
2537 /// UT test for `ylong_json_delete_array_node`.
2538 ///
2539 /// # Title
2540 /// ut_ylong_json_delete_array_node
2541 ///
2542 /// # Brief
2543 /// 1. Calls `ylong_json_delete_array_node` to delete an array node.
2544 /// 2. Checks if the test results are correct.
2545 #[cfg(feature = "list_array")]
2546 #[test]
ut_ylong_json_delete_array_node()2547 fn ut_ylong_json_delete_array_node() {
2548 unsafe {
2549 // Null ptr scene, if the process does not exit abnormally, it is successful.
2550 let node = null_mut();
2551 ylong_json_delete_array_node(node);
2552
2553 const TEXT: &str = "[null, 1.0, true, \"Test\"]";
2554 let str = str_to_c_char(TEXT);
2555 let mut msg = null_mut();
2556 let array = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2557 let _ = Box::from_raw(str);
2558 let mut len = 0i32;
2559 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2560 assert_eq!(len, 4);
2561
2562 let node0 = ylong_json_get_array_node(array, 0);
2563 ylong_json_delete_array_node(node0);
2564 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2565 assert_eq!(len, 3);
2566
2567 let node1 = ylong_json_get_array_node(array, 0);
2568 ylong_json_delete_array_node(node1);
2569 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2570 assert_eq!(len, 2);
2571
2572 let node2 = ylong_json_get_array_node(array, 0);
2573 ylong_json_delete_array_node(node2);
2574 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2575 assert_eq!(len, 1);
2576
2577 let node3 = ylong_json_get_array_node(array, 0);
2578 ylong_json_delete_array_node(node3);
2579 assert_eq!(ylong_json_get_array_size(array, &mut len as *mut c_int), 1);
2580 assert_eq!(len, 0);
2581
2582 ylong_json_delete(array);
2583 }
2584 }
2585
2586 /// UT test for `ylong_json_create_object`.
2587 ///
2588 /// # Title
2589 /// ut_ylong_json_create_object
2590 ///
2591 /// # Brief
2592 /// 1. Calls `ylong_json_create_object` to create an object.
2593 /// 2. Checks if the test results are correct.
2594 #[test]
ut_ylong_json_create_object()2595 fn ut_ylong_json_create_object() {
2596 unsafe {
2597 let object = ylong_json_create_object();
2598 assert_eq!(ylong_json_is_object(object), 1);
2599 let result = ylong_json_print_unformatted(object);
2600 let result = CString::from_raw(result).into_string().unwrap();
2601 assert_eq!(result, "{}");
2602 ylong_json_delete(object);
2603 }
2604 }
2605
2606 /// UT test for `ylong_json_is_object`.
2607 ///
2608 /// # Title
2609 /// ut_ylong_json_is_object
2610 ///
2611 /// # Brief
2612 /// 1. Calls `ylong_json_is_object` to determine whether the value is object.
2613 /// 2. Checks if the test results are correct.
2614 #[test]
ut_ylong_json_is_object()2615 fn ut_ylong_json_is_object() {
2616 unsafe {
2617 // Null ptr
2618 let object = null_mut();
2619 assert_eq!(ylong_json_is_object(object), 0);
2620
2621 let object = ylong_json_create_object();
2622 assert_eq!(ylong_json_is_object(object), 1);
2623 ylong_json_delete(object);
2624
2625 let null = ylong_json_create_null();
2626 assert_eq!(ylong_json_is_object(null), 0);
2627 ylong_json_delete(null);
2628 }
2629 }
2630
2631 /// UT test for `ylong_json_get_object_size`.
2632 ///
2633 /// # Title
2634 /// ut_ylong_json_get_object_size
2635 ///
2636 /// # Brief
2637 /// 1. Calls `ylong_json_get_object_size` to get size of an object.
2638 /// 2. Checks if the test results are correct.
2639 #[test]
ut_ylong_json_get_object_size()2640 fn ut_ylong_json_get_object_size() {
2641 unsafe {
2642 // Null ptr
2643 let object = null_mut();
2644 let mut len = 0i32;
2645 assert_eq!(
2646 ylong_json_get_object_size(object, &mut len as *mut c_int),
2647 0
2648 );
2649
2650 // Null ptr
2651 let object = ylong_json_create_object();
2652 let len = null_mut();
2653 assert_eq!(ylong_json_get_object_size(object, len), 0);
2654 ylong_json_delete(object);
2655
2656 let object = ylong_json_create_object();
2657 let mut len = 1i32;
2658 assert_eq!(
2659 ylong_json_get_object_size(object, &mut len as *mut c_int),
2660 1
2661 );
2662 assert_eq!(len, 0);
2663 ylong_json_delete(object);
2664
2665 let null = ylong_json_create_null();
2666 let mut len = 0i32;
2667 assert_eq!(ylong_json_get_object_size(null, &mut len as *mut c_int), 0);
2668 ylong_json_delete(null);
2669 }
2670 }
2671
2672 /// UT test for `ylong_json_has_object_item`.
2673 ///
2674 /// # Title
2675 /// ut_ylong_json_has_object_item
2676 ///
2677 /// # Brief
2678 /// 1. Calls `ylong_json_has_object_item` to determine whether the item exists in the object.
2679 /// 2. Checks if the test results are correct.
2680 #[test]
ut_ylong_json_has_object_item()2681 fn ut_ylong_json_has_object_item() {
2682 unsafe {
2683 // Null ptr
2684 let object = null_mut();
2685 let str = str_to_c_char("Hello World");
2686 assert_eq!(ylong_json_has_object_item(object, str), 0);
2687 let _ = Box::from_raw(str);
2688
2689 // Null ptr
2690 let object = ylong_json_create_object();
2691 let str = null();
2692 assert_eq!(ylong_json_has_object_item(object, str), 0);
2693 ylong_json_delete(object);
2694
2695 const TEXT: &str = "{\"null\":null}";
2696 let str = str_to_c_char(TEXT);
2697 let mut msg = null_mut();
2698 let object = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2699 let _ = Box::from_raw(str);
2700
2701 let str = str_to_c_char("null");
2702 assert_eq!(ylong_json_has_object_item(object, str), 1);
2703 let _ = Box::from_raw(str);
2704
2705 let str = str_to_c_char("no_such_key");
2706 assert_eq!(ylong_json_has_object_item(object, str), 0);
2707 let _ = Box::from_raw(str);
2708
2709 ylong_json_delete(object);
2710
2711 let null = ylong_json_create_null();
2712 let str = str_to_c_char("Invalid");
2713 assert_eq!(ylong_json_has_object_item(null, str), 0);
2714 let _ = Box::from_raw(str);
2715 ylong_json_delete(null);
2716 }
2717 }
2718
2719 /// UT test for `ylong_json_get_object_item`.
2720 ///
2721 /// # Title
2722 /// ut_ylong_json_get_object_item
2723 ///
2724 /// # Brief
2725 /// 1. Calls `ylong_json_get_object_item` to get an item in the object.
2726 /// 2. Checks if the test results are correct.
2727 #[test]
ut_ylong_json_get_object_item()2728 fn ut_ylong_json_get_object_item() {
2729 unsafe {
2730 // Null ptr
2731 let object = null_mut();
2732 let str = str_to_c_char("Hello World");
2733 assert!(ylong_json_get_object_item(object, str).is_null());
2734 let _ = Box::from_raw(str);
2735
2736 // Null ptr
2737 let object = ylong_json_create_object();
2738 let str = null();
2739 assert!(ylong_json_get_object_item(object, str).is_null());
2740 ylong_json_delete(object);
2741
2742 const TEXT: &str = "{\"null\":null}";
2743 let str = str_to_c_char(TEXT);
2744 let mut msg = null_mut();
2745 let object = ylong_json_parse(str, &mut msg as *mut *mut c_char);
2746 let _ = Box::from_raw(str);
2747
2748 let str = str_to_c_char("null");
2749 let item = ylong_json_get_object_item(object, str);
2750 assert_eq!(ylong_json_is_null(item), 1);
2751 let _ = Box::from_raw(str);
2752
2753 let str = str_to_c_char("no_such_key");
2754 let item = ylong_json_get_object_item(object, str);
2755 assert!(item.is_null());
2756 let _ = Box::from_raw(str);
2757
2758 ylong_json_delete(object);
2759
2760 let null = ylong_json_create_null();
2761 let str = str_to_c_char("Invalid");
2762 assert!(ylong_json_get_object_item(null, str).is_null());
2763 let _ = Box::from_raw(str);
2764 ylong_json_delete(null);
2765 }
2766 }
2767
2768 /// UT test for `ylong_json_add_item_to_object`.
2769 ///
2770 /// # Title
2771 /// ut_ylong_json_add_item_to_object
2772 ///
2773 /// # Brief
2774 /// 1. Calls `ylong_json_add_item_to_object` to add an item to the object.
2775 /// 2. Checks if the test results are correct.
2776 #[test]
ut_ylong_json_add_item_to_object()2777 fn ut_ylong_json_add_item_to_object() {
2778 unsafe {
2779 // Null ptr
2780 let object = null_mut();
2781 let str = str_to_c_char("Hello World");
2782 let item = ylong_json_create_null();
2783 assert_eq!(ylong_json_add_item_to_object(object, str, item), 0);
2784 let _ = Box::from_raw(str);
2785 ylong_json_delete(item);
2786
2787 // Null ptr
2788 let object = ylong_json_create_object();
2789 let str = null();
2790 let item = ylong_json_create_null();
2791 assert_eq!(ylong_json_add_item_to_object(object, str, item), 0);
2792 ylong_json_delete(object);
2793 ylong_json_delete(item);
2794
2795 // Null ptr
2796 let object = ylong_json_create_object();
2797 let str = str_to_c_char("Hello World");
2798 let item = null_mut();
2799 assert_eq!(ylong_json_add_item_to_object(object, str, item), 0);
2800 ylong_json_delete(object);
2801 let _ = Box::from_raw(str);
2802
2803 let object = ylong_json_create_object();
2804 let mut len = 0i32;
2805 assert_eq!(
2806 ylong_json_get_object_size(object, &mut len as *mut c_int),
2807 1
2808 );
2809 assert_eq!(len, 0);
2810 let str = str_to_c_char("Hello World");
2811 let item = ylong_json_create_null();
2812 assert_eq!(ylong_json_add_item_to_object(object, str, item), 1);
2813 let _ = Box::from_raw(str);
2814 assert_eq!(
2815 ylong_json_get_object_size(object, &mut len as *mut c_int),
2816 1
2817 );
2818 assert_eq!(len, 1);
2819 ylong_json_delete(object);
2820
2821 let null = ylong_json_create_null();
2822 let str = str_to_c_char("Hello World");
2823 let item = ylong_json_create_null();
2824 assert_eq!(ylong_json_add_item_to_object(null, str, item), 0);
2825 ylong_json_delete(null);
2826 let _ = Box::from_raw(str);
2827 ylong_json_delete(item);
2828 }
2829 }
2830
2831 /// UT test for `ylong_json_replace_object_item_by_index`.
2832 ///
2833 /// # Title
2834 /// ut_ylong_json_replace_object_item_by_index
2835 ///
2836 /// # Brief
2837 /// 1. Calls `ylong_json_replace_object_item_by_index` to replace an item in the object by index.
2838 /// 2. Checks if the test results are correct.
2839 #[test]
ut_ylong_json_replace_object_item_by_index()2840 fn ut_ylong_json_replace_object_item_by_index() {
2841 unsafe {
2842 // Null ptr
2843 let object = null_mut();
2844 let str = str_to_c_char("Hello World");
2845 let item = ylong_json_create_null();
2846 assert_eq!(
2847 ylong_json_replace_object_item_by_index(object, str, item),
2848 0
2849 );
2850 let _ = Box::from_raw(str);
2851 ylong_json_delete(item);
2852
2853 // Null ptr
2854 let object = ylong_json_create_object();
2855 let str = null();
2856 let item = ylong_json_create_null();
2857 assert_eq!(
2858 ylong_json_replace_object_item_by_index(object, str, item),
2859 0
2860 );
2861 ylong_json_delete(object);
2862 ylong_json_delete(item);
2863
2864 // Null ptr
2865 let object = ylong_json_create_object();
2866 let str = str_to_c_char("Hello World");
2867 let item = null_mut();
2868 assert_eq!(
2869 ylong_json_replace_object_item_by_index(object, str, item),
2870 0
2871 );
2872 ylong_json_delete(object);
2873 let _ = Box::from_raw(str);
2874
2875 let object = ylong_json_create_object();
2876 let str = str_to_c_char("Init");
2877 let item = ylong_json_create_null();
2878 assert_eq!(ylong_json_add_item_to_object(object, str, item), 1);
2879 let result = ylong_json_print_unformatted(object);
2880 let result = CString::from_raw(result).into_string().unwrap();
2881 assert_eq!(result, "{\"Init\":null}");
2882 let item = ylong_json_create_bool(1);
2883 assert_eq!(
2884 ylong_json_replace_object_item_by_index(object, str, item),
2885 1
2886 );
2887 let _ = Box::from_raw(str);
2888 let result = ylong_json_print_unformatted(object);
2889 let result = CString::from_raw(result).into_string().unwrap();
2890 assert_eq!(result, "{\"Init\":true}");
2891 ylong_json_delete(object);
2892
2893 let null = ylong_json_create_null();
2894 let str = str_to_c_char("Hello World");
2895 let item = ylong_json_create_null();
2896 assert_eq!(ylong_json_replace_object_item_by_index(null, str, item), 0);
2897 ylong_json_delete(null);
2898 let _ = Box::from_raw(str);
2899 ylong_json_delete(item);
2900 }
2901 }
2902
2903 /// UT test for `ylong_json_remove_object_item_by_index`.
2904 ///
2905 /// # Title
2906 /// ut_ylong_json_remove_object_item_by_index
2907 ///
2908 /// # Brief
2909 /// 1. Calls `ylong_json_remove_object_item_by_index` to remove an item in the object by index.
2910 /// 2. Checks if the test results are correct.
2911 #[test]
ut_ylong_json_remove_object_item_by_index()2912 fn ut_ylong_json_remove_object_item_by_index() {
2913 unsafe {
2914 // Null ptr
2915 let object = null_mut();
2916 let str = str_to_c_char("Hello World");
2917 assert!(ylong_json_remove_object_item_by_index(object, str).is_null());
2918 let _ = Box::from_raw(str);
2919
2920 // Null ptr
2921 let object = ylong_json_create_object();
2922 let str = null();
2923 assert!(ylong_json_remove_object_item_by_index(object, str).is_null());
2924 ylong_json_delete(object);
2925
2926 let object = ylong_json_create_object();
2927 let str = str_to_c_char("Init");
2928 let item = ylong_json_create_null();
2929 assert_eq!(ylong_json_add_item_to_object(object, str, item), 1);
2930 let result = ylong_json_print_unformatted(object);
2931 let result = CString::from_raw(result).into_string().unwrap();
2932 assert_eq!(result, "{\"Init\":null}");
2933 let item = ylong_json_remove_object_item_by_index(object, str);
2934 assert!(!item.is_null());
2935 assert_eq!(ylong_json_is_null(item), 1);
2936 let result = ylong_json_print_unformatted(object);
2937 let result = CString::from_raw(result).into_string().unwrap();
2938 assert_eq!(result, "{}");
2939 ylong_json_delete(object);
2940 let _ = Box::from_raw(str);
2941 ylong_json_delete(item);
2942
2943 let null = ylong_json_create_null();
2944 let str = str_to_c_char("Hello World");
2945 assert!(ylong_json_remove_object_item_by_index(null, str).is_null());
2946 ylong_json_delete(null);
2947 let _ = Box::from_raw(str);
2948 }
2949 }
2950
2951 /// UT test for `ylong_json_delete_object_by_index`.
2952 ///
2953 /// # Title
2954 /// ut_ylong_json_delete_object_by_index
2955 ///
2956 /// # Brief
2957 /// 1. Calls `ylong_json_delete_object_by_index` to delete an item in the object by index.
2958 /// 2. Checks if the test results are correct.
2959 #[test]
ut_ylong_json_delete_object_by_index()2960 fn ut_ylong_json_delete_object_by_index() {
2961 unsafe {
2962 // Null ptr
2963 let object = null_mut();
2964 let str = str_to_c_char("Hello World");
2965 ylong_json_delete_object_item_by_index(object, str);
2966 let _ = Box::from_raw(str);
2967
2968 // Null ptr
2969 let object = ylong_json_create_object();
2970 let str = null();
2971 ylong_json_delete_object_item_by_index(object, str);
2972 ylong_json_delete(object);
2973
2974 let object = ylong_json_create_object();
2975 let str = str_to_c_char("Init");
2976 let item = ylong_json_create_null();
2977 assert_eq!(ylong_json_add_item_to_object(object, str, item), 1);
2978 let result = ylong_json_print_unformatted(object);
2979 let result = CString::from_raw(result).into_string().unwrap();
2980 assert_eq!(result, "{\"Init\":null}");
2981 ylong_json_delete_object_item_by_index(object, str);
2982 let result = ylong_json_print_unformatted(object);
2983 let result = CString::from_raw(result).into_string().unwrap();
2984 assert_eq!(result, "{}");
2985 ylong_json_delete(object);
2986 let _ = Box::from_raw(str);
2987
2988 let null = ylong_json_create_null();
2989 let str = str_to_c_char("Hello World");
2990 ylong_json_delete_object_item_by_index(null, str);
2991 ylong_json_delete(null);
2992 let _ = Box::from_raw(str);
2993 }
2994 }
2995
2996 /// UT test for `ylong_json_get_all_object_items`.
2997 ///
2998 /// # Title
2999 /// ut_ylong_json_get_all_object_items
3000 ///
3001 /// # Brief
3002 /// 1. Calls `ylong_json_get_all_object_items` to get all items in the object.
3003 /// 2. Checks if the test results are correct.
3004 #[test]
ut_ylong_json_get_all_object_items()3005 fn ut_ylong_json_get_all_object_items() {
3006 unsafe {
3007 // Null ptr
3008 let object = null_mut();
3009 let mut len = 1i32;
3010 let keys = malloc(size_of::<*mut c_char>() * (len as usize)) as *mut *mut c_char;
3011 let values =
3012 malloc(size_of::<*mut YlongJson>() * (len as usize)) as *mut *mut YlongJson;
3013 assert_eq!(
3014 ylong_json_get_all_object_items(object, keys, values, &mut len as *mut c_int),
3015 0
3016 );
3017 free(keys as *mut c_void);
3018 free(values as *mut c_void);
3019
3020 // Null ptr
3021 let object = ylong_json_create_object();
3022 let mut len = 1i32;
3023 let keys = null_mut();
3024 let values =
3025 malloc(size_of::<*mut YlongJson>() * (len as usize)) as *mut *mut YlongJson;
3026 assert_eq!(
3027 ylong_json_get_all_object_items(object, keys, values, &mut len as *mut c_int),
3028 0
3029 );
3030 ylong_json_delete(object);
3031 free(values as *mut c_void);
3032
3033 // Null ptr
3034 let object = ylong_json_create_object();
3035 let mut len = 1i32;
3036 let keys = malloc(size_of::<*mut c_char>() * (len as usize)) as *mut *mut c_char;
3037 let values = null_mut();
3038 assert_eq!(
3039 ylong_json_get_all_object_items(object, keys, values, &mut len as *mut c_int),
3040 0
3041 );
3042 ylong_json_delete(object);
3043 free(keys as *mut c_void);
3044
3045 // Null ptr
3046 let object = ylong_json_create_object();
3047 let len = 1i32;
3048 let keys = malloc(size_of::<*mut c_char>() * (len as usize)) as *mut *mut c_char;
3049 let values =
3050 malloc(size_of::<*mut YlongJson>() * (len as usize)) as *mut *mut YlongJson;
3051 let len = null_mut();
3052 assert_eq!(
3053 ylong_json_get_all_object_items(object, keys, values, len),
3054 0
3055 );
3056 ylong_json_delete(object);
3057 free(keys as *mut c_void);
3058 free(values as *mut c_void);
3059
3060 const TEXT: &str = r#"{"A":null,"B":1.0,"C":true,"D":"Test"}"#;
3061 let text = str_to_c_char(TEXT);
3062 let mut err_msg = null_mut();
3063 let object = ylong_json_parse(text, &mut err_msg as *mut *mut c_char);
3064 let _ = Box::from_raw(text);
3065 let mut len = 0i32;
3066 assert_eq!(
3067 ylong_json_get_object_size(object, &mut len as *mut c_int),
3068 1
3069 );
3070 assert_eq!(len, 4);
3071 let keys = malloc(size_of::<*mut c_char>() * (len as usize)) as *mut *mut c_char;
3072 let values =
3073 malloc(size_of::<*mut YlongJson>() * (len as usize)) as *mut *mut YlongJson;
3074 assert_eq!(
3075 ylong_json_get_all_object_items(object, keys, values, &mut len as *mut c_int),
3076 1
3077 );
3078 let mut cnt = 0;
3079 let key_result = ["A", "B", "C", "D"];
3080 let value_result = ["null", "1.0", "true", "\"Test\""];
3081 while cnt != len {
3082 let key = *(keys.offset(cnt as isize));
3083 let key_str = CStr::from_ptr(key).to_str().unwrap();
3084 assert_eq!(key_str, key_result[cnt as usize]);
3085 ylong_json_free_string(key);
3086
3087 let item = *(values.offset(cnt as isize));
3088 let value = ylong_json_print_unformatted(item);
3089 let value_str = CString::from_raw(value).into_string().unwrap();
3090 assert_eq!(value_str, value_result[cnt as usize]);
3091 cnt += 1;
3092 }
3093 free(keys as *mut c_void);
3094 free(values as *mut c_void);
3095 ylong_json_delete(object);
3096
3097 // 非 object
3098 let null = ylong_json_create_null();
3099 let mut len = 1i32;
3100 let keys = malloc(size_of::<*mut c_char>() * (len as usize)) as *mut *mut c_char;
3101 let values =
3102 malloc(size_of::<*mut YlongJson>() * (len as usize)) as *mut *mut YlongJson;
3103 assert_eq!(
3104 ylong_json_get_all_object_items(null, keys, values, &mut len as *mut c_int),
3105 0
3106 );
3107 ylong_json_delete(null);
3108 free(keys as *mut c_void);
3109 free(values as *mut c_void);
3110 }
3111 }
3112
3113 /// UT test for `ylong_json_for_each_object_item`.
3114 ///
3115 /// # Title
3116 /// ut_ylong_json_for_each_object_item
3117 ///
3118 /// # Brief
3119 /// 1. Calls `ylong_json_for_each_object_item` to do `func` for each item in the object.
3120 /// 2. Checks if the test results are correct.
3121 #[test]
ut_ylong_json_for_each_object_item()3122 fn ut_ylong_json_for_each_object_item() {
3123 unsafe {
3124 unsafe extern "C" fn func(target: *mut YlongJson) {
3125 ylong_json_set_int_value_to_number(target, 1000);
3126 }
3127
3128 // Null ptr
3129 let object = null_mut();
3130 assert_eq!(ylong_json_for_each_object_item(object, func), 0);
3131
3132 const TEXT: &str = r#"{"A":1,"B":2,"C":3,"D":null,"E":1.0}"#;
3133 let text = str_to_c_char(TEXT);
3134 let err_msg = null_mut();
3135 let object = ylong_json_parse(text, err_msg);
3136 let _ = Box::from_raw(text);
3137 let result = ylong_json_print_unformatted(object);
3138 let result = CString::from_raw(result).into_string().unwrap();
3139 assert_eq!(result, "{\"A\":1,\"B\":2,\"C\":3,\"D\":null,\"E\":1.0}");
3140 assert_eq!(ylong_json_for_each_object_item(object, func), 1);
3141 let result = ylong_json_print_unformatted(object);
3142 let result = CString::from_raw(result).into_string().unwrap();
3143 assert_eq!(
3144 result,
3145 "{\"A\":1000,\"B\":1000,\"C\":1000,\"D\":null,\"E\":1000}"
3146 );
3147 ylong_json_delete(object);
3148
3149 let null = ylong_json_create_null();
3150 assert_eq!(ylong_json_for_each_object_item(null, func), 0);
3151 ylong_json_delete(null);
3152 }
3153 }
3154
3155 /// UT test for `ylong_json_get_object_node`.
3156 ///
3157 /// # Title
3158 /// ut_ylong_json_get_object_node
3159 ///
3160 /// # Brief
3161 /// 1. Calls `ylong_json_get_object_node` to get an object node.
3162 /// 2. Checks if the test results are correct.
3163 #[cfg(feature = "list_object")]
3164 #[test]
ut_ylong_json_get_object_node()3165 fn ut_ylong_json_get_object_node() {
3166 unsafe {
3167 // Null ptr
3168 let object = null_mut();
3169 let str = str_to_c_char("Hello World");
3170 let node = ylong_json_get_object_node(object, str);
3171 assert!(node.is_null());
3172 let _ = Box::from_raw(str);
3173
3174 // Null ptr
3175 let object = ylong_json_create_object();
3176 let str = null_mut();
3177 let node = ylong_json_get_object_node(object, str);
3178 assert!(node.is_null());
3179 ylong_json_delete(object);
3180
3181 const TEXT: &str = r#"{"null":null}"#;
3182 let text = str_to_c_char(TEXT);
3183 let err_msg = null_mut();
3184 let object = ylong_json_parse(text, err_msg);
3185 let _ = Box::from_raw(text);
3186 let str = str_to_c_char("null");
3187 let node = ylong_json_get_object_node(object, str);
3188 let _ = Box::from_raw(str);
3189 assert!(!node.is_null());
3190 let item = ylong_json_get_item_from_object_node(node);
3191 assert_eq!(ylong_json_is_null(item), 1);
3192 ylong_json_delete(object);
3193
3194 // Non-object
3195 let null = ylong_json_create_null();
3196 let str = str_to_c_char("Hello World");
3197 let node = ylong_json_get_object_node(null, str);
3198 let _ = Box::from_raw(str);
3199 assert!(node.is_null());
3200 ylong_json_delete(null);
3201 }
3202 }
3203
3204 /// UT test for `ylong_json_get_item_from_object_node`.
3205 ///
3206 /// # Title
3207 /// ut_ylong_json_get_item_from_object_node
3208 ///
3209 /// # Brief
3210 /// 1. Calls `ylong_json_get_item_from_object_node` to get the item of an object node.
3211 /// 2. Checks if the test results are correct.
3212 #[cfg(feature = "list_object")]
3213 #[test]
ut_ylong_json_get_item_from_object_node()3214 fn ut_ylong_json_get_item_from_object_node() {
3215 unsafe {
3216 // Null ptr
3217 let node = null_mut();
3218 let item = ylong_json_get_item_from_object_node(node);
3219 assert!(item.is_null());
3220
3221 const TEXT: &str = r#"{"null":null}"#;
3222 let text = str_to_c_char(TEXT);
3223 let err_msg = null_mut();
3224 let object = ylong_json_parse(text, err_msg);
3225 let str = str_to_c_char("null");
3226 let node = ylong_json_get_object_node(object, str);
3227 assert!(!node.is_null());
3228 let item = ylong_json_get_item_from_object_node(node);
3229 assert_eq!(ylong_json_is_null(item), 1);
3230 let _ = Box::from_raw(text);
3231 let _ = Box::from_raw(str);
3232 ylong_json_delete(object);
3233 }
3234 }
3235
3236 /// UT test for `ylong_json_add_item_to_object_then_get_node`.
3237 ///
3238 /// # Title
3239 /// ut_ylong_json_add_item_to_object_then_get_node
3240 ///
3241 /// # Brief
3242 /// 1. Calls `ylong_json_add_item_to_object_then_get_node` to add an item to the object and get the corresponding node.
3243 /// 2. Checks if the test results are correct.
3244 #[cfg(feature = "list_object")]
3245 #[test]
ut_ylong_json_add_item_to_object_then_get_node()3246 fn ut_ylong_json_add_item_to_object_then_get_node() {
3247 unsafe {
3248 // Null ptr
3249 let object = null_mut();
3250 let str = str_to_c_char("null");
3251 let item = ylong_json_create_null();
3252 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3253 assert!(node.is_null());
3254 let _ = Box::from_raw(str);
3255 ylong_json_delete(item);
3256
3257 // Null ptr
3258 let object = ylong_json_create_object();
3259 let str = null_mut();
3260 let item = ylong_json_create_null();
3261 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3262 assert!(node.is_null());
3263 ylong_json_delete(object);
3264 ylong_json_delete(item);
3265
3266 // Null ptr
3267 let object = ylong_json_create_object();
3268 let str = str_to_c_char("null");
3269 let item = null_mut();
3270 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3271 assert!(node.is_null());
3272 ylong_json_delete(object);
3273 let _ = Box::from_raw(str);
3274
3275 let object = ylong_json_create_object();
3276 let str = str_to_c_char("null");
3277 let item = ylong_json_create_null();
3278 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3279 assert!(!node.is_null());
3280 let item = ylong_json_get_item_from_object_node(node);
3281 assert_eq!(ylong_json_is_null(item), 1);
3282 ylong_json_delete(object);
3283 let _ = Box::from_raw(str);
3284
3285 let null = ylong_json_create_null();
3286 let str = str_to_c_char("null");
3287 let item = ylong_json_create_null();
3288 let node = ylong_json_add_item_to_object_then_get_node(null, str, item);
3289 assert!(node.is_null());
3290 ylong_json_delete(null);
3291 let _ = Box::from_raw(str);
3292 ylong_json_delete(item);
3293 }
3294 }
3295
3296 /// UT test for `ylong_json_replace_item_of_object_node`.
3297 ///
3298 /// # Title
3299 /// ut_ylong_json_replace_item_of_object_node
3300 ///
3301 /// # Brief
3302 /// 1. Calls `ylong_json_replace_item_of_object_node` to replace the item of an object node.
3303 /// 2. Checks if the test results are correct.
3304 #[cfg(feature = "list_object")]
3305 #[test]
ut_ylong_json_replace_item_of_object_node()3306 fn ut_ylong_json_replace_item_of_object_node() {
3307 unsafe {
3308 // Null ptr
3309 let node = null_mut();
3310 let item = ylong_json_create_null();
3311 assert_eq!(ylong_json_replace_item_of_object_node(node, item), 0);
3312 ylong_json_delete(item);
3313
3314 // Null ptr
3315 let object = ylong_json_create_object();
3316 let str = str_to_c_char("null");
3317 let item = ylong_json_create_null();
3318 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3319 let item = null_mut();
3320 assert_eq!(ylong_json_replace_item_of_object_node(node, item), 0);
3321 ylong_json_delete(object);
3322 let _ = Box::from_raw(str);
3323
3324 let object = ylong_json_create_object();
3325 let str = str_to_c_char("null");
3326 let item = ylong_json_create_null();
3327 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3328 let result = ylong_json_print_unformatted(object);
3329 let result = CString::from_raw(result).into_string().unwrap();
3330 assert_eq!(result, "{\"null\":null}");
3331 let item = ylong_json_create_bool(1);
3332 assert_eq!(ylong_json_replace_item_of_object_node(node, item), 1);
3333 let result = ylong_json_print_unformatted(object);
3334 let result = CString::from_raw(result).into_string().unwrap();
3335 assert_eq!(result, "{\"null\":true}");
3336 ylong_json_delete(object);
3337 let _ = Box::from_raw(str);
3338 }
3339 }
3340
3341 /// UT test for `ylong_json_remove_object_node`.
3342 ///
3343 /// # Title
3344 /// ut_ylong_json_remove_object_node
3345 ///
3346 /// # Brief
3347 /// 1. Calls `ylong_json_remove_object_node` to remove an object node.
3348 /// 2. Checks if the test results are correct.
3349 #[cfg(feature = "list_object")]
3350 #[test]
ut_ylong_json_remove_object_node()3351 fn ut_ylong_json_remove_object_node() {
3352 unsafe {
3353 // Null ptr
3354 let node = null_mut();
3355 let item = ylong_json_remove_object_node(node);
3356 assert!(item.is_null());
3357
3358 let object = ylong_json_create_object();
3359 let str = str_to_c_char("null");
3360 let item = ylong_json_create_null();
3361 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3362 let _ = Box::from_raw(str);
3363 let result = ylong_json_print_unformatted(object);
3364 let result = CString::from_raw(result).into_string().unwrap();
3365 assert_eq!(result, "{\"null\":null}");
3366 let item = ylong_json_remove_object_node(node);
3367 assert_eq!(ylong_json_is_null(item), 1);
3368 let result = ylong_json_print_unformatted(object);
3369 let result = CString::from_raw(result).into_string().unwrap();
3370 assert_eq!(result, "{}");
3371 ylong_json_delete(item);
3372 ylong_json_delete(object);
3373 }
3374 }
3375
3376 /// UT test for `ylong_json_delete_object_node`.
3377 ///
3378 /// # Title
3379 /// ut_ylong_json_delete_object_node
3380 ///
3381 /// # Brief
3382 /// 1. Calls `ylong_json_delete_object_node` to delete an object node.
3383 /// 2. Checks if the test results are correct.
3384 #[cfg(feature = "list_object")]
3385 #[test]
ut_ylong_json_delete_object_node()3386 fn ut_ylong_json_delete_object_node() {
3387 unsafe {
3388 // Null ptr scene, the process is correct if it exits without exception.
3389 let node = null_mut();
3390 ylong_json_delete_object_node(node);
3391
3392 let object = ylong_json_create_object();
3393 let str = str_to_c_char("null");
3394 let item = ylong_json_create_null();
3395 let node = ylong_json_add_item_to_object_then_get_node(object, str, item);
3396 let result = ylong_json_print_unformatted(object);
3397 let result = CString::from_raw(result).into_string().unwrap();
3398 assert_eq!(result, "{\"null\":null}");
3399 ylong_json_delete_object_node(node);
3400 let result = ylong_json_print_unformatted(object);
3401 let result = CString::from_raw(result).into_string().unwrap();
3402 assert_eq!(result, "{}");
3403 let _ = Box::from_raw(str);
3404 ylong_json_delete(object);
3405 }
3406 }
3407 }
3408