7

Using jq, I want to search for a pattern via regex, and wrap the matched string with something like <div> tags

$ echo "\"This is a valid json file"\" | jq '. | gsub("valid";"how_to_refer_to_matches";"i") -

How to refer to the matched results in the second argument of gsub?
What if there are more than 1 matches?

Zeta.Investigator
  • 880
  • 1
  • 7
  • 25

1 Answers1

8
$ jq -n '"some string" | gsub("(?<a>[[:lower:]]+)"; "<div>\(.a)</div>")'
"<div>some</div> <div>string</div>"

or

$ jq -n '"some string" | gsub("(?<a>[[:lower:]]+)"; "<div>" + .a + "</div>")'
"<div>some</div> <div>string</div>"

This replaces each run of lowercase letters with the same letters, flanked by <div> and </div>. The capture is done with (?<a>RE) where a is a key name that you can refer to in the replacement using .a (it does not need to be a single letter), and where RE is some expression. You may capture multiple groups with different key names at the same time.

gsub() works like e.g. gsub() in awk and like s///g in Perl, sed, and ed, so it will perform the substitution once for each non-overlapping match of the expression. This is illustrated in my example above where there are two matches of the pattern in the string.


Just to use a more similar example as you:

$ jq -n '"this is a valid JSON string" | gsub("(?<match>valid)"; "<div>" + .match + "</div>")'
"this is a <div>valid</div> JSON string"
Kusalananda
  • 320,670
  • 36
  • 633
  • 936