Using the async Pipe with HttpClientModule in Angular

server.service.ts

import {Injectable} from '@angular/core';
import {HttpClient, HttpHeaders} from '@angular/common/http';
import {Server} from './server';
import {Observable} from 'rxjs/Observable';
import {catchError, map} from 'rxjs/operators';

@Injectable({
  providedIn: 'root'
})
export class ServerService {

  constructor(private http: HttpClient) {
  }

  putAppName(name: string) {
    const appName = {'AppName': name};
    this.http.put('https://angularsamples.firebaseio.com/data.json', appName).subscribe();
  }

  getAppName() {
    return this.http.get('https://angularsamples.firebaseio.com/data.json').pipe(
      map((value, index) => {
        return value['AppName'];
      })
    );
  }
}

app.component.html

<div class="container">
  <div class="row">
    <div class="col-xs-12 col-sm-10 col-md-8 col-sm-offset-1 col-md-offset-2">
      <div>
        App Name : <input type="text" [(ngModel)]="appName"/>
        &nbsp;
        <button class="btn btn-default" (click)="onSaveAppName()">Save</button>
        &nbsp;
        <p>{{appNameServer | async }}</p>
      </div>
    </div>
  </div>
</div>

app.component.ts

import {Component, OnInit} from '@angular/core';
import {ServerService} from './server.service';
import {Server} from './server';
import {catchError, map, retry} from 'rxjs/operators';
import {of} from 'rxjs';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit {
  appName = '';
  appNameServer;


  ngOnInit(): void {
    this.appNameServer = this.server.getAppName();
  }

  constructor(private server: ServerService) {
  }

  onSaveAppName() {
    this.server.putAppName(this.appName);
  }
}

 

Sending GET Requests with HttpClientModule in Angular

server.ts

export interface Server {
  name: string;
  capacity: number;
  id: number;
}

app.component.html

<div class="container">
  <div class="row">
    <div class="col-xs-12 col-sm-10 col-md-8 col-sm-offset-1 col-md-offset-2">
      <input type="text" #serverName>
      <button class="btn btn-primary" (click)="onAddServer(serverName.value)">Add Server</button>
      <br><br>
      <button class="btn btn-primary" (click)="onPostServer()">Post Server</button>
      &nbsp;
      <button class="btn btn-primary" (click)="onPutServer()">Put Server</button>
      &nbsp;
      <button class="btn btn-primary" (click)="onGetServer()">Get Server</button>
      &nbsp;
      <button class="btn btn-primary" (click)="onGetServer2()">Get Server 2</button>
      &nbsp;
      <button class="btn btn-primary" (click)="onGetServer3()">Get Server 3</button>
      <hr>
      <div *ngFor="let s of fetchedServers">
        {{s.name}} , {{s.capacity}} = > {{s.id}}
      </div>
      <hr>
      <ul class="list-group" *ngFor="let server of servers">
        <li class="list-group-item">{{ server.name }} (ID: {{ server.id }})</li>
      </ul>
    </div>
  </div>
</div>

server.service.ts

import {Injectable} from '@angular/core';
import {HttpClient, HttpHeaders} from '@angular/common/http';
import {Server} from './server';
import {Observable} from 'rxjs/Observable';
import {catchError, map} from 'rxjs/operators';

@Injectable({
  providedIn: 'root'
})
export class ServerService {

  constructor(private http: HttpClient) {
  }

  postServers(servers: any[]) {

    const headers = new HttpHeaders().set('Content-Type', 'application/json');

    this.http.post('https://angularsamples.firebaseio.com/data.json', servers, {
      headers: headers
    }).subscribe(value => {
      console.log(value);
    });
  }

  putServers(servers: any[]) {

    const headers = new HttpHeaders().set('Content-Type', 'application/json');

    this.http.put('https://angularsamples.firebaseio.com/data.json', servers, {
      headers: headers
    }).subscribe(value => {
      console.log(value);
    });
  }

  getServers() {
    this.http.get<Server[]>('https://angularsamples.firebaseio.com/data.json').subscribe((value: Server[]) => {
      for (const s of value) {
        console.log(s);
      }
    });
  }

  getServers2(): Observable<Server[]> {
    return this.http.get<Server[]>('https://angularsamples.firebaseio.com/data.json');
  }
}

app.component.html

import {Component} from '@angular/core';
import {ServerService} from './server.service';
import {Server} from './server';
import {catchError, map, retry} from 'rxjs/operators';
import {of} from 'rxjs';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {

  fetchedServers: Server[];

  servers = [
    {
      name: 'Testserver',
      capacity: 10,
      id: this.generateId()
    },
    {
      name: 'Liveserver',
      capacity: 100,
      id: this.generateId()
    }
  ];

  constructor(private server: ServerService) {
  }

  onPostServer() {
    this.server.postServers(this.servers);
  }

  onPutServer() {
    this.server.putServers(this.servers);
  }

  onAddServer(name: string) {
    this.servers.push({
      name: name,
      capacity: 50,
      id: this.generateId()
    });
  }

  private generateId() {
    return Math.round(Math.random() * 10000);
  }

  onGetServer() {
    this.server.getServers();
  }

  onGetServer2() {
    this.server.getServers2().subscribe((value: Server[]) => {
      this.fetchedServers = value;
    });
  }

  onGetServer3() {
    this.server.getServers2().pipe(
      retry(3), // Retry up to 3 times before failing
      map((value: Server[], index: number) => {
        for (const s of value) {
          if (s.id === 0) {
            s.capacity = -1;
            s.name = '';
          }
        }

        return value;
      }),
      catchError(err => of([]))
    ).subscribe({
      next(v) {
        console.log('Value : ' + v);
      },
      error(e) {
        console.log('Error : ' + e);
      }
    });
  }
}

References
https://angular.io/guide/http#getting-json-data
https://angular.io/guide/rx-library#operators

Adjusting Request Headers with HttpClientModule in Angular

postServers(servers: any[]) {

  const headers = new HttpHeaders().set('Content-Type', 'application/json');

  this.http.post('https://angularsamples.firebaseio.com/data.json', servers, {
    headers: headers
  }).subscribe(value => {
    console.log(value);
  });
}

putServers(servers: any[]) {

  const headers = new HttpHeaders().set('Content-Type', 'application/json');

  this.http.put('https://angularsamples.firebaseio.com/data.json', servers, {
    headers: headers
  }).subscribe(value => {
    console.log(value);
  });
}

References
https://angular.io/guide/http#adding-headers

Post and Put Request with HttpClientModule in Angular

app.module.ts

import {BrowserModule} from '@angular/platform-browser';
import {NgModule} from '@angular/core';
import {FormsModule} from '@angular/forms';

import {AppComponent} from './app.component';
import {HttpClientModule} from '@angular/common/http';

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    FormsModule,
    HttpClientModule
  ],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule {
}

server.service.ts

import {Injectable} from '@angular/core';
import {HttpClient} from '@angular/common/http';

@Injectable({
  providedIn: 'root'
})
export class ServerService {

  constructor(private http: HttpClient) {
  }

  postServers(servers: any[]) {
    this.http.post('https://angularsamples.firebaseio.com/data.json', servers).subscribe(value => {
      console.log(value);
    });
  }

  putServers(servers: any[]) {
    this.http.put('https://angularsamples.firebaseio.com/data.json', servers).subscribe(value => {
      console.log(value);
    });
  }
}

app.component.ts

import {Component} from '@angular/core';
import {ServerService} from './server.service';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  servers = [
    {
      name: 'Testserver',
      capacity: 10,
      id: this.generateId()
    },
    {
      name: 'Liveserver',
      capacity: 100,
      id: this.generateId()
    }
  ];

  constructor(private server: ServerService) {
  }

  onPostServer() {
    this.server.postServers(this.servers);
  }

  onPutServer()
  {
    this.server.putServers(this.servers);
  }

  onAddServer(name: string) {
    this.servers.push({
      name: name,
      capacity: 50,
      id: this.generateId()
    });
  }

  private generateId() {
    return Math.round(Math.random() * 10000);
  }
}

References
https://angular.io/guide/http#making-a-post-request
https://angular.io/guide/http#making-a-put-request

Understanding the async Pipe in Angular

app.component.ts

import {Component} from '@angular/core';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {


  appStatus = new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve('stable');
    }, 2000);
  });

  servers = [
    {
      instanceType: 'medium',
      name: 'Production Server',
      status: 'stable',
      started: new Date(15, 1, 2017)
    },
    {
      instanceType: 'large',
      name: 'User Database',
      status: 'stable',
      started: new Date(15, 1, 2017)
    },
    {
      instanceType: 'small',
      name: 'Development Server',
      status: 'offline',
      started: new Date(15, 1, 2017)
    },
    {
      instanceType: 'small',
      name: 'Testing Environment Server',
      status: 'stable',
      started: new Date(15, 1, 2017)
    }
  ];

  getStatusClasses(server: { instanceType: string, name: string, status: string, started: Date }) {
    return {
      'list-group-item-success': server.status === 'stable',
      'list-group-item-warning': server.status === 'offline',
      'list-group-item-danger': server.status === 'critical'
    };
  }
}

app.component.html

<div class="container">
  <div class="row">
    <div class="col-xs-12 col-sm-10 col-md-8 col-sm-offset-1 col-md-offset-2">

      <h3>App Status : {{appStatus|async}}</h3>

      <ul class="list-group">
        <li
          class="list-group-item"
          *ngFor="let server of servers"
          [ngClass]="getStatusClasses(server)">
          <span
            class="badge">
            {{ server.status }}
          </span>
          <strong>{{ server.name | shorten:5}}</strong> |
          {{ server.instanceType | uppercase }} |
          {{ server.started | date:'fullDate' | uppercase }}
        </li>
      </ul>
    </div>
  </div>
</div>

References
https://angular.io/api/common/AsyncPipe

Parametrizing a Custom Pipe in Angular

shorten.pipe.ts

import {Pipe, PipeTransform} from '@angular/core';

@Pipe({
  name: 'shorten'
})
export class ShortenPipe implements PipeTransform {

  transform(value: any, limit: number): any {
    if (value.length > limit) {
      return value.substr(0, limit) + ' ...';
    }
    return value;
  }
}

app.component.html

<div class="container">
  <div class="row">
    <div class="col-xs-12 col-sm-10 col-md-8 col-sm-offset-1 col-md-offset-2">
      <ul class="list-group">
        <li
          class="list-group-item"
          *ngFor="let server of servers"
          [ngClass]="getStatusClasses(server)">
          <span
            class="badge">
            {{ server.status }}
          </span>
          <strong>{{ server.name | shorten:5}}</strong> |
          {{ server.instanceType | uppercase }} |
          {{ server.started | date:'fullDate' | uppercase }}
        </li>
      </ul>
    </div>
  </div>
</div>

References
https://angular.io/guide/pipes#custom-pipes

Chaining Multiple Pipes in Angular

app.component.html

<div class="container">
  <div class="row">
    <div class="col-xs-12 col-sm-10 col-md-8 col-sm-offset-1 col-md-offset-2">
      <ul class="list-group">
        <li
          class="list-group-item"
          *ngFor="let server of servers"
          [ngClass]="getStatusClasses(server)">
          <span
            class="badge">
            {{ server.status }}
          </span>
          <strong>{{ server.name }}</strong> |
          {{ server.instanceType | uppercase }} |
          {{ server.started | date:'fullDate' | uppercase }}
        </li>
      </ul>
    </div>
  </div>
</div>

References
https://angular.io/guide/pipes#chaining-pipes