Lajith
Lajith

Reputation: 1867

Remove empty [] from object in angular

This is my service class method

public getSidebarItems(): Observable<INavData[]>   {

    //  let params = new HttpParams();
    //  params = params.set('userId', userid.toString());
      return this.httpClient.get<Result<INavData[]>> (`${baseUrl}/GetMenusByRoles`)
       .pipe(map( res => res.data));
      
  }

This is my json file recieved from api

[{"id":1,"name":"Dashboard","url":"/dashboard","icon":"icon-speedometer","parentId":null,"parent":null,"children":[]},{"id":2,"name":"User","url":"/user/user-list","icon":"icon-list","parentId":null,"parent":null,"children":[]},{"id":3,"name":"Role","url":"/role/role-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":4,"name":"Bank","url":"/bank/bank-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":5,"name":"Branch","url":"/branch/branch-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":6,"name":"Customer","url":"/customer/customer-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":7,"name":"Transaction","url":"/transaction/transaction-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[{"id":8,"name":"Test","url":"/report/transaction-report\n","icon":"icon-folder-alt","parentId":7,"children":[]}]}]

I have to remove empty "children": []

items$: Observable<INavData[]>;

 let result=this.sidebar.getSidebarItems();   
  this.items$ = result.pipe(
    map( sidebarItems => {
      return sidebarItems
      .filter( value=> Object.keys( value ).length !==0 )
     
   }));

The above code fremove empty

My Question is

  1. Above code is not working .. i have to removeempty children with node children":[].

Please let me know ..thanks

EDIT:

export interface INavData {
    name?: string;
    url?: string;
    icon?: string;
    childrens?: INavData[];
    ..other property
}

EDIT 1:

After updating code:

Update

 result.pipe(
        map(x => {
            return this.removeEmptyObjects(x);
        })
       ).subscribe(results => { console.log(results); });

Upvotes: 0

Views: 1832

Answers (2)

Vimal Patel
Vimal Patel

Reputation: 3055

While looping through array of object. Grab the object information's using object.entries. This will give you keys and values as an array then after filter out empty array. Loop through resultset and delete those keys from your main object.

const { from } = rxjs;
const { map, reduce } = rxjs.operators;

var data =[{"id":1,"name":"Dashboard","url":"/dashboard","icon":"icon-speedometer","parentId":null,"parent":null,"children":[]},{"id":2,"name":"User","url":"/user/user-list","icon":"icon-list","parentId":null,"parent":null,"children":[]},{"id":3,"name":"Role","url":"/role/role-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":4,"name":"Bank","url":"/bank/bank-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":5,"name":"Branch","url":"/branch/branch-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":6,"name":"Customer","url":"/customer/customer-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[]},{"id":7,"name":"Transaction","url":"/transaction/transaction-list","icon":"icon-folder-alt","parentId":null,"parent":null,"children":[{"id":8,"name":"Test","url":"/report/transaction-report\n","icon":"icon-folder-alt","parentId":7,"children":[]}]}];

from(data).pipe(
  map(x => {
      return removeEmptyObjects(x);
  })
).subscribe(results => { console.log(results); });

function removeEmptyObjects(x){
      var emptyKeys = getEmptyObjects(x);
          removeKey(x,emptyKeys);
      if (x.children && x.children.length>0) {
        x.children.map(y=>removeEmptyObjects(y));
      }
          return x;
}
 
function getEmptyObjects(x){
return Object.entries(x)
    .filter(x => Array.isArray(x[1]) && x[1].length == 0);
}

function removeKey(obj,tobeRemoved) {
  if(tobeRemoved && tobeRemoved.length > 0) {
              tobeRemoved.map(key=> delete obj[key[0]])
   }
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/rxjs/6.3.3/rxjs.umd.min.js"></script>

Edit 1: updated the code for nested level removal.

Edit 2 As it is returning array of object we need to use map function of that.

result.pipe(
        map((x) => {
          return x.map((y) => this.removeEmptyObjects(y));
        })
      )
    .subscribe((results) => {
      console.log(results);
    });

Upvotes: 3

Edward
Edward

Reputation: 1126

use the rxjs pipe & map operator on the observable to transform the raw data to the format you desire.

this.sidebar.getSidebarItems().pipe(
  map( sidebarItems => {
     return sideBarItems
     .filter( value=> Object.keys( value ).length !==0 )
     .filter( value=> JSON.stringify( value !== '[]' ) )
     .map( (item: SideBarItem) => {
        return removeEmpty(item);
     });
  }
);
  • the first map takes the value returned from the observable and allows you to operate on it

this allows you to subscribe to an shared Observable, but transform the values to the format you need.

Upvotes: 1

Related Questions