Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dots in object key names are misrepresented and treated as nested values #432

Closed
belvederef opened this issue Jun 5, 2020 · 2 comments · Fixed by #457
Closed

Dots in object key names are misrepresented and treated as nested values #432

belvederef opened this issue Jun 5, 2020 · 2 comments · Fixed by #457

Comments

@belvederef
Copy link

Describe the bug

If you want to search into nested objects, the keys of that object cannot contain dots, otherwise when specifying Fuse options they will be treated as nested values. In my case, every key is a url and the dots cannot be avoided.

Version

v6.0.2

Is this a regression?

No

🔬Minimal Reproduction

Have a list of objects such as:

[
  {
    id: 'http://xmlns.com/foaf/0.1/',
    'http://www.w3.org/1999/02/22-rdf-syntax-ns#type': [
      {
        type: 'uri',
        value: 'http://www.w3.org/2002/07/owl#Ontology',
      },
    ],
  },
]

You want to search for value inside http://www.w3.org/1999/02/22-rdf-syntax-ns#type, so you define an options object:

const options = {
  keys: ['id', 'http://www.w3.org/1999/02/22-rdf-syntax-ns#type.value'],
};

Since nested objects are indicated with a dot, Fuse treats e.g. w3 as a key contained in the object http://www.

Additional context

It could be solved by using e.g. optional nested arrays for such values:

const options = {
  keys: ['id', ['http://www.w3.org/1999/02/22-rdf-syntax-ns#type', 'value']],
};
@belvederef belvederef added the bug label Jun 5, 2020
@belvederef belvederef changed the title Dots in object key names are misrepresented and treated as subvalues Dots in object key names are misrepresented and treated as nested values Jun 9, 2020
@krisk krisk self-assigned this Jun 22, 2020
@krisk
Copy link
Owner

krisk commented Jun 22, 2020

Yes, I think it's a good solution. That way it'll serve double duty even for string-based dot-delimited paths. For example:

const list = [
  {
    title: 'HTML5',
    author: {
      firstName: 'Remy',
      lastName: 'Sharp'
    }
  },
  {
    title: 'Angels & Demons',
    author: {
      firstName: 'Dan',
      lastName: 'Brown'
    }
  }
]

const fuse = new Fuse(list, {
  // this is the same as `['title', 'author.firstName']`
  keys: ['title', ['author', 'firstName']]
})

And, as per your example:

const options = {
  keys: ['id', ['http://www.w3.org/1999/02/22-rdf-syntax-ns#type', 'value']],
};

The one tricky part is how this API should look like for logical query operators, since right now it looks like this:

const result = fuse1.search({
  $and: [{ 'author.firstName': 'dn' }, { 'author.lastName': 'bron' }]
})

However, if we were to also allow arrays as keys, then I'd have to rethink its API. One potential design could be the following:

const result = fuse.search({
  $and: [
    {
      $path: ['author', 'firstName'],
      $query: 'dn'
    },
    {
      $path: ['author', 'lastName'],
      $query: 'bron'
    }
  ]
})

Admittedly, this looks quite unpleasant.

Thoughts?

@belvederef
Copy link
Author

Good observation. The only other way I can think of to keep the API minimal and similar to the options use case is using:

const result = fuse1.search({
  $and: [
    { 
      "[ 'author', 'firstName' ]": 'dn' 
    }
  ]
})

And then parse the key. E.g. you could parse them with JSON.parse(), but it will be picky about the quote symbols as it requires " for the key names in the array, so will have to convert ' to " first. That might not be an extremely bad solution if you think this will be the "plan B" used only in specific circumstances. The majority will keep using the original way.

Although this solution is syntactically closer to the options use case, your solution looks more robust.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants