The Perl and Raku Conference 2025: Greenville, South Carolina - June 27-29 Learn more

#!/usr/bin/env perl
use strict;
use FindBin;
use lib "$FindBin::Bin/../lib";
# Argument parsing
my $raw_output = 0;
my $query;
my $filename;
while (@ARGV) {
my $arg = shift @ARGV;
if ($arg eq '--raw-output' || $arg eq '-r') {
$raw_output = 1;
}
elsif ($arg eq '--help' || $arg eq '-h') {
print <<'USAGE';
jq-lite - A lightweight jq-like JSON query tool written in pure Perl
Usage:
jq-lite [options] '.query' [file.json]
Options:
-r, --raw-output Print raw strings instead of JSON-encoded values
-h, --help Show this help message
Examples:
cat users.json | jq-lite '.users[].name'
jq-lite '.users[] | select(.age > 25)' users.json
jq-lite -r '.users[] | .name' users.json
jq-lite '.meta has "version"' config.json
jq-lite '.items | sort | reverse | first' data.json
Query Syntax:
.key Access a key (e.g. .user.name)
.key? Optional access (no error if missing)
.array[] Traverse all array elements
.array[n] Index into array
| Pipe to next operation
select(condition) Filter values
Built-in functions: length, keys, first, last, reverse, sort, unique, has
Tips:
- Query must start with a dot (e.g. '.users[]')
- Reads from STDIN if no file is provided
- Outputs JSON by default; use -r for plain text
Homepage:
USAGE
exit 0;
}
elsif (!defined $query && $arg =~ /^\./) {
$query = $arg;
}
elsif (!defined $query) {
die "Error: Invalid query syntax '$arg'\nUsage: jq-lite [--raw-output|-r] '.query' [file.json]\n";
}
elsif (!defined $filename) {
$filename = $arg;
}
else {
die "Usage: jq-lite [--raw-output|-r] '.query' [file.json]\n";
}
}
die "Usage: jq-lite [--raw-output|-r] '.query' [file.json]\n" unless defined $query;
# Load JSON from file or STDIN
my $json_text;
if (defined $filename) {
open my $fh, '<', $filename or die "Cannot open file '$filename': $!\n";
local $/;
$json_text = <$fh>;
close $fh;
}
else {
local $/;
$json_text = <STDIN>;
}
# Run query
my $jq = JQ::Lite->new(raw => $raw_output);
my @results = $jq->run_query($json_text, $query);
# Output formatter
my $pp = JSON::PP->new->utf8->canonical->pretty;
# Print results
for my $r (@results) {
if (!defined $r) {
print "null\n";
}
elsif ($raw_output && ref($r) eq '') {
print "$r\n";
}
else {
print $pp->encode($r);
}
}