I have an array of object that looks like this. I made it look that way using .groupBy with lodash.
States.ts
STATES: Object[] = [
{
USA: [
{
name: 'Alabama',
abbreviation: 'AL',
country: 'USA'
},
{
name: 'Alaska',
abbreviation: 'AK',
country: 'USA'
}
]
},
{
Canada: [
{
name: 'Alberta',
abbreviation: 'ALB',
country: 'Canada'
}
]
}
];
I need it to look like this:
stateList:StateDropdownItem[] =[
{
label: 'USA',
items: [
{label: 'AL', value: 'Alabama'},
{label: 'AK', value: 'Alaska'},
]
},
.
.
]
I have tried the code below, but it doesn't work. When I print it to the console appears undefiened
even if I try to put an element without the forloop I get the following error Cannot read property 'push' of undefined
TS
dropdownOfStates: StateDropdownItem[];
.
.
dropdownBuilder() {
const STATES_BY_COUNTRY = this.getStatesByCountry();
let tempItem;
for (let i = 0; i < STATES_BY_COUNTRY.length; i++) {
tempItem = STATES_BY_COUNTRY[i];
this.dropdownOfStates.push(
new StateDropdownItem('KEY COUNTRY VALUE HERE', [
tempItem.abbreviation,
tempItem.name
])
);
}
}
Console.log after printing the result of using .groupBy with lodash groupby objects by country
You can use the map
function of arrays to transform their structure.
The code below should transform it into the structure you want. You can click "Run code snippet" to see the output
let states = [
{
USA: [
{
name: 'Alabama',
abbreviation: 'AL',
country: 'USA'
},
{
name: 'Alaska',
abbreviation: 'AK',
country: 'USA'
}
]
},
{
Canada: [
{
name: 'Alberta',
abbreviation: 'ALB',
country: 'Canada'
}
]
}
];
// Use the code below to transform
let res = states.map((val) => {
let country = Object.keys(val)[0]; // Get the name of the country, e.g. USA
return { // Return the new object structure
label: country,
items: val[country].map((item) => ({label: item.abbreviation, value: item.name}))
}
});
// Log the value
console.log(res);