Angular get Json Object and display it with HTML - html

I have json object like this:
{
"cartId": 1,
"cartName": "Cart",
"CartItems": [
{
"productId": 1,
"product": {
"productId": 1,
"productName": "milk",
"price": 3.0,
"categoryId": 1,
},
"price": 3.0,
"quantity": 4,
"subTotal": 12.0
},
{
"productId": 2,
"product": {
"productId": 2,
"productName": "oranges",
"price": 3.0,
"categoryId": 5,
},
"price": 3.0,
"quantity": 6,
"subTotal": 18.0
}
],
"grandTotal": 30.0
}
this is my service:
getCart(): Observable<Cart[]> {
return this.http.get<Cart[]>(this.myAppUrl + this.myApiUrl)
.pipe(
retry(1)
);
}
this is my component:
cart$: Observable<Cart[]>;
constructor(private cart_Service: CartService,private http: HttpClient) {
}
ngOnInit() {
this.loadCart();
}
loadCart() {
this.cart$ = this.cart_Service.getCart();
}
I want to catch grandTotal like this in cart.component.html file:
<p *ngIf="!(cart$ | async)"><em></em></p>
<table class="table table-sm table-hover" >
<thead>
<tr>
<th> Grand Total</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let i of (cart$ | async)">
<td>{{ i.grandTotal }}</td>
</tr>
</tbody>
but I get error saying that " NgFor only supports binding to Iterables such as Arrays."
I tried different solutions to convert my json object to typescript array but none of them were helpful.
Can someone please help me to catch grandTotal and show it with html in my web api. I think we should have array to be able to get that grandTotal.

You can try either this
return this.http.get<Cart[]>(this.myAppUrl + this.myApiUrl)
.pipe(
map(response => response as unknows as Cart[])
retry(1)
);
OR
map the response as Cart[]

I finally could solve this. This is my service
getCart(): Observable<Cart[]> {
return this.http.get<Cart[]>(this.myAppUrl + this.myApiUrl);
}
this is my component:
my_data: any;
public loadCart() {
this.cart_Service.getCart().subscribe((data: Cart[]) => this.my_data = data);
}
this is my HTML:
<div>
<p> Grand Total : {{ my_data.grandTotal }} </p>
</div>

Related

Cannot find a differ supporting object '[object Object]' of type 'object'. NgFor Angular 9

I tried so many solutions none of them are not working. please help me to solve this. I need to loop through JSON objects. below is what I tried and my JSON code. I can print the Section name in tr tag but I cannot print the School object Name in the tr tag.
service.ts
getSections(): Observable<Section> {
return this.http
.get<Section>(this.apiUrl + 'sections/all')
.pipe(
retry(2),
catchError(this.handleError),
);
}
Component.ts
getSections() {
this.service.getSections().subscribe(response => {
Object.assign(this.sectionData, response);
console.log(response);
});
}
component.html
<table class="table table-hover">
<thead class="thead-light">
<tr>
<th>#</th>
<th>Section Name</th>
<th>School Name</th>
</tr>
</thead>
<tr *ngFor="let pro of sectionData ;let i=index">
<td [hidden]="true">{{pro.sectionID}}</td>
<td>{{i + 1}}</td>
<td>{{pro.Name}}</td>
<ng-container *ngFor="let sch of pro.School">
<td>{{sch.Name}}</td>
</ng-container>
</tr>
</table>
My JSON
[{
"$id": "1",
"SectionID": 1,
"SchoolID": 6,
"Name": "Grade 1",
"Active": true,
"Tstamp": null,
"Classes": [],
"School": {
"$id": "2",
"SchoolID": 6,
"Name": "Yalpanam",
"AlternativeName": "سصر ءصيص",
"TelephoneNumber": "16556489",
"URL": "",
"EmailID": "",
"Longitude": null,
"Latitude": null,
"Active": true,
"Tstamp": null,
"ClassSections": [],
"NonStaffs": [],
"Principals": [],
"Students": []
}
}]
The error which I get is
Error Msg
In you JSON, School is not an array - it is an object. So you can't iterate over it. To fix that, in your markup change:
<ng-container *ngFor="let sch of pro.School">
<td>{{sch.Name}}</td>
</ng-container>
to simply
<td>{{pro.School?.Name}}</td>

Retrieve Data from JSON Data Structure in Vue.js

I want retrieve Data from meal table (json data schema) to a table form in the browser. The retrievement works but unfortunately I do not know how to retrieve the data of the weekdays from my meal table and show them in the table.
How can I retrieve Monday, Tuesday, Wednesday, Thursday and Friday???
JSON DATA SCHEMA:
// 20200901152958
// http://localhost:8080/mealtable/weekly/1
{
"id": 1,
"calendarWeek": 1,
"mealTableWeek": {
"Monday": {
"id": 4,
"name": "Burger",
"type": "fleischhaltig",
"price": 2.60
},
"Tuesday": {
"id": 3,
"name": "Reishänchenpfanne",
"type": "fleischhaltig",
"price": 2.60
},
"Wednesday": {
"id": 1,
"name": "Vollkornnudeln",
"type": "vegan",
"price": 2.30
},
"Thursday": {
"id": 5,
"name": "Kartoffelpüree",
"type": "vegetarisch",
"price": 2.30
},
"Friday": {
"id": 2,
"name": "Falafel",
"type": "vegan",
"price": 1.90
}
}
}
MealTablWeekComponent.vue:
<template>
<div class="container">
<h3>Meal Table</h3>
<div class="container">
<table class="table">
<thead>
<tr>
<th scope="col">#</th>
<th>Meal</th>
<th>Type</th>
<th>Price in $</th>
</tr>
</thead>
<tbody>
<tr v-for="d in mealTables.mealTableWeek" v-bind:key="d.id">
<th></th>
<td>{{d.name}}</td>
<td>{{d.type}}</td>
<td>{{d.price}}</td>
</tr>
</tbody>
</table>
</div>
</div>
</template>
<script>
import MealTableDataService from "#/service/MealTableDataService";
export default {
name: "MealTableWeekComponent",
data() {
return {
mealTables: {
id: " ",
mealTableWeek: {
name: {
id: " ",
name: " ",
type: " ",
price: " "
}
}
}
};
},
methods: {
refreshMealTable() {
const id = this.$route.params.id;
MealTableDataService.retrieveMealTableById(id)
.then(response => {
console.log(response)
this.mealTables = response.data;
});
}
},
created() {
this.refreshMealTable();
}
};
</script>
<style scoped lang="scss">
</style>
View in the Browser:
<tr v-for="(d, key) in mealTables.mealTableWeek" v-bind:key="d.id">
<td>{{key}}</td>
<td>{{d.name}}</td>
<td>{{d.type}}</td>
<td>{{d.price}}</td>
</tr>

How to fetch nested JSON to table with VueJs?

I need to create a table with Vue and the data are from a JSON. I don't know how to set for the td table tag the "Jogosultsagok" two "Nev" values.
I tried row.Jogosultsagok[0].Nev format, but this not work, I write down the code parts and the final error for this.
HTML
<tbody>
<tr v-for="row in get_rows()">
<td>{{row.Id}}</td>
<td>{{row.Nev}}</td>
<td>{{row.Jogosultsagok[0].Nev}}</td>
<td>{{row.Jogosultsagok[1].Nev}}</td>
</tr>
</tbody>
Vue
data: {
rows:[]
},
created:function() {
fetch('https://api.myjson.com/bins/7jr55')
.then(res => res.json())
.then(res => {
this.rows = res;
})
},
methods: {
"get_rows": function get_rows() {
var start = (this.currentPage-1) * this.elementsPerPage;
var end = start + this.elementsPerPage;
return this.rows.slice(start, end);
},
},
JSON
[
{
"Id": 1,
"Nev": "László",
"Jogosultsagok": [
{
"Id": 1,
"Nev": "Módosítás"
},
{
"Id": 2,
"Nev": "Olvasás"
}
],
"Eletkor": 25,
"Regisztralt": "2019-01-31 06:45:51.557Z",
"Munkahely": {
"Id": 12,
"Nev": "Cég 1"
}
},
{
"Id": 2,
"Nev": "Péter",
"Jogosultsagok": [
{
"Id": 2,
"Nev": "Olvasás"
}
],
"Eletkor": 44,
"Regisztralt": "2011-01-31 09:23:51.234Z",
"Munkahely": {
"Id": 34,
"Nev": "Cég 2"
}
},
...
I get this error: TypeError: Cannot read property 'Nev' of undefined
The problem occures because the JSON response is not consistent:
row.Jogosultsagok[1] is not always defined as the nested Array sometimes only contains one element.
You can fix the error by leaving the table cell empty in case the value is missing:
<template>
<tbody>
<tr v-for="row in get_rows()">
<td>{{row.Id}}</td>
<td>{{row.Nev}}</td>
<td>{{row.Jogosultsagok[0].Nev}}</td>
<td v-if="row.Jogosultsagok[1]">{{row.Jogosultsagok[1].Nev}}</td>
<td v-else></td>
</tr>
</tbody>
</template>

How to Fetch Data from JSON multiple array(live data from DB) using observable in Angular2

JSON response is as below:
{
"clientInfo": [
{
"clientId": "1234",
"clientName": "Test1234"
},
{
"clientId": "4356",
"clientName": "Test4356"
}],
"realTimeClientInfo": [
{
"clientId": "1234",
"clientName": "Test1234",
"Location": "Test1234",
"Designation" :"Test1234"
},
{
"clientId": "4356",
"clientName": "Test7896",
"Location": "Test7896",
"Designation" :"Test7896"
}]
}
I want to fetch the data from the second JSON array.
In client.component.ts invoke the clientService as below:
#Input() clientInfo$: Observable<any>;
constructor(private clientService: ClientService) { }
ngOnInit() { this.clientInfo$ = Observable
.interval(1000)
.startWith(0).switchMap(() =>
this.clientService.getAllInfo()); }
client.service.ts is as below :
getAllInfo(): Observable<ClientInfo[]> {
this.http.get<ClientInfo[]>('http://localhost:8080/api/auth/clientInfo');
In client.component.html
<table class="table table-hover">
<thead>
<tr>
<th *ngFor="let col of clientH">{{ col }}</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let client of clientInfo$ | async ">
<td *ngFor="let col of clientH"> {{client [col]}}</td>
</tr>
</tbody>
</table>
If the JSON contains only one single array this is working. How we can use the same logic to retrieve some values from first array and some other values from the second array

error display in *ngfor json array object

when fetching json array object from rest api and trying to display in ngfor failed with the reason
error
EXCEPTION: Cannot find a differ supporting object '[object Object]' of type 'object'. NgFor only supports binding to Iterables such as Arrays. in [indexes in HomeComponent#5:37]
Code
import {Component} from 'angular2/core';
import {HomeService} from './home.services';
import {Index} from './index';
#Component({
selector: 'home-app',
providers: [HomeService],
template: `
<section class="left_side">
<article>
<div class="div_home">
<div class="div_homeIndxPartition">
<div class="div_IndxPartition" *ngFor="#indObj of indexes">
<table width="500px" class="idx_cons_table_det">
<tr>
<th align="center" color="#A9F5F2"><h3>{{indObj.name}} ({{indObj.tracker}})</h3></th>
<th align="center">Value</th>
<th align="center">Change</th>
<th align="center">%</th>
</tr>
<tr>
<td align="center" colspan="1"></td>
<td align="center">{{indObj.value}}</td>
<td align="center">{{indObj.change}}</td>
<td align="center">{{indObj.percent}}%</td>
</tr>
</table>
<br/>
<table width="500px" class="idx_cons_table">
<tr>
<th align="center">High</th>
<th align="center">Low</th>
<th align="center">Open</th>
<th align="center">Close</th>
<th align="center">52 Week High</th>
<th align="center">52 Week Low</th>
</tr>
<tr>
<td align="center">{{indObj.high}}</td>
<td align="center">{{indObj.low}}</td>
<td align="center">{{indObj.open}}%</td>
<td align="center">{{indObj.close}}</td>
<td align="center">{{indObj.yearHigh}}</td>
<td align="center">{{indObj.yearLow}}%</td>
</tr>
</table>
</div>
</div>
</div>
</article>
</section>
`
})
export class HomeComponent {
public indexes:Array<Index>=[];
public error;
constructor(private _service: HomeService){
this.indexes = _service.getIndexes().subscribe(
data => this.indexes = JSON.parse(data),
error => alert(" Error is : " + error),
()=> console.log("finished")
);
console.log(this.indexes);
}
}
JSON Data
[
{
"id": 1,
"name": "FTSE 100",
"ticker": "UKX",
"value": 69875.23,
"change": 100,
"percent": 2.3,
"high": 69875.23,
"low": 69700.89,
"yearHigh": 699999.23,
"yearLow": 680005.23,
"open": 69600.54,
"close": 699000.97,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 2,
"name": "FTSE 250",
"ticker": "MCX",
"value": 465820.85,
"change": 100,
"percent": 2.3,
"high": 465880.12,
"low": 465810.74,
"yearHigh": 478990.34,
"yearLow": 465320.23,
"open": 69600.54,
"close": 699000.97,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 3,
"name": "FTSE All-Share",
"ticker": "ASX",
"value": 236549.23,
"change": 100,
"percent": 2.3,
"high": 236949.23,
"low": 236149,
"yearHigh": 246949.21,
"yearLow": 235549.29,
"open": 236519.23,
"close": 236649.23,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 4,
"name": "Euro Stoxx 50",
"ticker": "STOXX50E",
"value": 123469.87,
"change": 100,
"percent": 2.3,
"high": 123499.87,
"low": 123439.87,
"yearHigh": 123499.87,
"yearLow": 123169.87,
"open": 123465.87,
"close": 123459.87,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 5,
"name": "S&P 500 ",
"ticker": "S500",
"value": 358976.36,
"change": 100,
"percent": 2.3,
"high": 358986.36,
"low": 358946.36,
"yearHigh": 359976.36,
"yearLow": 357976.36,
"open": 358970.36,
"close": 358996.36,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 6,
"name": "Dow Jones I.A.",
"ticker": "INDU",
"value": 456789.36,
"change": 100,
"percent": 2.3,
"high": 456799.36,
"low": 456779.36,
"yearHigh": 456889.36,
"yearLow": 456689.36,
"open": 456729.36,
"close": 456779.36,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 7,
"name": "GOLD",
"ticker": "",
"value": 500,
"change": 100,
"percent": 2.3,
"high": 700,
"low": 300,
"yearHigh": 1500,
"yearLow": 350,
"open": 450,
"close": 470,
"constituents": null,
"runDate": "21/04/2015"
},
{
"id": 8,
"name": "Brent Crude",
"ticker": "",
"value": 112,
"change": 100,
"percent": 2.3,
"high": 115,
"low": 107,
"yearHigh": 200,
"yearLow": 72,
"open": 110,
"close": 115,
"constituents": null,
"runDate": "21/04/2015"
}
]
I think that the value you set in the indexes property isn't an array but an object.
I would see several reasons for this:
You receive the response instead of the payload from the getIndexes method. In this case, you could use the map operator in this method:
getIndexes() {
return this.http.get(...).map(res => res.json());
}
The received payload doesn't correspond to an array but some of its properties. In this case, you need to set this property into the indexes property.
If you want to iterate over the properties of an object, you need to implement a custom filter like this:
#Pipe({name: 'keyValues'})
export class KeysPipe implements PipeTransform {
transform(value, args:string[]) : any {
let keys = [];
for (let key in value) {
keys.push({key: key, value: value[key]);
}
return keys;
}
}
and use it like that:
<div class="div_IndxPartition" *ngFor="#indObj of indexes | keyValues">
(...)
</div>
See this question:
How to display json object using *ngFor
You should try this:
In html:
<div *ngFor="let subsciption of subscriptions;">
<div class="col-md-6">
<h5 class="widget-title">{{subsciption.name}}</h5>
</div>
</div>
in .ts file:
export class SubscriptionComponent implements OnInit {
private subscriptions: any =[];
// private subscriptions: any ={}; // here dont use {}
.
.
.
.
.
getAllSubscriptions(queryString) {
this._http.get(`${environment.base_url}/subscriptions` + queryString)
.subscribe((response: Response) => {
this.subscriptions = response.json();
},
(error: Response) => {
console.log("Login error");
});
}
this.getAllSubscriptions(query);
}
I had same problem and my solution was without Pipes. I did not use variable in the template that returns Observer, create intermediate variable and assign result to it. For example, we will save stream to this.sub but result will save to this.indexes on success callback and will use this variable in the html template.
#Component({
template: `
<ul>
<li *ngFor="let index of indexs">
{{ index }}
</li>
</ul>
`
})
export class HomeComponent {
privat sub;
public indexes:Array<Index>=[];
public error;
constructor(private _service: HomeService) {
this.sub = this._service.getIndexes().subscribe(
data => this.indexes = JSON.parse(data),
error => alert(" Error is : " + error),
() => console.log("finished")
);
}
}
You don't want to use pipes when working with Observables.
This error is very generic and the best way is to throw in a console.log() and see where you are going wrong as it could be numerous things.
My problem was my Array was inside the Object, and I was trying to loop over the Object. Other problems could include the mapping or the ngFor. My console output would look something like this:
this.indexes = _service.getIndexes()
.subscribe(
data => {
this.indexes = JSON.parse(data);
console.log(indexes);
},
error => alert(" Error is : " + error),
()=> console.log("finished")
);
console.log(this.indexes);
So the fix I needed was something like this:
this.indexes = _service.getIndexes()
.subscribe(
data => {
this.myNewObject = JSON.parse(data);
this.indexes = this.myNewObject.indexes;
},
error => alert(" Error is : " + error),
()=> console.log("finished")
);
console.log(this.indexes);
This was because the array was nested inside the Object, so I just created a new object and accessed the array by getting its property.
i see your answer, and the easy way to solve is just set the type of the object in the *ngFor to array like this:
public indexes:Array<TYPE_OF_YOUR_DATA>=[];