Trying to loop over an object using Moment JS - json

I have a section that pulls in data from an array and displays it and groups it by month. In order for it to show the date object I have to remove a layer from the JSON file.
It feels like I'm missing something something very small and just need to make a tiny change to loop over the data array. Can anyone point out what I'm doing wrong?
Here is the table that displays the data:
<table class="table" *ngFor="let month of transactions | keyvalue">
<tr>
<th>{{month.key}}</th>
</tr>
<tr>
<td>
<table class="table" *ngFor="let customer of month.value">
<tr>
<td>
{{customer}}
</td>
</tr>
</table>
</td>
</tr>
</table>
This is the component that groups the data:
export class AppComponent {
public transactions = {};
// Sample Data
customers = [
{
data: [
{
customer: {
name: "John"
},
// transaction_date: "2017-04-18"
transaction_date: "2019-9-22T13:56:11.971643+00:00"
},
{
customer: {
name: "Dick"
},
transaction_date: "2019-10-22T13:56:11.971643+00:00"
},
{
customer: {
name: "Harry"
},
transaction_date: "2019-7-22T13:56:11.971643+00:00"
},
{
customer: {
name: "John"
},
transaction_date: "2019-9-22T13:56:11.971643+00:00"
}
]
}
];
constructor() {}
ngOnInit() {
const monthName = item =>
moment(item.transaction_date, "YYYY-MM-DD").format("MMM");
// Establish groupBy array
this.transactions = _.chain(this.customers)
.groupBy(monthName)
.mapValues(items => _.map(items, "customer.name"))
.value();
const byMonth = _.chain(this.customers)
.groupBy(monthName)
.mapValues(items => _.map(items, "customer.name"))
.value();
console.log(byMonth);
return byMonth;
console.log(this.customers2);
}
}
If I format the Json differently it works, but I need it to work with the data [] array as well.
// Working Array
customers2 = [
{
customer: {
name: "John"
},
// transaction_date: "2017-04-18"
transaction_date: "2019-9-22T13:56:11.971643+00:00"
},
{
customer: {
name: "Dick"
},
transaction_date: "2019-10-22T13:56:11.971643+00:00"
},
{
customer: {
name: "Harry"
},
transaction_date: "2019-7-22T13:56:11.971643+00:00"
},
{
customer: {
name: "John"
},
transaction_date: "2019-9-22T13:56:11.971643+00:00"
}
];

Try this:
this.transactions = _.chain(this.customers[0].data)
const byMonth = _.chain(this.customers[0].data)
Working stackblitz.
UPDATE
Your customers member variable is an array with only one element.
That was the reason for adding [0] to access it.
You simply access the first element in an array like that. Array name and an index value (zero based).
Few more examples:
customers = []; // <-- simple array
customers = [{}]; // <-- simple array with one object in it
How to access it?
customers[0] // <-- first element
Your case:
customers = [{ data: [] }]; // <-- simple array with one object in it with a property "data" which is another array.
How to access it?
customers[0].data // <-- the solution

Related

Destructuring an array of objects inside an object

I have an object with the following structure:
const inventory = {
item: {
details: [
{
name: "Item A",
type: "Type A"
}
]
}
}
I would like to access the name property with pure destructuring. So far I got to the first element in the details array.
const {item: {details: [firstDetail]}} = inventory;
I don't know where to go from here to access the name property. I was expecting it to be like the following but it doesn't work. Any ideas on how to achieve this?
const {item: {details: [firstDetail]: {name}}} = inventory;
Just {name} instead of firstDetail:
const inventory = {
item: {
details: [
{
name: "Item A",
type: "Type A"
}
]
}
}
const {item: {details: [{name}]}} = inventory;
console.log(name);

jQuery array to splited json

Hello I have am trying to build a post request. Below is the format that I have to send
const data = {
categories: [
{
id: 9
},
{
id: 14
}
],
}
But what I have is ["29", "23", "22"] : these are category ids
Please help
You can use .map:
const arr = ["29", "23", "22"];
const data = {
categories: arr.map( e => ({ id: e }) )
};
console.log(data);

Getting json object data with react

I am attempting to pull data out of json like this, which is imported as "values"
{
"content": {
"person": [
{
"name": "Test"
"age" : "24:
}
]
}
}
I am using .map like below but getting the error .default.map is not a function I believe it is because i have objects not arrays, i've tried a bunch of stuff including object.keys but i'm getting errors all over the place, any direction would be appreciated.
import values from './sample.json'
const vals = values.map((myval, index) => {
const items = person.items.map((item, i) => {
return (
<div>{item.name}</div>
)
})
return (
<div>{items}</div>
)
})
I think your data and code have some errors. But after fixing those and also changing the name from 'person' to 'people' if that's what you are after, here's the code that does what you are trying to do:
var data = {
content: {
people: [
{
name: "Test",
age: 24,
},
{
name: "Foo",
age: 25,
},
],
},
};
var App = React.createClass({
render: function () {
var people = data.content.people.map(function (person) {
return <div>{person.name}</div>;
});
return <div>{people}</div>;
},
});
ReactDOM.render(<App />, document.getElementById("app"));
And here's the JSBin for that: https://jsbin.com/coyalec/2/edit?html,js,output
Update: I'm updating the answer with more detailed example. It now deals with data more generically, like it doesn't assume what are the entries of 'contents' and such, but it knows that each type like 'people' or 'pets' are an array.
var data = {
content: {
people: [
{
name: "Test",
age: 24,
},
{
name: "Foo",
age: 25,
},
],
pets: [
{
name: "Sweety",
age: 3,
},
{
name: "Kitty",
age: 5,
},
],
},
};
var App = React.createClass({
render: function () {
// Get the keys in data.content. This will return ['people', 'pets']
var contentKeys = Object.keys(data.content);
// Now start iterating through these keys and use those keys to
// retrieve the underlying arrays and then extract the name field
var allNames = contentKeys.map((t) =>
data.content[t].map((e) => <div>{e.name}</div>)
);
return <div>{allNames}</div>;
},
});
ReactDOM.render(<App />, document.getElementById("app"));
And here's the latest JSBin: https://jsbin.com/coyalec/4/edit?html,js,output

ImmutableJS: Convert List to indexed Map

This question is about Immutable.js library.
I have a List<T>, where T is {name: string, id: number}. I want to convert it to Map<number, T>, with id of T to the keys. Using standard method toMap gives me a Map with sequential indexes, and there is no way to hook there. And no method like indexBy or other. how to do that?
You can do it with a reducer like this:
function indexBy(iterable, searchKey) {
return iterable.reduce(
(lookup, item) => lookup.set(item.get(searchKey), item),
Immutable.Map()
);
}
var things = Immutable.fromJS([
{id: 'id-1', lol: 'abc'},
{id: 'id-2', lol: 'def'},
{id: 'id-3', lol: 'jkl'}
]);
var thingsLookup = indexBy(things, 'id');
thingsLookup.toJS() === {
"id-1": { "id": "id-1", "lol": "abc" },
"id-2": { "id": "id-2", "lol": "def" },
"id-3": { "id": "id-3", "lol": "jkl" }
};

Handlebars lookup in array

I have JSON object:
{
groups: [
{id: 1, title: "group1"},
{id: 2, title: "group2"},
],
users: [
{id:1, login: "user1", groupId: 1},
{id:2, login: "user2", groupId: 2},
{id:3, login: "user3", groupId: 1}
]
}
and handlebars template:
{{#each users}}
<tr data-id="{{id}}">
<td>{{login}}</td>
<td data-id="{{groupId}}">{{lookup ../groups groupId}}{{title}}</td>
</tr>
{{/each}}
but it is not working. Template compile and table render, but table group column contains only id as attribute of td tag. How to render title of group inside td tag (it is possible with handlebars using this JSON object)?
The lookup helper only looks up by array index, not but an id, but you can whip up a helper to do that:
Handlebars.registerHelper('lookup2', function(collection, id) {
var collectionLength = collection.length;
for (var i = 0; i < collectionLength; i++) {
if (collection[i].id === id) {
return collection[i];
}
}
return null;
});
Then you'll need to lookup the title from that object. Here I use #with to change context:
{{#each users}}
<tr data-id="{{id}}">
<td>{{login}}</td>
<td data-id="{{groupId}}">{{#with (lookup2 ../groups groupId)}}{{title}}{{/with}}</td>
</tr>
{{/each}}