Reputation: 744
I have the following two datasets:
// This is based on what user input, usually they will just select 1 or 2.
var selected = ['alpha', 'bravo', 'charlie', 'delta', ...]
var list = [
{
"properties":{
"name" : "Example Name",
"tags":{
"multi_select":[
{
"name":"alpha"
},
{
"name":"charlie"
}
]
}
}
},
...
// same same but many more objects with different tags each
]
Yes, it's super nested, but it comes from an API...
Anyway, so what I'm trying to do now is filter()
it based on the selected terms, example,
If list tags contain "alpha, charlie" and "alpha" is selected, it would display object, but if "alpha and bravo" is selected, the object won't match.
So with fewer it can match, but when it gets narrowed don't it shouldn't match.
I tried the following:
let res = list.filter(hb => hb.properties.Tags.multi_select.some(tag => tag.name.includes(selected)));
console.log(res);
This code is largely from Javascript array.filter by element in children
So I noticed, if I have selected "charlie" it returns the correct objects(s) that contains tag "charlie", but when I select more than 1, eg "charlie" and "alpha" it returns nothing even though there is suppose to be matching objects.
Any suggestions how I could improve the filtering?
Thanks in advance.
Upvotes: 1
Views: 88
Reputation: 547
I think the argument of your includes
method here shouldn't be an array here, the check should rather be other way around.
let res = list.filter(hb => hb.properties.tags.multi_select.some(tag => selected.includes(tag.name));
Also, one suggestion - It might be more optimal to use Set
instead of Array
for this use case maybe, if you want to research a bit.
As to why your code is working when you are only having one item, the reason is that the selected
array undergoes a string conversion so ["charlie"]
becomes charlie
which is returned as true as charlie
is your first element in the multiselect
array. But when you add another item, it happens like this ["alpha", "charlie"]
is casted to "alpha,charlie"
which is concatenation of two items, so it would naturally return false
.
Upvotes: 1
Reputation: 386868
You need to check every selected tag agains some name
of the filtering object.
let res = list.filter(hb => selected.every(tag =>
hb.properties.tags.multi_select.some(({ name }) => name === tag)
));
Upvotes: 1