pygjson 0.0.1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,92 @@
1
+ name: Publish to PyPI
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - "v*"
7
+
8
+ permissions:
9
+ contents: read
10
+
11
+ jobs:
12
+ build-wheels:
13
+ name: Build wheels on ${{ matrix.os }}
14
+ runs-on: ${{ matrix.os }}
15
+ strategy:
16
+ matrix:
17
+ include:
18
+ - os: ubuntu-latest
19
+ target: x86_64
20
+ - os: ubuntu-latest
21
+ target: aarch64
22
+ - os: windows-latest
23
+ target: x86_64
24
+ - os: windows-latest
25
+ target: aarch64
26
+ - os: macos-latest
27
+ target: x86_64
28
+ - os: macos-latest
29
+ target: aarch64
30
+
31
+ steps:
32
+ - uses: actions/checkout@v6
33
+
34
+ - name: Build wheels
35
+ uses: PyO3/maturin-action@v1
36
+ with:
37
+ target: ${{ matrix.target }}
38
+ args: --release --out dist
39
+ sccache: "true"
40
+ manylinux: auto
41
+ env:
42
+ PYO3_USE_ABI3_FORWARD_COMPATIBILITY: 1
43
+
44
+ - name: Upload wheels
45
+ uses: actions/upload-artifact@v6
46
+ with:
47
+ name: wheels-${{ matrix.os }}-${{ matrix.target }}
48
+ path: dist
49
+
50
+ build-sdist:
51
+ name: Build source distribution
52
+ runs-on: ubuntu-latest
53
+ steps:
54
+ - uses: actions/checkout@v6
55
+
56
+ - name: Build sdist
57
+ uses: PyO3/maturin-action@v1
58
+ with:
59
+ command: sdist
60
+ args: --out dist
61
+
62
+ - name: Upload sdist
63
+ uses: actions/upload-artifact@v6
64
+ with:
65
+ name: sdist
66
+ path: dist
67
+
68
+ publish:
69
+ name: Publish to PyPI
70
+ runs-on: ubuntu-latest
71
+ needs: [build-wheels, build-sdist]
72
+ permissions:
73
+ id-token: write
74
+ environment:
75
+ name: pypi
76
+ url: https://pypi.org/p/pygjson
77
+ steps:
78
+ - name: Download all artifacts
79
+ uses: actions/download-artifact@v4
80
+ with:
81
+ pattern: wheels-*
82
+ merge-multiple: true
83
+ path: dist
84
+
85
+ - name: Download sdist
86
+ uses: actions/download-artifact@v4
87
+ with:
88
+ name: sdist
89
+ path: dist
90
+
91
+ - name: Publish to PyPI
92
+ uses: pypa/gh-action-pypi-publish@release/v1
@@ -0,0 +1,9 @@
1
+ target/
2
+ .venv/
3
+ *.so
4
+ __pycache__/
5
+ *.egg-info/
6
+ dist/
7
+ build/
8
+ .pytest_cache/
9
+ Cargo.lock
@@ -0,0 +1,219 @@
1
+ # This file is automatically @generated by Cargo.
2
+ # It is not intended for manual editing.
3
+ version = 4
4
+
5
+ [[package]]
6
+ name = "autocfg"
7
+ version = "1.5.0"
8
+ source = "registry+https://github.com/rust-lang/crates.io-index"
9
+ checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8"
10
+
11
+ [[package]]
12
+ name = "cc"
13
+ version = "1.2.59"
14
+ source = "registry+https://github.com/rust-lang/crates.io-index"
15
+ checksum = "b7a4d3ec6524d28a329fc53654bbadc9bdd7b0431f5d65f1a56ffb28a1ee5283"
16
+ dependencies = [
17
+ "find-msvc-tools",
18
+ "shlex",
19
+ ]
20
+
21
+ [[package]]
22
+ name = "cfg-if"
23
+ version = "1.0.4"
24
+ source = "registry+https://github.com/rust-lang/crates.io-index"
25
+ checksum = "9330f8b2ff13f34540b44e946ef35111825727b38d33286ef986142615121801"
26
+
27
+ [[package]]
28
+ name = "find-msvc-tools"
29
+ version = "0.1.9"
30
+ source = "registry+https://github.com/rust-lang/crates.io-index"
31
+ checksum = "5baebc0774151f905a1a2cc41989300b1e6fbb29aff0ceffa1064fdd3088d582"
32
+
33
+ [[package]]
34
+ name = "gjson"
35
+ version = "0.8.1"
36
+ source = "registry+https://github.com/rust-lang/crates.io-index"
37
+ checksum = "43503cc176394dd30a6525f5f36e838339b8b5619be33ed9a7783841580a97b6"
38
+
39
+ [[package]]
40
+ name = "heck"
41
+ version = "0.5.0"
42
+ source = "registry+https://github.com/rust-lang/crates.io-index"
43
+ checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea"
44
+
45
+ [[package]]
46
+ name = "indoc"
47
+ version = "2.0.7"
48
+ source = "registry+https://github.com/rust-lang/crates.io-index"
49
+ checksum = "79cf5c93f93228cf8efb3ba362535fb11199ac548a09ce117c9b1adc3030d706"
50
+ dependencies = [
51
+ "rustversion",
52
+ ]
53
+
54
+ [[package]]
55
+ name = "libc"
56
+ version = "0.2.184"
57
+ source = "registry+https://github.com/rust-lang/crates.io-index"
58
+ checksum = "48f5d2a454e16a5ea0f4ced81bd44e4cfc7bd3a507b61887c99fd3538b28e4af"
59
+
60
+ [[package]]
61
+ name = "memoffset"
62
+ version = "0.9.1"
63
+ source = "registry+https://github.com/rust-lang/crates.io-index"
64
+ checksum = "488016bfae457b036d996092f6cb448677611ce4449e970ceaf42695203f218a"
65
+ dependencies = [
66
+ "autocfg",
67
+ ]
68
+
69
+ [[package]]
70
+ name = "once_cell"
71
+ version = "1.21.4"
72
+ source = "registry+https://github.com/rust-lang/crates.io-index"
73
+ checksum = "9f7c3e4beb33f85d45ae3e3a1792185706c8e16d043238c593331cc7cd313b50"
74
+
75
+ [[package]]
76
+ name = "portable-atomic"
77
+ version = "1.13.1"
78
+ source = "registry+https://github.com/rust-lang/crates.io-index"
79
+ checksum = "c33a9471896f1c69cecef8d20cbe2f7accd12527ce60845ff44c153bb2a21b49"
80
+
81
+ [[package]]
82
+ name = "proc-macro2"
83
+ version = "1.0.106"
84
+ source = "registry+https://github.com/rust-lang/crates.io-index"
85
+ checksum = "8fd00f0bb2e90d81d1044c2b32617f68fcb9fa3bb7640c23e9c748e53fb30934"
86
+ dependencies = [
87
+ "unicode-ident",
88
+ ]
89
+
90
+ [[package]]
91
+ name = "pygjson"
92
+ version = "0.0.1"
93
+ dependencies = [
94
+ "gjson",
95
+ "pyo3",
96
+ ]
97
+
98
+ [[package]]
99
+ name = "pyo3"
100
+ version = "0.22.6"
101
+ source = "registry+https://github.com/rust-lang/crates.io-index"
102
+ checksum = "f402062616ab18202ae8319da13fa4279883a2b8a9d9f83f20dbade813ce1884"
103
+ dependencies = [
104
+ "cfg-if",
105
+ "indoc",
106
+ "libc",
107
+ "memoffset",
108
+ "once_cell",
109
+ "portable-atomic",
110
+ "pyo3-build-config",
111
+ "pyo3-ffi",
112
+ "pyo3-macros",
113
+ "unindent",
114
+ ]
115
+
116
+ [[package]]
117
+ name = "pyo3-build-config"
118
+ version = "0.22.6"
119
+ source = "registry+https://github.com/rust-lang/crates.io-index"
120
+ checksum = "b14b5775b5ff446dd1056212d778012cbe8a0fbffd368029fd9e25b514479c38"
121
+ dependencies = [
122
+ "once_cell",
123
+ "python3-dll-a",
124
+ "target-lexicon",
125
+ ]
126
+
127
+ [[package]]
128
+ name = "pyo3-ffi"
129
+ version = "0.22.6"
130
+ source = "registry+https://github.com/rust-lang/crates.io-index"
131
+ checksum = "9ab5bcf04a2cdcbb50c7d6105de943f543f9ed92af55818fd17b660390fc8636"
132
+ dependencies = [
133
+ "libc",
134
+ "pyo3-build-config",
135
+ ]
136
+
137
+ [[package]]
138
+ name = "pyo3-macros"
139
+ version = "0.22.6"
140
+ source = "registry+https://github.com/rust-lang/crates.io-index"
141
+ checksum = "0fd24d897903a9e6d80b968368a34e1525aeb719d568dba8b3d4bfa5dc67d453"
142
+ dependencies = [
143
+ "proc-macro2",
144
+ "pyo3-macros-backend",
145
+ "quote",
146
+ "syn",
147
+ ]
148
+
149
+ [[package]]
150
+ name = "pyo3-macros-backend"
151
+ version = "0.22.6"
152
+ source = "registry+https://github.com/rust-lang/crates.io-index"
153
+ checksum = "36c011a03ba1e50152b4b394b479826cad97e7a21eb52df179cd91ac411cbfbe"
154
+ dependencies = [
155
+ "heck",
156
+ "proc-macro2",
157
+ "pyo3-build-config",
158
+ "quote",
159
+ "syn",
160
+ ]
161
+
162
+ [[package]]
163
+ name = "python3-dll-a"
164
+ version = "0.2.15"
165
+ source = "registry+https://github.com/rust-lang/crates.io-index"
166
+ checksum = "d80ba7540edb18890d444c5aa8e1f1f99b1bdf26fb26ae383135325f4a36042b"
167
+ dependencies = [
168
+ "cc",
169
+ ]
170
+
171
+ [[package]]
172
+ name = "quote"
173
+ version = "1.0.45"
174
+ source = "registry+https://github.com/rust-lang/crates.io-index"
175
+ checksum = "41f2619966050689382d2b44f664f4bc593e129785a36d6ee376ddf37259b924"
176
+ dependencies = [
177
+ "proc-macro2",
178
+ ]
179
+
180
+ [[package]]
181
+ name = "rustversion"
182
+ version = "1.0.22"
183
+ source = "registry+https://github.com/rust-lang/crates.io-index"
184
+ checksum = "b39cdef0fa800fc44525c84ccb54a029961a8215f9619753635a9c0d2538d46d"
185
+
186
+ [[package]]
187
+ name = "shlex"
188
+ version = "1.3.0"
189
+ source = "registry+https://github.com/rust-lang/crates.io-index"
190
+ checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64"
191
+
192
+ [[package]]
193
+ name = "syn"
194
+ version = "2.0.117"
195
+ source = "registry+https://github.com/rust-lang/crates.io-index"
196
+ checksum = "e665b8803e7b1d2a727f4023456bbbbe74da67099c585258af0ad9c5013b9b99"
197
+ dependencies = [
198
+ "proc-macro2",
199
+ "quote",
200
+ "unicode-ident",
201
+ ]
202
+
203
+ [[package]]
204
+ name = "target-lexicon"
205
+ version = "0.12.16"
206
+ source = "registry+https://github.com/rust-lang/crates.io-index"
207
+ checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1"
208
+
209
+ [[package]]
210
+ name = "unicode-ident"
211
+ version = "1.0.24"
212
+ source = "registry+https://github.com/rust-lang/crates.io-index"
213
+ checksum = "e6e4313cd5fcd3dad5cafa179702e2b244f760991f45397d14d4ebf38247da75"
214
+
215
+ [[package]]
216
+ name = "unindent"
217
+ version = "0.2.4"
218
+ source = "registry+https://github.com/rust-lang/crates.io-index"
219
+ checksum = "7264e107f553ccae879d21fbea1d6724ac785e8c3bfc762137959b5802826ef3"
@@ -0,0 +1,13 @@
1
+ [package]
2
+ name = "pygjson"
3
+ version = "0.0.1"
4
+ edition = "2021"
5
+ readme = "README.md"
6
+
7
+ [lib]
8
+ name = "_pygjson"
9
+ crate-type = ["cdylib"]
10
+
11
+ [dependencies]
12
+ pyo3 = { version = "0.22", features = ["extension-module", "abi3-py310", "generate-import-lib"] }
13
+ gjson = "0.8"
pygjson-0.0.1/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 minefuto
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
pygjson-0.0.1/PKG-INFO ADDED
@@ -0,0 +1,162 @@
1
+ Metadata-Version: 2.4
2
+ Name: pygjson
3
+ Version: 0.0.1
4
+ Classifier: Programming Language :: Rust
5
+ Classifier: Programming Language :: Python :: Implementation :: CPython
6
+ License-File: LICENSE
7
+ Summary: Python bindings for gjson.rs - fast JSON path queries
8
+ Requires-Python: >=3.10
9
+ Description-Content-Type: text/markdown; charset=UTF-8; variant=GFM
10
+
11
+ # pygjson
12
+
13
+ PyGJSON is a Python bindings for [tidwall/gjson.rs](https://github.com/tidwall/gjson.rs).
14
+
15
+ The original GJSON: [https://github.com/tidwall/gjson]()
16
+
17
+ ## Installation
18
+
19
+ ```bash
20
+ pip install pygjson
21
+ ```
22
+
23
+
24
+ ## Quick example
25
+
26
+ ```python
27
+ import pygjson
28
+
29
+ JSON = """{
30
+ "name": {"first": "Tom", "last": "Anderson"},
31
+ "age": 37,
32
+ "children": ["Sara", "Alex", "Jack"],
33
+ "friends": [
34
+ {"first": "Dale", "last": "Murphy", "age": 44},
35
+ {"first": "Roger", "last": "Craig", "age": 68},
36
+ {"first": "Jane", "last": "Murphy", "age": 47}
37
+ ]
38
+ }"""
39
+
40
+ str(pygjson.get(JSON, "name.last")) # 'Anderson'
41
+ int(pygjson.get(JSON, "age")) # 37
42
+ int(pygjson.get(JSON, "children.#")) # 3
43
+ str(pygjson.get(JSON, "children.1")) # 'Alex'
44
+ str(pygjson.get(JSON, 'friends.#(last="Murphy").first')) # 'Dale'
45
+
46
+ [str(v) for v in pygjson.get(JSON, "children|@reverse")]
47
+ # ['Jack', 'Alex', 'Sara']
48
+
49
+ pygjson.valid(JSON) # True
50
+ ```
51
+
52
+ ## API
53
+
54
+ ### Module-level functions
55
+
56
+ | Function | Description |
57
+ |-------------------------------|--------------------------------------------------------------|
58
+ | `get(json, path)` | Query `json` at `path`; returns `Value` (gjson-native) |
59
+ | `get(json, path, default)` | Returns `default` if path is not found (Pythonic) |
60
+ | `parse(json)` | Parse the entire JSON document into a `Value` |
61
+ | `valid(json)` | `True` if `json` is syntactically valid |
62
+
63
+ ### Value
64
+
65
+ `get` and `parse` return a `Value`. The API is split into two layers:
66
+
67
+ **gjson-native methods** — mirror the Rust `gjson::Value` API directly:
68
+
69
+ | Method | Description |
70
+ |--------------------|----------------------------------------------------------|
71
+ | `v.kind()` | Returns a `Kind` enum value |
72
+ | `v.exists()` | `True` if the value was actually found in the JSON |
73
+ | `v.to_str()` | String representation (gjson `str` behaviour) |
74
+ | `v.to_int()` | Signed 64-bit integer (`i64`) |
75
+ | `v.to_uint()` | Unsigned 64-bit integer (`u64`) |
76
+ | `v.to_float()` | 64-bit float |
77
+ | `v.to_bool()` | `True` only for the JSON literal `true` |
78
+ | `v.json()` | Raw JSON text for this value |
79
+ | `v.get(path)` | Sub-query relative to this value (gjson-native) |
80
+ | `v.get(path, default)` | Sub-query; returns `default` if not found (Pythonic) |
81
+ | `v.to_list()` | `list[Value]` for arrays |
82
+ | `v.to_dict()` | `dict[str, Value]` for objects |
83
+
84
+ **Pythonic methods** — follow standard Python protocols:
85
+
86
+ | Syntax | Description |
87
+ |---------------------|--------------------------------------------------------------|
88
+ | `str(v)` | String representation |
89
+ | `int(v)` | Integer (negative → `i64`, non-negative → `u64`) |
90
+ | `float(v)` | 64-bit float |
91
+ | `bool(v)` | `True` if `v.exists()` |
92
+ | `len(v)` | Chars for String; element count for Array/Object |
93
+ | `v[key]` | Subscript access for Object values |
94
+ | `key in v` | Key membership for Object; str match for Array elements |
95
+ | `iter(v)` | Chars for String; `Value`s for Array; keys for Object |
96
+ | `v.keys()` | Object keys (raises `TypeError` for non-Object) |
97
+ | `v.values()` | Object values (raises `TypeError` for non-Object) |
98
+ | `v.items()` | `(key, Value)` pairs (raises `TypeError` for non-Object) |
99
+
100
+ ### Kind
101
+
102
+ ```python
103
+ from pygjson import Kind
104
+ Kind.Null Kind.False_ Kind.True_ Kind.Number
105
+ Kind.String Kind.Array Kind.Object
106
+ ```
107
+
108
+ (`False` and `True` are Python keywords, so the variants are named with a
109
+ trailing underscore.)
110
+
111
+ ## Usage examples
112
+
113
+ ```python
114
+ from pygjson import get, parse, valid, Kind
115
+
116
+ # gjson-native: missing value returns Value(exists=False)
117
+ v = get(JSON, "no.such.path")
118
+ v.exists() # False
119
+ bool(v) # False
120
+
121
+ # Pythonic: missing value returns None (or a custom default)
122
+ get(JSON, "no.such.path", None) # None
123
+ get(JSON, "no.such.path", 42) # 42
124
+
125
+ # Type conversion
126
+ age = get(JSON, "age")
127
+ age.to_int() # gjson i64 behaviour
128
+ int(age) # Python int protocol
129
+
130
+ # Boolean distinction
131
+ get('{"flag": true}', "flag").to_bool() # True (JSON true literal)
132
+ bool(get(JSON, "age")) # True (value exists)
133
+
134
+ # Array iteration
135
+ children = get(JSON, "children")
136
+ list(children) # [Value("Sara"), Value("Alex"), Value("Jack")]
137
+ [str(v) for v in children] # ['Sara', 'Alex', 'Jack']
138
+ "Sara" in children # True
139
+
140
+ # Object (dict-like) access
141
+ name = get(JSON, "name")
142
+ name["first"] # Value("Tom")
143
+ "first" in name # True
144
+ list(name) # ['first', 'last'] — keys
145
+ dict(name) # {'first': Value("Tom"), 'last': Value("Anderson")}
146
+ for k, v in name.items():
147
+ print(k, str(v))
148
+
149
+ # Chained queries
150
+ parse(JSON).get("name").get("first") # Value("Tom")
151
+ ```
152
+
153
+ ## Path syntax
154
+
155
+ For the full path / query / modifier syntax see the upstream
156
+ [gjson.rs](https://github.com/tidwall/gjson.rs) and the original
157
+ [GJSON path syntax](https://github.com/tidwall/gjson/blob/master/SYNTAX.md).
158
+
159
+ ## License
160
+
161
+ MIT
162
+
@@ -0,0 +1,151 @@
1
+ # pygjson
2
+
3
+ PyGJSON is a Python bindings for [tidwall/gjson.rs](https://github.com/tidwall/gjson.rs).
4
+
5
+ The original GJSON: [https://github.com/tidwall/gjson]()
6
+
7
+ ## Installation
8
+
9
+ ```bash
10
+ pip install pygjson
11
+ ```
12
+
13
+
14
+ ## Quick example
15
+
16
+ ```python
17
+ import pygjson
18
+
19
+ JSON = """{
20
+ "name": {"first": "Tom", "last": "Anderson"},
21
+ "age": 37,
22
+ "children": ["Sara", "Alex", "Jack"],
23
+ "friends": [
24
+ {"first": "Dale", "last": "Murphy", "age": 44},
25
+ {"first": "Roger", "last": "Craig", "age": 68},
26
+ {"first": "Jane", "last": "Murphy", "age": 47}
27
+ ]
28
+ }"""
29
+
30
+ str(pygjson.get(JSON, "name.last")) # 'Anderson'
31
+ int(pygjson.get(JSON, "age")) # 37
32
+ int(pygjson.get(JSON, "children.#")) # 3
33
+ str(pygjson.get(JSON, "children.1")) # 'Alex'
34
+ str(pygjson.get(JSON, 'friends.#(last="Murphy").first')) # 'Dale'
35
+
36
+ [str(v) for v in pygjson.get(JSON, "children|@reverse")]
37
+ # ['Jack', 'Alex', 'Sara']
38
+
39
+ pygjson.valid(JSON) # True
40
+ ```
41
+
42
+ ## API
43
+
44
+ ### Module-level functions
45
+
46
+ | Function | Description |
47
+ |-------------------------------|--------------------------------------------------------------|
48
+ | `get(json, path)` | Query `json` at `path`; returns `Value` (gjson-native) |
49
+ | `get(json, path, default)` | Returns `default` if path is not found (Pythonic) |
50
+ | `parse(json)` | Parse the entire JSON document into a `Value` |
51
+ | `valid(json)` | `True` if `json` is syntactically valid |
52
+
53
+ ### Value
54
+
55
+ `get` and `parse` return a `Value`. The API is split into two layers:
56
+
57
+ **gjson-native methods** — mirror the Rust `gjson::Value` API directly:
58
+
59
+ | Method | Description |
60
+ |--------------------|----------------------------------------------------------|
61
+ | `v.kind()` | Returns a `Kind` enum value |
62
+ | `v.exists()` | `True` if the value was actually found in the JSON |
63
+ | `v.to_str()` | String representation (gjson `str` behaviour) |
64
+ | `v.to_int()` | Signed 64-bit integer (`i64`) |
65
+ | `v.to_uint()` | Unsigned 64-bit integer (`u64`) |
66
+ | `v.to_float()` | 64-bit float |
67
+ | `v.to_bool()` | `True` only for the JSON literal `true` |
68
+ | `v.json()` | Raw JSON text for this value |
69
+ | `v.get(path)` | Sub-query relative to this value (gjson-native) |
70
+ | `v.get(path, default)` | Sub-query; returns `default` if not found (Pythonic) |
71
+ | `v.to_list()` | `list[Value]` for arrays |
72
+ | `v.to_dict()` | `dict[str, Value]` for objects |
73
+
74
+ **Pythonic methods** — follow standard Python protocols:
75
+
76
+ | Syntax | Description |
77
+ |---------------------|--------------------------------------------------------------|
78
+ | `str(v)` | String representation |
79
+ | `int(v)` | Integer (negative → `i64`, non-negative → `u64`) |
80
+ | `float(v)` | 64-bit float |
81
+ | `bool(v)` | `True` if `v.exists()` |
82
+ | `len(v)` | Chars for String; element count for Array/Object |
83
+ | `v[key]` | Subscript access for Object values |
84
+ | `key in v` | Key membership for Object; str match for Array elements |
85
+ | `iter(v)` | Chars for String; `Value`s for Array; keys for Object |
86
+ | `v.keys()` | Object keys (raises `TypeError` for non-Object) |
87
+ | `v.values()` | Object values (raises `TypeError` for non-Object) |
88
+ | `v.items()` | `(key, Value)` pairs (raises `TypeError` for non-Object) |
89
+
90
+ ### Kind
91
+
92
+ ```python
93
+ from pygjson import Kind
94
+ Kind.Null Kind.False_ Kind.True_ Kind.Number
95
+ Kind.String Kind.Array Kind.Object
96
+ ```
97
+
98
+ (`False` and `True` are Python keywords, so the variants are named with a
99
+ trailing underscore.)
100
+
101
+ ## Usage examples
102
+
103
+ ```python
104
+ from pygjson import get, parse, valid, Kind
105
+
106
+ # gjson-native: missing value returns Value(exists=False)
107
+ v = get(JSON, "no.such.path")
108
+ v.exists() # False
109
+ bool(v) # False
110
+
111
+ # Pythonic: missing value returns None (or a custom default)
112
+ get(JSON, "no.such.path", None) # None
113
+ get(JSON, "no.such.path", 42) # 42
114
+
115
+ # Type conversion
116
+ age = get(JSON, "age")
117
+ age.to_int() # gjson i64 behaviour
118
+ int(age) # Python int protocol
119
+
120
+ # Boolean distinction
121
+ get('{"flag": true}', "flag").to_bool() # True (JSON true literal)
122
+ bool(get(JSON, "age")) # True (value exists)
123
+
124
+ # Array iteration
125
+ children = get(JSON, "children")
126
+ list(children) # [Value("Sara"), Value("Alex"), Value("Jack")]
127
+ [str(v) for v in children] # ['Sara', 'Alex', 'Jack']
128
+ "Sara" in children # True
129
+
130
+ # Object (dict-like) access
131
+ name = get(JSON, "name")
132
+ name["first"] # Value("Tom")
133
+ "first" in name # True
134
+ list(name) # ['first', 'last'] — keys
135
+ dict(name) # {'first': Value("Tom"), 'last': Value("Anderson")}
136
+ for k, v in name.items():
137
+ print(k, str(v))
138
+
139
+ # Chained queries
140
+ parse(JSON).get("name").get("first") # Value("Tom")
141
+ ```
142
+
143
+ ## Path syntax
144
+
145
+ For the full path / query / modifier syntax see the upstream
146
+ [gjson.rs](https://github.com/tidwall/gjson.rs) and the original
147
+ [GJSON path syntax](https://github.com/tidwall/gjson/blob/master/SYNTAX.md).
148
+
149
+ ## License
150
+
151
+ MIT
@@ -0,0 +1,20 @@
1
+ [build-system]
2
+ requires = ["maturin>=1.5,<2.0"]
3
+ build-backend = "maturin"
4
+
5
+ [project]
6
+ name = "pygjson"
7
+ version = "0.0.1"
8
+ description = "Python bindings for gjson.rs - fast JSON path queries"
9
+ requires-python = ">=3.10"
10
+ license = { file = "LICENSE" }
11
+ readme = "README.md"
12
+ classifiers = [
13
+ "Programming Language :: Rust",
14
+ "Programming Language :: Python :: Implementation :: CPython",
15
+ ]
16
+
17
+ [tool.maturin]
18
+ python-source = "python"
19
+ module-name = "pygjson._pygjson"
20
+ features = ["pyo3/extension-module"]