jsondata 0.7.0

JSON processing package for document databases
Documentation
Why yet another JSON package in Rust ?
======================================

[![Rustdoc](https://img.shields.io/badge/rustdoc-hosted-blue.svg)](https://docs.rs/jsondata)
[![GitPitch](https://gitpitch.com/assets/badge.svg)](https://gitpitch.com/bnclabs/jsondata/master?grs=github)
[![Build Status](https://travis-ci.org/bnclabs/jsondata.svg?branch=master)](https://travis-ci.org/bnclabs/jsondata)

This crate makes several trade-offs that are tuned for big-data
and document database.

* [x] Support for 128-bit signed integers.
* [x] Deferred conversion for JSON numbers.
* [x] Serialization from Rust native type to JSON text.
* [x] De-serialization from JSON text to Rust native type.
* [x] CRUD operation on JSON documents, using [JSON Pointer][jptr].
* [x] Sorted keys in property object.
* [x] Streaming JSON parser.
* [x] Support [JSON5]http://json5.org standard.
* [x] Common arithmetic and logic operations.
* [x] Sortable JSON.

**Useful links**

* **[API Documentation]https://docs.rs/jsondata**
* [JSON Pointer][jptr].
* [JSON5][json5].
* Rust [internal discussion][rust1]  on f64 -> integer.
* [Json sort order][json-sort-order].
* [Json operations][json-ops].
* [Release notes]./RELEASE.md.

Deferred conversion for numbers
===============================

Converting JSON numbers to Rust native type is not always desired.
Especially in the context of big-data where data is stored in JSON
format and we need to lookup, only, specific fields within the document.

This implementation provides deferred conversion for JSON numbers
that leads to a **[performance improvement of upto 30%][commit-deferred]**.

CRUD operations on JSON document
================================

Using Json Pointer it is possible to identify a specific field nested within
a JSON document. For Example, with below document:

```json
  {
    "age": 26,
    "eyeColor": "green",
    "name": "Leon Robertson",
    "gender": "male",
    "company": "AEORA",
    "phone": "+1 (835) 447-2960",
    "tags": [ "officia", "reprehenderit", "magna" ],
    "friends": [
      {
        "id": 0,
        "name": "Glenda Chan"
      }
    ]
  }
```

* **/age** shall point to value ``26``.
* **/tags** shall point to value ``[ "officia", "reprehenderit", "magna" ]``.
* **/tags/0** shall point to value ``"officia"``.
* **/friends** shall point to value ``[{"id": 0, "name": "Glenda Chan"}]``.
* **/friends/name** shall point to value ``"Glenda Chan"``.

**List of operations**

* [x] Get a field nested within a JSON document using [JSON Pointer][jptr].
* [x] Set a field nested within a JSON document.
* [x] Delete a field nested within a JSON document.
* [x] Append string or array field withing a JSON document.

JSON5
=====

* [x] Object keys may be an ECMAScript 5.1 IdentifierName.
* [x] Objects may have a single trailing comma.
* [x] Arrays may have a single trailing comma.
* [ ] Strings may be single quoted.
* [ ] Strings may span multiple lines by escaping new line characters.
* [ ] Strings may include character escapes.
* [x] Numbers may be hexadecimal.
* [x] Numbers may have a leading or trailing decimal point.
* [x] Numbers may be IEEE 754 positive infinity, negative infinity, and NaN.
* [x] Numbers may begin with an explicit plus sign.
* [ ] Single and multi-line comments are allowed.
* [x] Additional white space characters are allowed.

**[Track this feature](https://github.com/bnclabs/jsondata/issues/4)**.

Sortable JSON
=============

* **Null** type shall sort before all other types.
* **Boolean** type shall sort after Null type.
* **Number** type shall sort after Boolean type.
  * f64 values that are <= -2^127 will sort before all i128 integers.
  * f64 values that are >= 2^127-1 will sort after all i128 integers.
  * NaN, Not a Number, values shall sort after all i128 integers
  * **-Infinity** shall sort before all numbers.
  * **+Infinity** shall sort after all numbers.
  * **NaN** shall sort after +Infinity.
* **String** type shall sort after Number type.
* **Array** type shall sort after String type.
* **Object** type shall sort after Array type.
  * All (key,value) pairs within the object shall be presorted based
    on the key.
  * When comparing two objects, comparison shall start from first key
    and proceed to the last key.
  * If two keys are equal at a given position within the objects, then
    its corresponding values shall be compared.
  * When one object is a subset of another object, as in, if one object
    contain all the (key,value) properties that the other object has
    then it shall sort before the other object.

**Useful links**

- **[A detailed description of JSON sort order][json-sort-order]**.
- Rust-lang [issue#46298]https://github.com/rust-lang/rust/issues/46298 and
  [issue#10184]https://github.com/rust-lang/rust/issues/10184,
  discussing saturating cast of f64 -> integer.
- Rust [internal discussion][rust1]  on f64 -> integer.
- Unicode collation [TR10]http://unicode.org/reports/tr10.
- [ICU collation]http://userguide.icu-project.org/collation.
- Floating point [Total ordering][fp-total-order]
- Total ordering for floating point in [stackoverflow][sf1].
- [Total ordering thread]https://users.rust-lang.org/t/sort-order-for-json/24166
  in http://users.rust-lang.org.
- A good [blog][blog1] on floating point, to get started.

Operations on JSON documents
============================

* Arithmetic operations, ADD, SUB, MUL, DIV, REM, NEG.
* Bitwise operations, SHL, SHR, BITAND, BITOR, BITXOR.
* Logical operations, NOT, AND, OR.
* Index operations.
* Range operations.

**[Detailed description can be found here][json-ops].**

Contribution
------------

* Simple workflow. Fork - Modify - Pull request.
* Before creating a PR,
  * Run `make build` to confirm all versions of build is passing with
    0 warnings and 0 errors.
  * Run `check.sh` with 0 warnings, 0 errors and all testcases passing.
  * Run `perf.sh` with 0 warnings, 0 errors and all testcases passing.
  * [Install][spellcheck] and run `cargo spellcheck` to remove common spelling mistakes.
* [Developer certificate of origin][dco] is preferred.

[commit-deferred]: https://github.com/bnclabs/jsondata/commit/70e6dedf0121f16e130f224daaa23948f5a5d782
[json5]: http://json5.org
[jptr]: https://tools.ietf.org/html/rfc6901
[#1]: https://github.com/bnclabs/jsondata/issues/1
[#3]: https://github.com/bnclabs/jsondata/issues/3
[#4]: https://github.com/bnclabs/jsondata/issues/4
[#13]: https://github.com/bnclabs/jsondata/issues/13
[json-sort-order]: https://prataprc.github.io/json-sort-order.html
[json-ops]: https://prataprc.github.io/json-operations.html
[rust1]: https://internals.rust-lang.org/t/help-us-benchmark-saturating-float-casts/6231
[sf1]: https://stackoverflow.com/questions/8341395/what-is-a-subnormal-floating-point-number
[fp-total-order]: https://en.m.wikipedia.org/wiki/IEEE_754#Total-ordering_predicate
[blog1]: https://steve.hollasch.net/cgindex/coding/ieeefloat.html
[MIT license]: https://opensource.org/licenses/MIT