Last active
November 17, 2023 00:32
-
-
Save grdscrc/2d0b0549f48950e12d0386bb0fbd8b4f to your computer and use it in GitHub Desktop.
jazz : list paths from a json input, fuzzy search a node, get its content ; useful with large payloads
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# Tested with jq 1.6 & fzf 0.42.0 | |
# Inspired by https://github.com/reegnz/jq-zsh-plugin | |
# Call with `jazz <big_file_with_many_paths>.json` or `<command producing a valid json> | jazz` | |
# End command with `... | pbcopy` or `... > output.json` to save selection | |
input=$1 | |
TMP_DIR=$(mktemp -d /tmp/jazz_XXX) | |
chmod 700 "$TMP_DIR" | |
if [[ -z $1 ]] || [[ $1 == "-" ]]; then | |
input="$TMP_DIR/input" | |
cat /dev/stdin > "$TMP_DIR/input" | |
fi | |
trap 'rm -rf "$TMP_DIR"' EXIT | |
echo "[]" > "$TMP_DIR/root" | |
echo >&2 -n "Generating iterable paths..." | |
jq -c "paths(iterables)" "$input" > "$TMP_DIR"/iterables | |
echo >&2 -ne "\r\033[K" # Erase STDERR line | |
echo >&2 -n "Generating scalar paths..." | |
jq -c "paths(scalars)" "$input" > "$TMP_DIR"/scalars | |
echo >&2 -ne "\r\033[K" | |
# Inspired by this snippet from @dakusui for jq-front https://github.com/jqlang/jq/issues/1949#issuecomment-569278958 | |
PATH_CONVERTER='if length == 0 then "." | |
else | |
reduce .[] as $segment ( | |
""; | |
. + ($segment |if type == "string" then "." + . else "[\(.)]" end) | |
) | |
end' | |
PATH_CMD="printf %s {} | jq -cr '$PATH_CONVERTER'" | |
PREVIEW_CMD="cat {+f}" # print content of selected line to escape quotes | |
PREVIEW_CMD="$PREVIEW_CMD | awk '{print \"getpath(\"\$1\")\"}'" # interpolate quoted path in `getpath()` | |
PREVIEW_CMD="$PREVIEW_CMD | xargs -0 -I path jq --color-output path $input" # -0 to escape quotes | |
cat "$TMP_DIR"/{root,iterables,scalars} | fzf \ | |
--height='50%' \ | |
--preview-window='right:50%' \ | |
--preview "$PATH_CMD ; $PREVIEW_CMD" \ | |
--tiebreak=length \ | |
--preview-label="Enter to output node, Ctrl-l to output path, Ctrl-c to exit" \ | |
--bind "enter:become($PREVIEW_CMD)" \ | |
--bind "ctrl-l:become($PATH_CMD)" | |
rm -rf "$TMP_DIR" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment