Home > Net >  Using observable to map() and filter() data fetching from server
Using observable to map() and filter() data fetching from server

Time:10-06

I have an Angular Service which sends a data service call and returns an array of objects containing multiple layers of data. I want to be able to filter that data and return only the matched records.

this.behaviourStore.state$ = {
  "todos": [
    { 
      "accountNo": "50190000009400",
      "vpainfo": [
        {
          "vpa": "log@bandhan"
        }
      ]
    },
    {
      "accountNo": "10180000025686",
      "vpainfo": []
    }
  ]
}

And have tried in the below way but getting the error saying, TypeError: Cannot read properties of undefined (reading 'vpainfo')

this.virtualAddressListObj = this.behaviourStore.state$.
   pipe(map(state => state.todos.filter((v: any) => (v.vpainfo.length !=0 && v.vpainfo[0].vpa !== null && v.vpainfo[0].vpa !== undefined))));
   
  this.virtualAddressListObj.subscribe(
    val => { console.log(JSON.stringify(val))}, //next callback
    error => { console.log(error) }, //error callback
    () => { console.log("Completed") } //complete callback
 )

CodePudding user response:

Not sure if you always want to get all vpainfo properties but, I think you could use an auxiliary function for that filtering operation:

this.behaviourStore.state$.pipe(
  map((response) => this.getPainfo(response['todos']))
 ).subscribe(
   (data) => console.log('my data:', data), // output: my data: ['log@bandhan']
   (error) => console.log('Error produced:', error),
   () => console.log('Finalized')
);

private getPainfo(dataArray: any[]) {
  const result = [];

  for (const element of dataArray) {
    const keys = Object.keys(element);

    for (const key of keys) {
      if (key !== 'vpainfo') { continue; }

      element[key].filter((e) => e?.vpa ? result.push(e.vpa) : '')
    }
  }

  return result;
}

CodePudding user response:

With the example of how the state model you provided should be your code should work.

use tap operator to console the state object

this.virtualAddressListObj = this.behaviourStore.state$.
  pipe(
    tap((state) => console.log(state)),// Make sure here the data have the right structure!
    map(state => state.todos.filter((v: any) => (v.vpainfo.length !=0 && v.vpainfo[0].vpa !== null && v.vpainfo[0].vpa !== undefined)))
  );
   
  this.virtualAddressListObj.subscribe(
    val => { console.log(JSON.stringify(val))}, //next callback
    error => { console.log(error) }, //error callback
    () => { console.log("Completed") } //complete callback
 )
  • Related