JSON Patch
JSON Patch (RFC 6902) and Merge Patch (RFC 7396): the difference between two values as operations, and patches applied.
Version 1.0.0 · 3 functions · 1 crate
Functions
What use json_patch.qwer gives a program, with the types Quillo sees. To take only some, or under other names: use json_diff, json_patch_apply from json_patch (Quillo 0.6).
json_diff(before: any, after: any) → anyor an errorThe RFC 6902 patch that turns before into after: a list of { op, path, value } (add, remove, replace), empty when they are equal.
json_patch_apply(value: any, patch: any) → anyor an errorvalue with an RFC 6902 patch applied (add, remove, replace, move, copy and test). All or nothing: when one operation fails (a path that is not there, a test that does not hold), the error names it and nothing is applied.
json_merge(value: any, merge_patch: any) → anyvalue with an RFC 7396 merge patch applied: the patch's keys replace the value's, null removes a key, maps merge all the way down, lists are replaced whole. What most PATCH endpoints take.
Get it
$ quillo install json_patch # json_patch.qwer into this folder$ quillo install json_patch --example # and its example, json_patch.qweOr with curl:
$ curl -O https://quillolang.org/plugins/files/json_patch.qwer$ curl -O https://quillolang.org/plugins/files/json_patch.qweThen, in your program, all of it or only what you call:
use json_patch.qweruse json_diff, json_patch_apply from json_patch // Quillo 0.6: only theseIt uses this crate, which cargo fetches the first time the plugin is built:
json-patch = "3"Example
// A PATCH endpoint that takes merge patches, an undo built from the diff, and a change history.//// quillo run json_patch.qwe then open http://localhost:8080/historyuse "json_patch.qwer"let product = { sku: "B7", name: "Blue mug", price: 12.5, tags: ["kitchen", "blue"], stock: { amsterdam: 4, london: 0 } }route PATCH /products/b7 = json_merge(product, request.json)route GET /history { let after = json_merge(product, { price: 11.0, tags: ["kitchen", "blue", "sale"], stock: { london: 12 }, name: null }) let change = json_diff(product, after)? let undo = json_diff(after, product)? { after, change, undone: json_patch_apply(after, undo)? == product }}route GET /apply { let patch = [{ op: "test", path: "/price", value: 12.5 }, { op: "replace", path: "/price", value: 9.99 }, { op: "add", path: "/tags/-", value: "gift" }] { patched: json_patch_apply(product, patch)?, stale: json_patch_apply(json_merge(product, { price: 13 }), patch).error }}$ quillo run json_patch.qwe$ curl 'localhost:8080/history'$ curl 'localhost:8080/apply'Source
//! JSON Patch (RFC 6902) and JSON Merge Patch (RFC 7396): the difference between two values as a list of operations, and patches applied, for PATCH endpoints, undo and audit trails.//! version: 1.0.0//!//! [dependencies]//! json-patch = "3"use serde_json::Value;/// The RFC 6902 patch that turns `before` into `after`: a list of `{ op, path, value }` (`add`, `remove`, `replace`), empty when they are equal.pub fn json_diff(before: serde_json::Value, after: serde_json::Value) -> Result<Value, String> { serde_json::to_value(json_patch::diff(&before, &after)).map_err(|e| e.to_string())}/// `value` with an RFC 6902 `patch` applied (`add`, `remove`, `replace`, `move`, `copy` and `test`). All or nothing: when one/// operation fails (a path that is not there, a `test` that does not hold), the error names it and nothing is applied.pub fn json_patch_apply(value: serde_json::Value, patch: serde_json::Value) -> Result<Value, String> { let p: json_patch::Patch = serde_json::from_value(patch).map_err(|e| format!("not a JSON Patch (a list of {{ op, path, ... }}): {}", e))?; if p.0.len() > 10_000 { return Err("at most 10,000 operations".into()); } let mut v = value; json_patch::patch(&mut v, &p).map_err(|e| e.to_string())?; Ok(v)}/// `value` with an RFC 7396 merge patch applied: the patch's keys replace the value's, `null` removes a key, maps merge all/// the way down, lists are replaced whole. What most PATCH endpoints take.pub fn json_merge(value: serde_json::Value, merge_patch: serde_json::Value) -> Value { let mut v = value; json_patch::merge(&mut v, &merge_patch); v}Related
fhir.qwer · 1.0.0HL7 FHIR R4 JSON: resources checked for required fields, bound codes and date formats, Bundles read and built, references resolved across a Bundle, FHIRPath-lite field access, and search parameters with paging, sorting and includes for a FHIR server.3 views · 7 downloadsJSON Schema json_schema.qwer · 1.0.0Check values against a JSON Schema (drafts 4 to 2020-12), with every error and the path of the value at fault.8 views · 8 downloadsJSONPath jsonpath.qwer · 1.0.0Query values with JSONPath (RFC 9535): filters, slices, recursive descent and functions, with the paths of what matched.8 views · 7 downloadsCanonical JSON json_canonical.qwer · 1.0.0Canonical JSON (RFC 8785): one way to write a value, keys sorted and numbers as JavaScript writes them, so hashes and signatures of JSON hold however it was spaced or ordered.7 views · 5 downloadsJSON Lines ndjson.qwer · 1.0.0JSON Lines (NDJSON) read a page at a time from files of any size, searched by field, appended to and written: logs, exports and imports.7 views · 6 downloadsJSON5 json5.qwer · 1.0.0JSON5 and JSON with comments read as values: tsconfig.json and editor settings, with comments, trailing commas and unquoted keys.7 views · 8 downloadsThread 0 posts
On JSON Patch: questions, tips, corrections, and code that uses it.
No posts yet. The first one opens the thread.