Filtering on objects

I’m reading in a json file into an object, which is being used by a ion-list to display the data. I want to be able to search the data, but I’m having problems.

I see multiple examples of filtering an array (which works fine) but I need a more complicated object.

This is the json

{
  "menuItems": [ {
    "id": "1",
    "name": "Protocols",
    "itemPage": "protocols",
    "icon": "bookmarks"
  },
  {
    "id": "2",
    "name": "Hospitals",
    "itemPage": "hospitals",
    "icon": "compass"
  },
  {
    "id": "3",
    "name": "Medications",
    "itemPage": "meds",
    "icon": "medkit"
  },
  {
    "id": "4",
    "name": "Calculators",
    "itemPage": "calcs",
    "icon": "calculator"
  },
  {
    "id": "5",
    "name": "Burn Tools",
    "itemPage": "burntools",
    "icon": "bonfire"
  },
  {
    "id": "6",
    "name": "References",
    "itemPage": "references",
    "icon": "book"
  },
  {
    "id": "7",
    "name": "Medical Command",
    "itemPage": "medcomm",
    "icon": "logo-whatsapp"
  }
  ]
}

So the object returned should be able to be accessed like:

results.id
results.name
etc.

I want to be able to pass a search string and only return the items that contain that search string but darn if I can find any working examples to help me along.

Can anyone help?

hi, @JohnCressman
Can you please tell us what is search string here. I mean do you want to search data through name or itemPage or anything else?

var MENU = {
  "menuItems": [ {
    "id": "1",
    "name": "Protocols",
    "itemPage": "protocols",
    "icon": "bookmarks"
  },
  {
    "id": "2",
    "name": "Hospitals",
    "itemPage": "hospitals",
    "icon": "compass"
  },
  {
    "id": "3",
    "name": "Medications",
    "itemPage": "meds",
    "icon": "medkit"
  },
  {
    "id": "4",
    "name": "Calculators",
    "itemPage": "calcs",
    "icon": "calculator"
  },
  {
    "id": "5",
    "name": "Burn Tools",
    "itemPage": "burntools",
    "icon": "bonfire"
  },
  {
    "id": "6",
    "name": "References",
    "itemPage": "references",
    "icon": "book"
  },
  {
    "id": "7",
    "name": "Medical Command",
    "itemPage": "medcomm",
    "icon": "logo-whatsapp"
  }
  ]
};

var search_string = 'Med';
var search_results = MENU['menuItems'].filter(menu_item => menu_item['name'].indexOf(search_string) !== -1);
console.log(search_results);

In this example, I would search through name or itempage.

This is one that doesn’t work. It’s supposed to look for a match for the id and I get nothing returned (null)

  getHospitalByID(id: string): Observable<any> {
    console.log('getHospitalByID = ' + id);
    let searchText = id.toLowerCase();
    console.log('getHospitalByID = ' + searchText);
    return this.http.get('../../assets/data/hospitals.json').pipe(
        map(results => results['hospitals'].filter(res => res.id === searchText ) )
    );
  }
let searchText = id.toLowerCase();

Why will someone search by ID ? Also, what is the need of the above statement when ID is an integer in string form? Also, what doesn’t work in your code? Is it the filtering or returning of the observable?

This function is designed to return a specific record based on id. Technically, they’re not searching for id, they are picking one from a list and then it should display that record on a details screen that calls this function.

But, the return is null, even though it does receive the id value.

Then we will have to debug step by step. Does the above code work individually?

John, did you want the [‘hospitals’] index? Maybe you meant:

return this.http.get(’…/…/assets/data/hospitals.json’).pipe(
map(results => results.filter(res => res.id === searchText ) )
);

They way the json is arranged, all of the items are in the hospitals container (or whatever you call them in json), so map(results => results[‘hospitals’]) returns only those results, and then I want to filter on the returned results within the hospitals container.