Skip to content

Commit af48aea

Browse files
authored
refactor the code base to align with rfc9535,
* refactor rfc9535, moved one test to todo since it caused the panic (a bug in the jspath) * add the suite * add readme to rfc * fix some parts in parser for slices * add test-suite * remove ( ) for filter * fix () * fix some tests * add slices * fix some tests * obj in filter * add slice restr * fix slice * add q heck * add neg for idx * add fix for some detail * add parser * add parser * add 9535 grammar pest file * add grammar * add model * add literal * add test mod * add sing query * add slice * add part grammar * add part to parse * add tests * add tests * add + 1 * add selectors * add fns * change sign * add eq * add eq neq * add test fn * add processing * add * fix some tests * add fix * add tests * add fix * fix some tests * fix some tests * tests * fix tests * add changes * add tests * add des * add changes * add custom extentions * rem prev mods * add docs * fix mut * fix some tests * fix some tests * change rem opt * upd doc test * rem cow * add privacy for pointer * add changes * fix one test * add tests * add upd for tests * add 2 tests to filter * add changes for tests and reformat
1 parent bfaa1f2 commit af48aea

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

44 files changed

+5117
-15901
lines changed

.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
/target
2+
**/target
23
.idea
34
Cargo.lock
45
.DS_Store

.gitmodules

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
[submodule "rfc9535/test_suite/jsonpath-compliance-test-suite"]
2+
path = rfc9535/test_suite/jsonpath-compliance-test-suite
3+
url = https://github.com/jsonpath-standard/jsonpath-compliance-test-suite.git

CHANGELOG.md

+4-1
Original file line numberDiff line numberDiff line change
@@ -59,4 +59,7 @@
5959
- **`0.7.3`**
6060
- make some methods public
6161
- **`0.7.5`**
62-
- add reference and reference_mut methods
62+
- add reference and reference_mut methods
63+
- **`1.0.1`**
64+
- introduced breaking changes to the API to make it compliant with the RFC9535
65+

Cargo.toml

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
[package]
22
name = "jsonpath-rust"
33
description = "The library provides the basic functionality to find the set of the data according to the filtering query."
4-
version = "0.7.5"
4+
version = "1.0.0"
55
authors = ["BorisZhguchev <[email protected]>"]
66
edition = "2021"
77
license = "MIT"
@@ -14,14 +14,14 @@ categories = ["development-tools", "parsing", "text-processing"]
1414
[dependencies]
1515
serde_json = "1.0"
1616
regex = "1"
17-
pest = "2.0"
18-
pest_derive = "2.0"
17+
pest = "2.7.15"
18+
pest_derive = "2.7.15"
1919
thiserror = "2.0.9"
2020

2121
[dev-dependencies]
2222
serde = { version = "1.0", features = ["derive"] }
2323
criterion = "0.5.1"
24-
colored = "2"
24+
2525

2626
[[bench]]
2727
name = "regex"

README.md

+137-230
Large diffs are not rendered by default.

benches/equal.rs

+13-10
Original file line numberDiff line numberDiff line change
@@ -1,33 +1,36 @@
11
use criterion::{criterion_group, criterion_main, Criterion};
2-
use jsonpath_rust::{JsonPath, JsonPathQuery};
3-
use serde_json::json;
4-
use std::str::FromStr;
2+
3+
use jsonpath_rust::parser::model::JpQuery;
4+
use jsonpath_rust::parser::parse_json_path;
5+
use jsonpath_rust::query::state::State;
6+
use jsonpath_rust::query::Query;
7+
use jsonpath_rust::JsonPath;
8+
use serde_json::{json, Value};
59

610
struct SearchData {
7-
json: serde_json::Value,
8-
path: JsonPath,
11+
json: Value,
12+
path: JpQuery,
913
}
1014

11-
const PATH: &str = "$.[?(@.author == 'abcd(Rees)')]";
15+
const PATH: &str = "$[?@.author == 'abcd(Rees)']";
1216

1317
fn equal_perf_test_with_reuse(cfg: &SearchData) {
14-
let _v = cfg.path.find(&cfg.json);
18+
let _v = cfg.path.process(State::root(&cfg.json)).data;
1519
}
16-
1720
fn equal_perf_test_without_reuse() {
1821
let json = Box::new(json!({
1922
"author":"abcd(Rees)",
2023
}));
2124

22-
let _v = json.path(PATH).expect("the path is correct");
25+
let _v = json.query(PATH).expect("the path is correct");
2326
}
2427

2528
pub fn criterion_benchmark(c: &mut Criterion) {
2629
let data = SearchData {
2730
json: json!({
2831
"author":"abcd(Rees)",
2932
}),
30-
path: JsonPath::from_str(PATH).unwrap(),
33+
path: parse_json_path(PATH).unwrap(),
3134
};
3235
c.bench_function("equal bench with reuse", |b| {
3336
b.iter(|| equal_perf_test_with_reuse(&data))

benches/regex.rs

+12-9
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,40 @@
11
use criterion::{criterion_group, criterion_main, Criterion};
2-
use jsonpath_rust::{JsonPath, JsonPathQuery};
2+
use jsonpath_rust::parser::model::JpQuery;
3+
use jsonpath_rust::parser::parse_json_path;
4+
use jsonpath_rust::query::state::State;
5+
use jsonpath_rust::query::Query;
6+
use jsonpath_rust::JsonPath;
37
use serde_json::{json, Value};
4-
use std::str::FromStr;
58

69
struct SearchData {
7-
json: serde_json::Value,
8-
path: JsonPath,
10+
json: Value,
11+
path: JpQuery,
912
}
1013

11-
const PATH: &str = "$.[?(@.author ~= '.*(?i)d\\(Rees\\)')]";
14+
const PATH: &str = "$[?search(@.author,'.*(?i)d\\\\(Rees\\\\)')]";
1215

1316
fn regex_perf_test_with_reuse(cfg: &SearchData) {
14-
let _v = cfg.path.find(&cfg.json);
17+
let _v = cfg.path.process(State::root(&cfg.json)).data;
1518
}
1619

1720
fn regex_perf_test_without_reuse() {
1821
let json = Box::new(json!({
1922
"author":"abcd(Rees)",
2023
}));
2124

22-
let _v = json.path(PATH).expect("the path is correct");
25+
let _v = json.query(PATH).expect("the path is correct");
2326
}
2427

2528
fn json_path_compiling() {
26-
let _v = JsonPath::<Value>::from_str(PATH).unwrap();
29+
let _v = parse_json_path(PATH).unwrap();
2730
}
2831

2932
pub fn criterion_benchmark(c: &mut Criterion) {
3033
let data = SearchData {
3134
json: json!({
3235
"author":"abcd(Rees)",
3336
}),
34-
path: JsonPath::from_str(PATH).unwrap(),
37+
path: parse_json_path(PATH).unwrap(),
3538
};
3639
c.bench_function("regex bench with reuse", |b| {
3740
b.iter(|| regex_perf_test_with_reuse(&data))

examples/hello-world.rs

-12
This file was deleted.

rfc9535/Cargo.toml

+15
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
[package]
2+
name = "jsonpath-rust-rfc9535"
3+
description = "The tests to check the compliance with RFC 9535"
4+
version = "0.0.1"
5+
edition = "2021"
6+
license = "MIT"
7+
readme = "README.md"
8+
9+
10+
[dependencies]
11+
jsonpath-rust = { path = "../" }
12+
serde_json = "1.0"
13+
serde = { version = "1.0.217", features = ["derive"] }
14+
colored = "2.0"
15+
chrono = "0.4.39"

rfc9535/README.md

+31
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
# Tests for RFC9535
2+
3+
This directory contains tests for the [RFC9535](https://www.rfc-editor.org/info/rfc9535) implementation.
4+
The tests can be downloaded using `prepare.sh` script.
5+
6+
## Usage
7+
Run the main.rs.
8+
It will print the test results in the console with the following format:
9+
```
10+
...
11+
Skipping test case: `<name>` because of reason: `reason`
12+
...
13+
Failed tests:
14+
15+
------- <name> -------
16+
<reason>
17+
18+
...
19+
20+
RFC9535 Compliance tests:
21+
Total: 671
22+
Passed: 209
23+
Failed: 462
24+
Skipped: 25 where 18 to fix in 5 issues
25+
26+
```
27+
28+
The results will be saved in the `results.csv` file.
29+
30+
The cases can be filtered using `filtered_cases.json` file.
31+
The file should contain json array with the test case names that should be filtered out and the reason.

rfc9535/src/console.rs

+79
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
use crate::suite::TestFailure;
2+
use chrono::Local;
3+
use colored::Colorize;
4+
use std::fs::{File, OpenOptions};
5+
use std::io::Write;
6+
use std::io::{BufRead, BufReader, Error};
7+
pub fn process_results(
8+
results: Vec<TestResult>,
9+
skipped_cases: usize,
10+
skipped_to_fix: usize,
11+
issues: usize,
12+
) -> Result<(), Error> {
13+
let (passed, failed): (Vec<_>, Vec<_>) = results.into_iter().partition(TestResult::is_ok);
14+
let total = passed.len() + failed.len() + skipped_cases;
15+
let passed_count = passed.len();
16+
let failed_count = failed.len();
17+
let date = Local::now().format("%Y-%m-%d %H:%M:%S").to_string();
18+
19+
if failed_count > 0 {
20+
println!("\n{}:", "Failed tests".bold());
21+
println!("\n");
22+
}
23+
for failure in failed.iter() {
24+
if let Err(TestFailure(case, reason)) = failure {
25+
println!(" ------- {} -------", case.name.bold());
26+
println!("{}", reason.bold().red());
27+
}
28+
}
29+
30+
let mut file = OpenOptions::new()
31+
.create(true)
32+
.append(true)
33+
.open("test_suite/results.csv")?;
34+
writeln!(
35+
file,
36+
"{}; {}; {}; {}",
37+
total, passed_count, failed_count, date
38+
)?;
39+
40+
clean_file(10)?;
41+
42+
println!(
43+
"\n{}:\n{}\n{}\n{}\n{}",
44+
format!("RFC9535 Compliance tests").underline().bold(),
45+
format!("Total: {}", total).bold(),
46+
format!("Passed: {}", passed_count).green().bold(),
47+
format!("Failed: {}", failed_count).red().bold(),
48+
format!(
49+
"Skipped: {} where {} to fix in {} issues",
50+
skipped_cases, skipped_to_fix, issues
51+
)
52+
.bold()
53+
);
54+
Ok(())
55+
}
56+
57+
fn clean_file(limit: usize) -> Result<(), Error> {
58+
let file_path = "test_suite/results.csv";
59+
let file = File::open(file_path)?;
60+
let reader = BufReader::new(file);
61+
let lines: Vec<String> = reader.lines().collect::<Result<_, _>>()?;
62+
63+
if lines.len() > limit {
64+
let header = &lines[0];
65+
let trimmed_lines = [&[header.clone()], &lines[lines.len() - limit..]].concat();
66+
67+
let mut file = OpenOptions::new()
68+
.write(true)
69+
.truncate(true)
70+
.open(file_path)?;
71+
for line in trimmed_lines {
72+
writeln!(file, "{}", line)?;
73+
}
74+
}
75+
76+
Ok(())
77+
}
78+
79+
pub type TestResult<'a> = Result<(), TestFailure<'a>>;

rfc9535/src/main.rs

+23
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
2+
mod console;
3+
mod suite;
4+
use crate::suite::get_suite;
5+
use colored::Colorize;
6+
use console::TestResult;
7+
use std::io::Error;
8+
use std::io::Write;
9+
use std::str::FromStr;
10+
11+
fn main() -> Result<(), Error> {
12+
let (cases, skipped, skipped_to_fix, issues) = get_suite()?;
13+
console::process_results(
14+
cases
15+
.iter()
16+
.map(suite::handle_test_case)
17+
.collect::<Vec<TestResult>>(),
18+
skipped,
19+
skipped_to_fix,
20+
issues,
21+
)
22+
}
23+

0 commit comments

Comments
 (0)