How to loop through nested JSON data - json

I am trying to loop through json data bellow, to so each element. I need to get down to the details data and then in side that loop through the f1,f2 into a div. I have tried using the index but that didn't work. Also I don't know how many f1,f2 there will be as it is returned from an api
JSON data
{
"data":[
{
"title": "test",
"image": "assets/imgs/test.png",
"date": "22/07/2018 - 19.00",
"location": "test",
"details": [
{
"f1":[
{
"FunctioName": "test",
"Time": "10:00:00"
}
],
"f2":[
{
"FunctioName": "test",
"Time": "11:00:00"
}
]
}
]
}
]
}
HTML
<div *ngFor="let item of card">
<div class="swiper-zoom-container">
<div class="out-card-box">
<h2>Date</h2>
<p>{{item.date}}</p>
<h2>Program</h2>
<div *ngFor="let details of item.details; let i = index">
</div>
</div>
</div>
</div>
TS
import { Component } from '#angular/core';
import { App } from 'ionic-angular';
import { DataService } from "../../services/data";
import { LoginPage } from "../login/login";
import { AngularFireAuth } from "angularfire2/auth";
import { Storage } from "#ionic/storage";
#Component({
selector: 'page-card',
templateUrl: 'card.html',
})
export class CardPage {
card:any;
constructor(private dataservice: DataService, private afAuth:AngularFireAuth, private app:App, private storage:Storage) {
this.dataservice.cardData().subscribe(
data => {
var jsonObj = JSON.parse(data["_body"]);
this.card = jsonObj.data;
console.log(jsonObj.data)
}
);
}

You can create an object which will hold the returned data from the api and you can just navigate the object values.
Example:
export class Class1 {
data: Class2[];
}
export class Class2 {
title: string;
image: string;
date: string;
location: string;
details: Class3[];
}
export class Class3 {
f1: Class4[];
f2: Class4[];
}
export class Class4 {
FunctioName: string;
Time: string
}
#Component({
selector: 'page-card',
templateUrl: 'card.html',
})
export class CardPage {
card:Class1;
constructor(private dataservice: DataService, private afAuth:AngularFireAuth, private app:App, private storage:Storage) {
this.dataservice.cardData().subscribe(
data => {
this.card = data;
}
);
}
then in your component template
<div *ngFor="let item of card.data">
<div class="swiper-zoom-container">
<div class="out-card-box">
<h2>Date</h2>
<p>{{item.date}}</p>
<h2>Program</h2>
<div *ngFor="let details of item.details; let i = index">
<!-- Print the remaining items here -->
</div>
</div>
</div>
</div>

Related

How to display mock data in html in Angular

I have created mock service file and I want to display in my html but not really sure how to make it display properly so I'll be really appreciated If I can get any help or suggestion.
<div class="container2">
<div class="header" style="height: 400px">
<div class="content3">
<div>
<h1 class="kpi-title">90,346</h1>. // I'm trying to remove this hard code html
<p class="kpi-des">Users Right Now</p> // and display it from my mock data file.
</div>
<div>
<h1 class="kpi-title">250++l</h1>
<p class="kpi-des">Saved</p>
</div>
<div>
<h1 class="kpi-title">$34.5 mill</h1>
<p class="kpi-des">New User per Week</p>
</div>
</div>
</div>
</div>
TS
import { ProductService } from '../../data/product-suite.service';
export class MaxisProductSuiteComponent {
productService: ProductService[];
ngOnIT(){
}
product-suite.service.ts
export class ProductService {
productsuite: ProductSuite[] = [
{
id: 1,
title: '90,346',
description: 'Users',
},
{
id: 2,
title: '$34.5 mill',
description: 'Saved',
},
{
id: 3,
title: '250++',
description: 'New User per Week',
},
];
}
Please find the below code for your solutions:
create a json file assets folder with name output.json.
{
"result" : [
{
"id": 1,
"title": "90,346",
"description": "Users at Ford"
},
{
"id": 2,
"title": "$34.5 mill",
"description": "Saved for Ford"
},
{
"id": 3,
"title": "250++",
"description": "New User per Week"
},
{
"id": 4,
"title": "64%",
"description": "Users At Ford"
}
]
}
in service file write below code:
import { observable, Observable } from "rxjs";
import { MaxisProductSuite } from "src/Model/model";
import { HttpClient } from '#angular/common/http';
import { Injectable } from "#angular/core";
#Injectable()
export class MaxisProductService {
constructor(private http: HttpClient){}
getAllMaxisps():Observable<MaxisProductSuite> {
return this.http.get<MaxisProductSuite>("./assets/output.json");
}
}
then component file add below code:
import { DOCUMENT } from '#angular/common';
import { Component, Inject, OnInit } from '#angular/core';
import { MaxisProductSuite } from 'src/Model/model';
import { MaxisProductService } from 'src/service/MaxisProductService';
#Component({
selector: 'app-temp',
templateUrl: './temp.component.html',
styleUrls: ['./temp.component.scss']
})
export class TempComponent implements OnInit {
maxisps: MaxisProductSuite[];
public resultData:MaxisProductSuite=null;
constructor(#Inject(DOCUMENT) private document: Document, private service : MaxisProductService) {}
ngOnInit() {
this.service.getAllMaxisps().subscribe((res:MaxisProductSuite) => {
console.log(res);
this.resultData =res;
});
}
}
then HTMl file add below code:
<div *ngFor="let item of resultData?.result">
<div class="header" style="height: 400px">
<h1>{{item.id}}</h1>
<h2>{{item.title}}</h2>
<h3>{{item.description}}</h3>
</div>
add below model in model file
export interface MaxisProductSuite {
result : Result[]
}
export interface Result{
id?: number;
title: string;
description: string;
}
I hope it will help you to get the solution.
happy to HELP!
make your service in module provider or make it injectable "root".
inject the service in your component you want to display data in constructor as a dependency injection.
assign your component variable array with productService.
in your HTML loop about your data array using *ngFor=" let product of products".
use you product value in the interpolation {{ product.id }}.

Cannot read property 'setRowData' of undefined / Issue with HTML template?

Am maintaining an AG-GRID re-usable template with all necessary methods (clear filer/ CSV download/ Autofit..etc options) --- Base Template.
I have another AG-Grid template , which uses "Base Template" (thru dependency injection) and populate grid with a row of data based on searchString value. (Sample file below)
import { Component, OnInit, } from '#angular/core';
import { GridOptions, GridApi, } from "ag-grid-community";
import { ReportersgridComponent } from '../../commonpages/reportersgrid/reportersgrid.component'
#Component({
selector: 'app-reporters',
templateUrl: './reporters.component.html',
styleUrls: ['./reporters.component.scss']
})
export class ReportersComponent implements OnInit {
private reporterGrid: GridOptions;
constructor(public reportersGrid: ReportersgridComponent, ) {
this.reporterGrid = <GridOptions>{};
this.reporterGrid.enableSorting = true;
this.reporterGrid.enableFilter = true;
this.reporterGrid.enableColResize = true;
this.reporterGrid.columnDefs = this.reportersGrid.createColumnDefs();
this.reporterGrid.rowData = this.reportersGrid.createRowData();
}
ngOnInit() {
}
//Search Function
performSearch() {
let searchString = "";
this.populateFiteredReporter(searchString);
// this.reporterGrid.api.setRowData(reporterGrid.rowData)
}
populateFiteredReporter(searchString) {
this.reporterGrid.rowData = [
{ fullName: 'fName,mName,lName2', address: "address2", country: "country2", postcode: "postcode2", phone: "phone", email: "email", qualification: "MBBS", institution: "institution", department: "department" },
];
var str = JSON.stringify(this.reporterGrid.rowData);
console.log('data:' + str);
this.reporterGrid.api.setRowData(this.reporterGrid.rowData);
//this.reportersGrid.populateFiteredReporter(searchString);
}
}
In HTML of the above file, I am using "Base Template" s SELECTOR AS HTML TAG. (
<app-reportersgrid></app-reportersgrid>
) to display the grid portion.
Above gives error -> Cannot read property 'setRowData' of undefined.
Please note that if I replace Base Template's selector with base template's FULL HTML portion for ag-grid (which has (gridReady)="onGridReady($event)"), page works fine.
Can I get help to stick back to my original idea of keeping base template intact? (Note that all base template functions like export to csv, autofit etc works fine - those are coded in the base template along with OnGridReadty().)
Thanks in Advance..
ASJ.
22/10/2019 /* Template of reporters.component.html*/
<div>
<div class="col-md-12">
<div class="card">
<div class="card-header text-uppercase font-weight-bold">
Search
</div>
<div class="card-body">
<div>
<div class="row">
<div class="col-sm-4">
<div class="form-group">
<span>Name <i>(First/Middle/Last)</i></span>
<input type="text" class="form-control" [(ngModel)]="reporterName">
</div>
</div>
</div>
</div>
</div>
<div class="card-footer">
<div class="row">
<div class="col-6 col-sm-4 col-md-2 col-xl mb-3 mb-xl-0">
<button type="button" class="btn btn-normal btn-primary" (click)="performSearch()" style="width: 100px; ">Search</button>
<button type="button" class="btn btn-normal btn-light" style="width: 100px;">Reset</button>
</div>
</div>
</div>
</div>
</div>
<app-reportersgrid></app-reportersgrid>
</div>
Base template - HTML of the AG-GRID
<div class="centered-content">
<div>
<ag-grid-angular #agGrid style="width: 100%; height: 358px;" class="ag-theme-balham"
[gridOptions]="reporterGrid" [enableSorting]="true" enableFilter [sideBar]="sideBar"
enableColResize [pagination]="true" [paginationPageSize]=10
rowDragManaged=true
(gridReady)="onGridReady($event)">
<ag-grid-column headerName="Name" field="fullName"></ag-grid-column>
<ag-grid-column headerName="Address" field="address" [width]="150"></ag-grid-column>
<ag-grid-column headerName="Country" field="country"></ag-grid-column>
<ag-grid-column headerName="Postcode" field="postCode"></ag-grid-column>
<ag-grid-column headerName="Phone" field="phone"></ag-grid-column>
<ag-grid-column headerName="Email" field="email"></ag-grid-column>
<ag-grid-column headerName="Qualification" field="qualification"></ag-grid-column>
<ag-grid-column headerName="Institution" field="institution"></ag-grid-column>
<ag-grid-column headerName="Department" field="department" [cellRenderer]="countryCellRenderer">
</ag-grid-column>
</ag-grid-angular>
</div>
</div>
/ReportersGridcomponent.ts file/
import { Component, OnInit } from '#angular/core';
//import { HttpClient, HttpErrorResponse } from '#angular/common/http';
import {GridOptions, GridApi, Grid} from "ag-grid-community";
#Component({
selector: 'app-reportersgrid',
templateUrl: './reportersgrid.component.html',
styleUrls: ['./reportersgrid.component.scss']
})
export class ReportersgridComponent implements OnInit {
private reporterGrid: GridOptions;
private gridApi:GridApi;
private gridColumnApi;
filterName: string | null;
constructor( ) {
this.reporterGrid = <GridOptions>{};
this.reporterGrid.enableSorting = true;
this.reporterGrid.enableFilter = true;
this.reporterGrid.enableColResize = true;
this.reporterGrid.columnDefs = this.createColumnDefs();
this.reporterGrid.rowData = this.createRowData();
}
ngOnInit() {
}
createColumnDefs() {
this.reporterGrid.columnDefs = [
{
headerName: "Name",
field: "fullName",
width:100,
},
{
headerName: "Address",
field: "address",
},
{
headerName: "Country",
field: "country",
},
{
headerName: "Postcode",
field: "postCode",
},
{
headerName: "Phone",
field: "phone",
},
{
headerName: "Email",
field: "email",
},
{
headerName: "Qualification",
field: "qualification",
},
{
headerName: "Institution",
field: "institution",
},
{
headerName: "Department",
field: "department",
}
];
return this.reporterGrid.columnDefs
}
createRowData(){
this.reporterGrid.rowData = [
// {fullName: 'fName,mName,lName',address:"address1",country: "country",postcode: "postcode",phone: "phone",email:"email",qualification:"MBBS",institution:"institution",department:"department"},
];
return this.reporterGrid.rowData;
}
onGridReady(params) {
this.gridApi = params.api;
this.gridColumnApi = params.columnApi;
this.autoSizeAll()
}
autoSizeAll() {
var allColumnIds = [];
this.gridColumnApi.getAllColumns().forEach(function(column) {
allColumnIds.push(column.colId);
});
this.gridColumnApi.autoSizeColumns(allColumnIds);
}
onCSVExport() {
this.reporterGrid.api.exportDataAsCsv();
}
onSearchTextChange(newData: string) {
this.reporterGrid.api.setQuickFilter(newData);
}
clearFilters() {
if (this.gridApi.isQuickFilterPresent())
{
this.gridApi.setQuickFilter('');
this.filterName="";
}
}
// populateFiteredReporter(searchString){
// this.reporterGrid.rowData = [
// {fullName: 'fName,mName,lName2',address:"address2",country: "country2",postcode: "postcode2",phone: "phone",email:"email",qualification:"MBBS",institution:"institution",department:"department"},
// ];
// var str= JSON.stringify(this.reporterGrid.rowData);
// console.log('data:'+str);
// this.reporterGrid.api.setRowData(this.reporterGrid.rowData);
// //return this.reporterGrid.rowData;
// }
}
The first thing you need to do is set your grid component to accept grid options from its parent:
#Input() public reporterGrid: GridOptions;
Here is an abbreviated version of what your grid component should look like. I suggest using properties or fields, instead of using methods to create your rows and columns. Just a suggestion.
export class ReportersgridComponent implements OnInit {
#Input() public reporterGrid: GridOptions;
private columnDefs = [
// put your column def json here
];
private rowDefs = [
// Put your row def json here
];
constructor() {
}
ngOnInit() {
this.reporterGrid.columnDefs = this.columnDefs;
this.reporterGrid.rowData = this.rowDefs;
}
// rest of your file
}
And your reporters component ts file should look like this:
export class ReportersComponent implements OnInit {
private reporterGridOptions: GridOptions;
constructor() {
this.reporterGridOptions = {
enableSorting: true,
enableFilter: true,
enableColResize: true,
};
}
ngOnInit() {
}
// other code...
}
In your reporter component html, you need to pass in this value through the element like this:
<app-reportersgrid [reporterGrid]="reporterGridOptions"></app-reportersgrid>
Another suggestion, I would take some time to properly name things, adjust casing, and format your code so it is easier to read. I hope this helps get you heading in the right direction. Basically you want to pass your options object to the grid component, so it can have access to it.
Also, you do not want to inject a component through a constructor. It will not be the same instance as the component in the template. Components are initialized and destroyed as they are rendered and removed from the view, and do not exist as singletons like services to.

How to access the nested jsondata in angular template, i have tried this using ngFor doesn't work for me

I am trying to access the JSON data inside my angular template but I have no idea how to do it:
JSON DATA:
{
"data": {
"active_cryptocurrencies": 2050,
"active_markets": 15110,
"bitcoin_percentage_of_market_cap": 53.85,
"quotes": {
"USD": {
"total_market_cap": 207937227143.0,
"total_volume_24h": 10373130891.0
}
},
"last_updated": 1540293278
},
"metadata": {
"timestamp": 1540292653,
"error": null
}
}
mycomponent.ts
jsonData: any[];
private _url = 'https://api.coinmarketcap.com/v2/global/';
constructor(private http: Http) {
http.get("https://api.coinmarketcap.com/v2/global/")
.subscribe(response =>{
this.jsonData = response.json().data.quotes;
console.log(this.jsonData);
});
}
So I am trying to show these details in the angular template but it says cannot
find-a-differ-supporting-object-object-object-of-type-object-ngfor
Can you please help me as to how to go with this as json here is little messy?
I simply want to show the JSON data in my html template.
Edited:
import { Component, Input, OnInit,Injectable } from '#angular/core';
import { Http, Headers } from '#angular/http' ;
#Component({
selector: 'hello',
template: `
Hello, Angular
<ul *ngFor="let item of data">
<li>active_markets :{{item.active_markets}}</li>
<li>bitcoin_percentage_of_market_cap:{{item.bitcoin_percentage_of_market_cap}}</li>
<li>last_updated: {{item.last_updated}} </li>
<li>
<ul *ngFor="let q of item.quotes">
<li>total_market_cap: {{q.total_market_cap}}</li>
<li>total_volume_24h: {{q.total_volume_24h}}</li>
</ul>
</li>
</ul>
`,
styles: [`h1 { font-family: Lato; }`]
})
export class HelloComponent {
#Input() name: string;
data:any=[];
private _url = 'https://api.coinmarketcap.com/v2/global/';
constructor(private http: Http) {}
async ngOnInit(){
let obj =(await this.http.get(this._url).toPromise()).json();
you should convert your json object
this.data= Object.keys(obj).map(function(e){
Object.keys(obj[e]).forEach(function(k){
if(typeof obj[e][k] == "object" && (obj[e][k]!=undefined || obj[e][k]!=null )) {
obj[e][k] = Object.keys(obj[e][k]).map(function(l){
return obj[e][k][l];
});
}
}return obj[e];
});
);}}

Angular 6 display data with HttpClient, RxJS and GroupBy

I'm using Ruby on Rails API app for the backend and Angular 6 for the front. this is the json respond I get from the backend:
loclhost3000/courses.json
[
{
id:1,
title:"Introduction",
author:"Dana Inbar",
segments:[
]
},
{
id:2,
title:"Master the ELN",
author:"Dana Inbar",
segments:[
]
},
{
id:3,
title:"Master the Inventory",
author:"Dana Inbar",
segments:[
{
id:1,
unit_id:1,
unit_title:"Introduction",
name:"Lesson 1: Introduction to the inventory module- looking at one collection",
data:"www.video01.com/vid.avi"
},
{
id:2,
unit_id:2,
unit_title:"Inventory Customisation",
name:"Lesson 2: Setting up custom collections",
data:"www.video02.com/vid.avi"
},
{
id:3,
unit_id:2,
unit_title:"Inventory Customisation",
name:"Lesson 3: Adding a custom field",
data:"www.video03.com/vid.avi"
},
{
id:4,
unit_id:2,
unit_title:"Inventory Customisation",
name:"Lesson 4: Creating derived collections",
data:"www.video04.com/vid.avi"
},
{
id:5,
unit_id:2,
unit_title:"Inventory Customisation",
name:"Lesson 5: Using repositories",
data:"www.video05.com/vid.avi"
},
{
id:6,
unit_id:2,
unit_title:"Inventory Customisation",
name:"Quiz",
data:"'[ { "
question 1":"___",
"answers":{
"1":"____",
"2":"____",
"3":"____"
},
"correct_answer":"2"
},
{
"question 2":"___",
"answers":{
"1":"____",
"2":"____"
},
"correct_answer":"1"
}
}
] ' "
}
]
}
]
I have Course model which has many Segments, and Segment is Video or Quiz.
I have course-list, course-detail and course-play components.
I have problem with the course-detail and I want the course-detail page to look like that: course-detail image
I thought I could do functions in course.service which use groupBy with unit_id and unit_title and do two ngFor (or ngFor group) but because I'm new to angular I don't know how is best to implement this.
I'm adding some files from the program which can help:
./courses/course.module
import { NgModule } from '#angular/core';
import { CommonModule } from '#angular/common';
import { RouterModule, Routes } from '#angular/router';
import { MatSidenavModule } from '#angular/material/sidenav';
import { BrowserAnimationsModule } from '#angular/platform-browser/animations';
import { CourseListComponent } from './course-list/course-list.component';
import { CourseDetailComponent } from './course-detail/course-detail.component';
import { CourseService } from './course.service';
import { CoursePlayComponent } from './course-play/course-play.component';
const coursesRoutes: Routes = [
{ path: 'courses', component: CourseListComponent },
{ path: 'courses/:id', component: CourseDetailComponent },
{ path: 'courses/:id/:segment_id', component: CoursePlayComponent }
]
#NgModule({
imports: [
CommonModule,
MatSidenavModule,
BrowserAnimationsModule,
RouterModule.forChild(
coursesRoutes
)
],
declarations: [
CourseListComponent,
CourseDetailComponent,
CoursePlayComponent
],
providers: [
CourseService
]
})
export class CourseModule { }
./courses/course
export interface ICourse {
course_id: number;
title: string;
autor: string;
segments: ISegment[];
}
export interface ISegment {
segment_id: number;
unit_id: number;
unit_title: string;
name: string;
type: string;
data: string;
}
./courses/course.service
import { Injectable } from '#angular/core';
import { HttpClient } from '#angular/common/http';
import { Observable, throwError } from 'rxjs';
import { map, catchError, retry, groupBy, Filter } from 'rxjs/operators';
import { Course } from './course';
// Inject Data from Rails app to Angular app
#Injectable()
export class CourseService{
constructor(private http: HttpClient) { }
private url = 'http://localhost:3000/courses';
private courseUrl = 'http://localhost:3000/courses.json';
// Handle Any Kind of Errors
private handleError(error: HttpErrorResponse) {
// A client-side or network error occured. Handle it accordingly.
if (error.error instanceof ErrorEvent) {
console.error('An error occured:', error.error.message);
}
// The backend returned an unsuccessful response code.
// The response body may contain clues as to what went wrong.
else {
console.error(
'Backend returned code ${error.status}, ' +
'body was ${error.error}');
}
// return an Observable with a user-facing error error message
return throwError(
'Something bad happend; please try again later.');
}
// Get All Courses from Rails API App
getCourses(): Observable<ICourse[]> {
const coursesUrl = `${this.url}` + '.json';
return this.http.get<ICourse[]>(coursesUrl)
.pipe(
catchError(this.handleError)
);
}
// Get Single Course by id. will 404 if id not found
getCourse(id: number): Observable<ICourse> {
const detailUrl = `${this.url}/${id}` + '.json';
return this.http.get<ICourse[]>(detailUrl)
.pipe(
catchError(this.handleError)
);
}
}
./courses/course-detail/course-detail.component
import { Component, OnInit } from '#angular/core';
import { ActivatedRoute, Router } from '#angular/router';
import { Course } from '../course';
import { CourseService } from '../course.service';
#Component({
selector: 'lg-course-detail',
templateUrl: './course-detail.component.html',
styleUrls: ['./course-detail.component.sass']
})
export class CourseDetailComponent implements OnInit {
course: ICourse;
errorMessage: string;
constructor(private courseService: CourseService,
private route: ActivatedRoute,
private router: Router) {
}
ngOnInit() {
const id = +this.route.snapshot.paramMap.get('id');
this.getCourse(id);
}
// Get course detail by id
getCourse(id: number) {
this.courseService.getCourse(id).subscribe(
course => this.course = course,
error => this.errorMessage = <any>error);
}
onBack(): void {
this.router.navigate(['/courses']);
}
}
./courses/course-detail/course-detail.html
<div id="main" *ngIf="course">
<div class="row" id="image">
<div class="col-lg-8">
<br>
<img src="./assets/images/lg-white.png" class="d-inline-block align-top" alt="">
</div>
</div>
<div class="row" id="header">
<div class="container text-center">
<br>
<h1>{{course.title}}</h1>
<br>
</div>
</div>
<div class="row justify-content-lg-center" id="progress">
<div class="container text-center">
<div class="progress">
<div class="progress-bar bg-white"></div>
</div>
<td>Your Progress</td>
<br><br><br>
</div>
</div>
<div class="row" id="body">
<div class="container">
<br>
<ul class="nav nav-tabs" role="tablist">
<li class="nav-item">
<a class="nav-link active" href="#Curiculum" role="tab" data-toggle="tab">Curiculum</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#About" role="tab" data-toggle="tab">About this course</a>
</li>
</ul>
<br>
<!-- Tab panes -->
<div class="tab-content">
<div role="tabpanel" class="tab-pane fade in active" id="Curiculum">
<h1>Course Overview</h1>
<br>
<ul *ngFor="let segment of course.segmentsByUnitId">
<ul>
<li id="title">Unit {{segment.unit_id}}: {{segment.unit_title}}</li>
<li>{{segment.name}}</li>
</ul>
</ul>
</div>
<div role="tabpanel" class="tab-pane fade" id="About">
<h1>Course Topics:</h1>
</div>
</div>
<br>
</div>
</div>
</div>
./courses/course-detail/course-detail.sass
$color: #FFFFFF
$bg-col: #5c0099
$prog-size: 10px
#image
background-color: $bg-col
color: $color
#header
background-color: $bg-col
color: $color
#body
background-color: $color
height: 100vh
max-width: initial
display: flex
#title
font-weight: bold
#progress
background-color: $bg-col
color: $color
font-size: $prog-size
.progress
height: 10px
left: 30%
.progress-bar
width: 10%
height: 20px
background-color: transparent
You can do it by using the below groupby pipes.
GroupBy pipe returns an object of a key/value pair.
https://github.com/danrevah/ngx-pipes#groupby
The installation process for ngx-pipes: https://github.com/danrevah/ngx-pipes#installation
Below is how I implemented it for my data:
My data:
tsks = [{
CompletedFlag: true,
ProgressFlag: false,
DueDate:"2014-10-02T13:12:37.027",
Signup: "2014-10-04T11:51:10.137",
ObMilestone: 1,
ObTask: 119,
AssignedToId: 0,
Company: "ABC Corp",
Description: "Lorem Ipsum",
Favourite: null,
FirstName: "Libin",
LastName: "J",
MilestoneName: "Blue",
OnboarderStatus: "Live",
Partner : null
},
{
CompletedFlag: true,
ProgressFlag: false,
DueDate:"2014-10-02T13:12:37.027",
Signup: "2014-10-04T11:51:10.137",
ObMilestone: 1,
ObTask: 119,
AssignedToId: 0,
Company: "ABC Corp",
Description: "Lorem Ipsum",
Favourite: null,
FirstName: "Libin",
LastName: "J",
MilestoneName: "Blue",
OnboarderStatus: "Live",
Partner : null
}];
My code to groupby "MilestoneName"
<div class="row" *ngFor="let task of tsks | groupBy: 'MilestoneName' | pairs">
<div>Group milestone name: {{task[0]}}</div>
<div class="row" *ngFor="let t of task[1]">
<div>Task: {{t.FirstName}}</div>
</div>
</div>

Get elements from Observable (Json object)

I have a Http request which give me the following Json that save in an observable
{
"proyecto":{
"nombre": "Mercado de Ideas",
"tecnologias": [
{
"nombre": ".NET",
"icono": "http://getsetwebsite.com/wp-content/uploads/2016/07/net.png"
},
{
"nombre": "Angular",
"icono": "http://fourcast.io/wp-content/uploads/2016/10/angular.png"
}
],
"tiempo_restante": 80,
"alcance_restante": 90,
"recursos_devengados": 22
}
}
and save the observable with the following code
import { Component } from '#angular/core';
import { NavController, NavParams } from 'ionic-angular';
import { Observable } from 'rxjs/Observable';
import { KpisProvider } from '../../providers/kpis/kpis';
/**
* Generated class for the ProyectoDetailsPage page.
*
* See http://ionicframework.com/docs/components/#navigation for more info
* on Ionic pages and navigation.
*/
#Component({
selector: 'page-proyecto-details',
templateUrl: 'proyecto-details.html',
})
export class ProyectoDetailsPage {
public projectID: number;
public project : Observable<any>;
constructor(
public navCtrl : NavController,
public navParams: NavParams,
public kpis : KpisProvider
) {
this.projectID = this.navParams.get("projectID");
console.log(this.projectID)
}
ionViewDidLoad() {
console.log('ionViewDidLoad ProyectoDetailsPage');
this.project = this.kpis.getUserDetails(this.projectID);
console.log(this.project);
}
}
How to get the parameters, for example the "nombre" or "tiempo_restante" in the html? and obtain something like that
You have to subscribe to observable inorder to receive a data from it
this.kpis.getUserDetails(this.projectID).subscribe(
(data) => this.project = data
);
Html
{{project?.proyecto?.tiempo_restante}}
{{project?.proyecto?.nombre}}
Otherway you can implicitly subscribe to observable by using async pipe over the HTML.
<div *ngFor="let item in (project | async)?.proyecto.tecnologias">
{{item.nombre}}
{{item.icono}}
</div>