788

I'm using jq to parse a JSON file as shown here. However, the results for string values contain the "double-quotes" as expected:

$ cat json.txt | jq '.name' "Google" 

How can I pipe this into another command to remove the ""?

$ cat json.txt | jq '.name' | other_command Google 
3
  • 11
    FYI, cat foo | bar is significantly less efficient than bar <foo or its equivalent <foo bar, especially if bar is a program like sort that can parallelize its operations when given a seekable file descriptor as opposed to a FIFO (which can only be read once front-to-back). It both means more startup overhead (invoking /bin/cat), and more context switches between userspace and kernel (each piece of content going through a read() within cat, then a write() to a FIFO in cat, and then a read() inside your destination program, instead of skipping to that last step directly). Commented Jun 20, 2017 at 14:58
  • 4
    Another example of a case where the difference is a big one is cat foo | wc -c, vs wc -c <foo -- in the latter case it can just do two syscalls, seek() and tell(), to get the exact size of the file now matter how long it is; in the former, it needs to read to the end, even if that's gigabytes of content, because only cat has direct access to the original file, and wc has no way to request metadata on it. Commented Jun 20, 2017 at 15:02
  • That is some really good info. Where can I read more about this? Commented Dec 15, 2022 at 7:47

3 Answers 3

1416

Use the -r (or --raw-output) option to emit raw strings as output:

jq -r '.name' <json.txt 
Sign up to request clarification or add additional context in comments.

9 Comments

If you want to strip the quotes, just pipe the output from this command to tr -d '"'.
@hd1, that's only true if there aren't literal quotes. If someone's name is "Mack \"The Knife\" Smith", you want it to change to Mack "The Knife" Smith, not Mack The Knife Smith.
Whether any given corner case is safe to ignore needs to be an explicit, case-by-case design consideration as a rule. Otherwise you end up in the world we live in, where software is riddled with bugs because the design didn't consider the full scope of possible inputs. Which is to say -- unless someone lays out as a requirement that " can never exist as literal data as opposed to syntax, it's irresponsible to assume such to be the case. (I work in security, and see sooo many issues misclassified as "input validation" failures when they're really failure to design for the full input domain)
jq takes a filename so no need to pipe or redirect the file contents jq -r '.name' json.txt works just fine
@ucbpaladin, <json.txt reads from the file json.txt, whereas >json.txt empties the file json.txt and then writes to it. The OP here is using cat json.txt, so they want to read from the file, so < is correct.
|
81

So for a file containing just {"name": "Google"} then yes

sample='{"name":"Google"}' echo $sample| jq '.name' "Google" 

using --raw-output helps

echo $sample| jq --raw-output '.name' Google 

But I stumbled upon this question because I was using --raw-output on a json array like this

sample='[{"name":"Yahoo"},{"name":"Google"}]' echo $sample | jq --raw-output 'map(.name)' [ "Yahoo", "Google" ] 

And I didn't understand why the quotes remained. I came across this post, and now I know adding | .[] does the trick!

echo $sample | jq --raw-output 'map(.name)| .[]' Yahoo Google 

1 Comment

Note that echo $sample is itself buggy. See I just assigned a variable, but echo $variable shows something else! -- always echo "$sample", with the quotes; or, even better, printf '%s\n' "$sample"
3

For me, it's more logical to detect an array first and then select a needed key:

sample='[{"name":"Yahoo"},{"name":"Google"}]' echo $sample | jq -r '.[] | .name' Yahoo Google 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.