I have an object like that:
{
"data": [
{
"id": "1234",
"is_deleted": false,
"name": "Sarah"
},
{
"id": "3520",
"is_deleted": true,
"name": "Bobby"
},
{
"id": "3520",
"is_deleted": true,
"name": "Sartah"
}
]
}
React code
import React from 'react';
import { Input } from 'antd';
import { connect } from 'dva';
const Search = Input.Search;
@connect(({ rule, loading }) => ({
rule,
loading: loading.models.rule,
}))
export default class SearchBox extends React.Component {
constructor(props) {
super(props)
this.state = {
isListLoaded: false,
resultArr: {}
}
}
performSearch(value) {
for( var i = this.props.rule.data.list.length; i--; ) {
for (var key in this.props.rule.data.list[i]) {
this.setState({resultArr: this.state.resultArr.push(i)});
}
}
}
ponentDidMount() {
if (!this.state.isListLoaded) {
const { dispatch } = this.props;
dispatch({
type: 'rule/fetch'
});
this.setState({ isListLoaded: true });
}
}
render() {
return (
<div>
<Search
placeholder="Search..."
onChange={(event) => this.performSearch(event.target.value)}
style={{ width: "250px", "margin-left": "20px"}}
/>
</div>
);
}
}
My goal is very simple: I want to search through this object, and return the entire array(s) that contains the keyword.
Example: if I search "Sar", I should get 2 objects:
{
"id": "1234",
"is_deleted": false,
"name": "Sarah"
},
{
"id": "3520",
"is_deleted": true,
"name": "Sartah"
}
Problem is, I get an error when I'm trying this code. I did search for previous solutions to this problem here on SO, but I can only find examples where there's only one element returned. What I want, is to get ALL the results that contain the keyword in ANY attributes (in this example, I'm returning 2 elements, not just one)
Any idea?
I have an object like that:
{
"data": [
{
"id": "1234",
"is_deleted": false,
"name": "Sarah"
},
{
"id": "3520",
"is_deleted": true,
"name": "Bobby"
},
{
"id": "3520",
"is_deleted": true,
"name": "Sartah"
}
]
}
React code
import React from 'react';
import { Input } from 'antd';
import { connect } from 'dva';
const Search = Input.Search;
@connect(({ rule, loading }) => ({
rule,
loading: loading.models.rule,
}))
export default class SearchBox extends React.Component {
constructor(props) {
super(props)
this.state = {
isListLoaded: false,
resultArr: {}
}
}
performSearch(value) {
for( var i = this.props.rule.data.list.length; i--; ) {
for (var key in this.props.rule.data.list[i]) {
this.setState({resultArr: this.state.resultArr.push(i)});
}
}
}
ponentDidMount() {
if (!this.state.isListLoaded) {
const { dispatch } = this.props;
dispatch({
type: 'rule/fetch'
});
this.setState({ isListLoaded: true });
}
}
render() {
return (
<div>
<Search
placeholder="Search..."
onChange={(event) => this.performSearch(event.target.value)}
style={{ width: "250px", "margin-left": "20px"}}
/>
</div>
);
}
}
My goal is very simple: I want to search through this object, and return the entire array(s) that contains the keyword.
Example: if I search "Sar", I should get 2 objects:
{
"id": "1234",
"is_deleted": false,
"name": "Sarah"
},
{
"id": "3520",
"is_deleted": true,
"name": "Sartah"
}
Problem is, I get an error when I'm trying this code. I did search for previous solutions to this problem here on SO, but I can only find examples where there's only one element returned. What I want, is to get ALL the results that contain the keyword in ANY attributes (in this example, I'm returning 2 elements, not just one)
Any idea?
Share Improve this question asked Apr 8, 2018 at 17:53 mokiliii Lomokiliii Lo 6373 gold badges14 silver badges27 bronze badges3 Answers
Reset to default 12
const { data } = {
"data": [
{
"id": "1234",
"is_deleted": false,
"name": "Sarah"
},
{
"id": "3520",
"is_deleted": true,
"name": "Bobby"
},
{
"id": "3520",
"is_deleted": true,
"name": "Sartah"
}
]
};
const keyword = "Sar";
const filtered = data.filter(entry => Object.values(entry).some(val => typeof val === "string" && val.includes(keyword)));
console.log(filtered);
It filters the entries
of data Array with the following criterium: at least one of the entry's values must contain a given keyword.
Since IE doesn't yet support Object.values()
and String.prototype.includes()
you can use the following:
const containsKeyword = val => typeof val === "string" && val.indexOf(keyword) !== -1;
const filtered = data.filter(entry => Object.keys(entry).map(key => entry[key]).some(containsKeyword));
or polyfill these ES6 features, see more here.
To make the keyword
lookup case insensitive, you can use RegExp:
const re = new RegExp(keyword, 'i');
const filtered = data.filter(entry => Object.values(entry).some(val => typeof val === "string" && val.match(re)));
Instead of looping through array simply use filter method of javascript
performSearch(value) {
const unfilteredData = this.props.rule.data.list;
const filteredDate = unfilteredData.filter((val) => {
return val.name.indexOf(val) !== -1;
});
this.setState({
resultArr: filteredDate,
})
}
performSearch(value) {
let filteredData = this.props.rule.data.list.filter(item => {
let isFiltered = false;
for(let key in item){
if(item[key].includes(value)){
isFiltered = true;
}
}
return isFiltered;
})
this.setState({resultArr: filteredData});
}