jmespath / jmespath.js

Javascript implementation of JMESPath, a query language for JSON
http://jmespath.org
Other
776 stars 95 forks source link

Single vs double quotes #86

Open diegodlh opened 1 year ago

diegodlh commented 1 year ago

In the following JSON:

[
  {
    "@context": "https://schema.org",
    "@type": "Organization",
    "name": "Organization name"
  },
  {
    "@context": "https://schema.org",
    "@type": "WebSite",
    "name": "Website name"
  }
]

I'm trying to get the name value for the first object (i.e., "Organization name"). I'm using https://jmespath.org/ but I'm posting here as I assume it uses jmespath.js.

I understand this expression won't work because @ has a special meaning: [?@type=='Organization'].author.name (it fails).

But this expression does not work either: [?'@type'=='Organization'].author.name (it returns []).

This expression does work: [?"@type"=='Organization'].author.name...

...but this one doesn't: [?"@type"=="Organization"].author.name (it returns []).

There seems to be some inconsistency regarding where double quotes and where single quotes should be used.

springcomp commented 1 year ago

In JMESPath expressions, you need to distinguish between identifier and raw-string literals:

An identifier is usually a plain sequence of characters, without quotation marks. However, to refer to JSON properties that contain special characters, you must use double-quotation marks as you have discovered. That would be the only way to refer to the @type property.

A raw-string literal is a just a JSON string value. It is expressed as a sequence of characters surrounded with simple quotation marks. Your first expression does not work because it tries to match the JSON string "@type" to the value of an hypothetical Organization property in your JSON objects.

Likewise your third expression does not work because it tries to match the @type property to the value of an hypothetical Organization property which does not exist.

Finally the second – correct – expression does the right thing. It tries to match the value of the property @type to the JSON string "Organization", which succeeds.