mirror of
https://github.com/fluencelabs/jsonpath
synced 2025-04-25 09:22:19 +00:00
58 lines
1.8 KiB
Rust
58 lines
1.8 KiB
Rust
|
use std::ffi::{CStr, CString};
|
||
|
use std::os::raw::{c_char, c_void};
|
||
|
|
||
|
use {parser, select, select_as_str};
|
||
|
|
||
|
const INVALID_PATH: &str = "invalid path";
|
||
|
const INVALID_JSON: &str = "invalud json";
|
||
|
|
||
|
fn to_str(v: *const c_char, err_msg: &str) -> &str {
|
||
|
unsafe { CStr::from_ptr(v) }.to_str().expect(err_msg)
|
||
|
}
|
||
|
|
||
|
fn to_char_ptr(v: &str) -> *const c_char {
|
||
|
let s = CString::new(v).expect(&format!("invalid string: {}", v));
|
||
|
let ptr = s.as_ptr();
|
||
|
std::mem::forget(s);
|
||
|
ptr
|
||
|
}
|
||
|
|
||
|
#[no_mangle]
|
||
|
pub extern "C" fn ffi_select(json_str: *const c_char, path: *const c_char) -> *const c_char {
|
||
|
let json_str = to_str(json_str, INVALID_JSON);
|
||
|
let path = to_str(path, INVALID_PATH);
|
||
|
match select_as_str(json_str, path) {
|
||
|
Ok(v) => to_char_ptr(v.as_str()),
|
||
|
Err(e) => {
|
||
|
panic!("{:?}", e);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
#[no_mangle]
|
||
|
pub extern "C" fn ffi_path_compile(path: *const c_char) -> *mut c_void {
|
||
|
let path = to_str(path, INVALID_PATH);
|
||
|
let ref_node = Box::into_raw(Box::new(parser::Parser::compile(path).unwrap()));
|
||
|
let ptr = ref_node as *mut c_void;
|
||
|
std::mem::forget(ref_node);
|
||
|
ptr
|
||
|
}
|
||
|
|
||
|
#[no_mangle]
|
||
|
pub extern "C" fn ffi_select_with_compiled_path(
|
||
|
path_ptr: *mut c_void,
|
||
|
json_ptr: *const c_char,
|
||
|
) -> *const c_char {
|
||
|
let node = unsafe { Box::from_raw(path_ptr as *mut parser::Node) };
|
||
|
let json_str = to_str(json_ptr, INVALID_JSON);
|
||
|
let json = serde_json::from_str(json_str).expect(&format!("invalid json string: {}", json_str));
|
||
|
|
||
|
let mut selector = select::Selector::default();
|
||
|
let found = selector.compiled_path(&node).value(&json).select().unwrap();
|
||
|
std::mem::forget(node);
|
||
|
|
||
|
let result =
|
||
|
serde_json::to_string(&found).expect(&format!("json serialize error: {:?}", found));
|
||
|
to_char_ptr(result.as_str())
|
||
|
}
|