Какой формат в jq для вызова пользовательского модуля?
Мне нужно URL-декодировать строку в структуре JSON, используя JQ. У меня есть пользовательский модуль, определенный в ~/.jq/urldecode.jq, но при его вызове:
jq '.http.referrer | url_decode::url_decode' file.json
Я получаю сообщение об ошибке:
jq: 1 compile error
Источник модуля:
def url_decode:
# The helper function converts the input string written in the given
# "base" to an integer
def to_i(base):
explode
| reverse
| map(if 65 <= . and . <= 90 then . + 32 else . end) # downcase
| map(if . > 96 then . - 87 else . - 48 end) # "a" ~ 97 => 10 ~ 87
| reduce .[] as $c
# base: [power, ans]
([1,0]; (.[0] * base) as $b | [$b, .[1] + (.[0] * $c)]) | .[1];
. as $in
| length as $length
| [0, ""] # i, answer
| until ( .[0] >= $length;
.[0] as $i
| if $in[$i:$i+1] == "%"
then [ $i + 3, .[1] + ([$in[$i+1:$i+3] | to_i(16)] | implode) ]
else [ $i + 1, .[1] + $in[$i:$i+1] ]
end)
| .[1]; # answer
Какой правильный синтаксис?
3 ответа
Теоретически, с вашей настройкой, вы должны иметь возможность вызывать JQ в соответствии с
jq 'import "url_decode" as url_decode;
.http.referrer | url_decode::url_decode' file.json
или проще:
jq 'include "url_decode";
.http.referrer | url_decode' file.json
Тем не менее, есть некоторые обстоятельства, в которых теория не совсем применима. В таких случаях должен работать (?) Следующий обходной путь: указать -L $HOME
в качестве параметра командной строки и укажите относительный путь в спецификации модуля. Таким образом, в вашем случае командная строка будет выглядеть так:
jq -L $HOME 'import ".jq/url_decode" as url_decode; ...
или же:
jq -L $HOME 'include ".jq/url_decode"; ...
jq читает по умолчанию из скрытой папки в корневом каталоге файлов, помеченных с расширением.jq: ~/.jq (["~/.jq", "$ORIGIN/../lib/jq", "$ORIGIN/../lib"])
Чтобы сослаться на модуль, вы можете использовать функцию импорта, а затем следуйте своей обычной команде jq после точки с запятой. "As lib" ниже позволяет вам также изменить имя пространства имен:
jq 'import "urldecode" as lib; .http.referrer | lib::url_decode' file.json
Вы можете переопределить место, где хранятся файлы.jq, с опцией -L.
Я не уверен, как создавать пользовательские модули в JQ, но если вы используете bash, я бы предложил для этого подключиться к PERL. До сих пор это самый простой способ быстрого кодирования / декодирования HTML-сущностей, который я нашел, и обычно я использую его в сочетании с JQ.
echo 'http://domain.tld/?fields={fieldname_of_type_Tab}' |
perl -MHTML::Entities -pe 'decode_entities($_)'