jpick is a tiny, dependency-free jq-like JSON tool written in C++20. It aims
to cover the querying essentials of jq — navigation, iteration, pipes and
a focused set of builtins — in a single small binary, without the weight of a
full expression language.
This document tracks what has shipped and what is being considered next.
Design principle:
jpickgrows by adding builtins (named functions), not by adding grammar (operators, control flow, variables). Comparison operators and array construction ([ ... ]) are the deliberate exceptions, since they makeselectpredicates and stream-to-array reduction genuinely useful.Litmus test for new grammar: add it only if it makes an everyday extraction possible rather than merely less verbose. If the honest reaction is "at that point I'd just use
jq", then it belongs tojq.jpickcannot win on capability against a mature, complete tool; its value is a small, predictable surface you can hold in your head. Every mid-tier feature erodes that without ever matchingjq.
- JSON lexer, recursive-descent parser and
std::variantdata model. - Path queries: object keys, array indices, slices (
[a:b]) and iteration ([]). - Pipe (
|) and alternative (//) operators. - Filtering with
select(...)and transformation withmap(...). - Comparison operators (
==,!=,<,<=,>,>=) following jq's total order, composing withselectandmap. - Array construction (
[ ... ], with top-level commas) to collect a stream back into a single array, e.g.[.users[].name]or[.assets[].n] | add. - Builtins:
length,keys,to_entries,from_entries,type,has,contains,not,empty,add,sort,unique,reverse,min,max,first,last,join,split,tonumber,tostring,fromjson,ascii_downcase,ascii_upcase,ltrimstr,rtrimstr,startswith,endswith. - String interpolation (
"\(.name)") and@formats (@csv,@tsv,@json,@base64,@base64d,@base32,@base32d,@uri,@html,@sh). - Output control: compact / pretty / raw, custom indent, sorted keys.
- Streaming input (NDJSON) and
--slurpto collect inputs into one array. - Raw input (
-R/--raw-input): read each line as a string instead of JSON (with--slurp, the whole input as one string). - Reads from stdin or a file; clear errors and non-zero exit codes.
- CI (Linux + macOS), test suite (doctest), Homebrew tap and release binaries.
flattento collapse nested arrays one or more levels deep.- Numeric builtins (
floor,ceil,round,abs). envbuiltin: expose environment variables as an object (e.g.env.HOME), navigable with the existing path syntax.
To stay a lite alternative rather than a second jq, the following are
intentionally out of scope:
- A full expression language: boolean logic (
and/or), arithmetic (+ - * /) and conditionals (if/then/else). - Assignment, variables,
reduce, and function definitions. - Object construction (
{a: .x}) and other reshaping grammar: you can already reshape withto_entries/from_entries, so this is convenience, not a missing capability — and it pulls towardjq-completeness (computed keys, shorthand, cartesian fan-out).
For those, use jq.
See CONTRIBUTING.md. Issues and pull requests are welcome.