Basic Angular tutorial

This page has been fully written by
Domitille Bertin (Epita, AppingX-2020)
Christian Martins (Epita, AppingX-2020)
and validated by Thomas Broussard

What is Angular?

General purpose

Angular is a web front-end framework that helps developers building modern, responsive apps that work on a wide variety of platforms. Indeed, Angular can be used to build progressive web apps, which can be run on web browsers or as regular apps on smartphones (see Ionic framework or computers (see Electron framework ).

More precisely, Angular allows developers to build Single Page Applications (SPA). SPAs are essentially websites on which navigation does not require any page reloading when clicking on links. Google Maps is the perfect example of this concept. If a user types an address on the search bar, there is no page reloading, which would be critical for user experience. Instead, the current page is simply reorganized to show the requested information: map position changes, and the UI displays new relevant data etc.

Angular versions

In 2009, Google released the first version of AngularJS (note the «JS» suffix), which can be considered as Angular’s «big brother», Angular version 1. Later on, in 2016, Angular came out as the new version of AngularJS. This new major version was a complete change of paradigm and implied many breaking changes. One of them is the fact that Angular is written in TypeScript, which has become the officially supported language for the framework. Moreover, since Angular 2, an Angular CLI has been introduced allowing developers to manage dependencies, generating code, building and deploying their apps more easily.

As these lines a being written, AngularJS has been put under Long Term Support (LTS). This means Google no longer delivers new features, but only provides bug fixes. Meanwhile, there are still many projects running on AngularJS which have not upgraded to Angular. This is mainly because the gap between these two versions is too important and the cost of upgrading too high, particularly for larger projects.

TypeScript

TypeScript brings, among other features, strict typing and backwards-compatibility to regular JavaScript. While TypeScript is a programming language on its own, it is considered to be a superset of JavaScript because it is always eventually compiled to JavaScript.

Angular is built with TypeScript and developers are highly advised to use it, even if they could still use the framework with regular JavaScript.

Angular key paradigms

MVC pattern

The way Angular apps are built strongly relies on the Model-View-Controller (MVC) pattern and Angular makes it easy to implement.

ControllerModelViewservicecomponent classtransport classcomponent view
MVC with angular concept mappings

The fact that MVC separates the data logic (Model/Service) from the UI logic (View/Template) greatly improves maintainability, modularity and makes it easy to implement new features.

Just to make it clear, here is a recap of the Angular MVC terminology in a table.

MVC conceptAngular equivalentPurpose
ModelTransport (TypeScript)Retrieves and manages data.
Can communicate with a REST API.
ViewTemplateDisplays data.
Composed of HTML and CSS.
ControllerComponent + ServiceMap the user actions to backend features

Concrete examples are provided later in this tutorial.

Dependency injection

Angular also relies on the Dependency Injection (DI) pattern and exposes its own internal system to manage it easily. Below is a simplified diagram of how DI works in Angular.

Classes usually need Dependencies to perform their job, which are, most of the time, Angular Services classes that provide data, and data management API s. The DI pattern states that it is the DI system that is responsible for instantiating the service classes once, rather than the dependent classes themselves.This works amazingly with the MVC pattern and makes the final app more efficient, modular, and maintainable.

REpresentational State Transfer (REST)

Most apps usually have two parts: a front-end (the app itself) and a back-end. The back-end stores and manages the data, it is invisible to the user. Usually, it is a server which can send data in an organized way and handle requests that modify this data. The front-end, on the other hand, is what the user sees: the interface he is presented with. The front-end displays data and forms that allow modifying this data. When the user validates his input, the front-end sends the modifications to the back-end, which saves it.

As a back-end, many Angular apps use REpresentational State Transfer (REST) APIs. REST is a software architecture that defines a set of rules (a norm) for managing Resources over a server. It is possible to build a REST API with any programming language that handles the HTTP protocol. Indeed, most REST API s communicate through HTTP, even though other protocols can be used as a replacement, like FTP. For this tutorial, we will consider that REST APIs solely rely on the HTTP protocol.

Basically, a REST API exposes interfaces on which actions can be made. A concrete example would be a student interface on a College student management server. Typically, this interface would exposed at an URL like https://epita.net/api/students on which the front-end could send requests with different HTTP methods like:

Creating a student-management app

In the last part of this tutorial, we will create a student management app that :

We will cover, in a concrete way the concepts explained at the beginning of the tutorial.

Prerequisites

For this tutorial, you will need:

Note: this tutorial does not aim at teach you how to create a REST API but only how to use it with Angular. If you are interested on how to create a RESTful HTTP Server, the code is also provided, but not explained here.

Creating a new project

Initializing a project with the Angular CLI

Once you have got everything you need, open up a terminal, navigate to the directory you want you project to be in and run the following command:

ng new college-app

When asked to choose:

This command initializes a new project. The main folder we will work on is the src folder, which currently contains different files:

Cleaning the default template

Now that we have this ready, lets open the app.component.html Template and replace all of its content by:

<p>
    Hello World!
</p>

Serving the app with the Angular CLI

Check that everything is working fine, run the following command on your terminal:

ng serve

When «Compiles successfully» appears on the console, open your favorite browser and navigate to http://localhost:4200. At this point, you should get a webpage that displays «Hello World!».

Creating a Student Service

Generating a Service with the Angular CLI

The first thing we will is to create a StudentService that will fetch the students from our back-end server, our REST API. To do so, run the following command on your terminal:

ng generate service Student

This command generates a new empty Angular Service by creating a student.service.ts file. Let’s take a look at it.

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

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

  constructor() { }
}

Notice the @@Injectable@ annotation. It makes the StudentService class available for Dependency Injection. The providedIn metadata option specifies that the Service will be injectable through the root injector, which means the entire app in our case.

Creating a data Model

Our Service will manage students. From a programming point-of-view, this is a Model. In most apps, this would translate into a Student class that allows manipulating instances.However, for our example, we will simply create an IStudent that describes what our back-end server can send us.

Let’s create a Student.ts file inside the src/app folder of our project containing the following code.

export interface IStudent {
  id: number;
  firstName: string;
  lastName: string;
  age: number;
  grade: number;
}

Communicating over HTTP

Introduction

We want out StudentService to fetch the IStudent objects from the College server. Once the Service has got that data, all Components on which it will be injected into will be able to get the list of IStudent objects.

Below is a diagram that shows how our StudentService will interact.

Importing the HttpClientModule and injecting the HttpClient service

First, we need to import Angular’s HttpClientModule into our app. To do so, open the app.module.ts file, locate the imports array in the @@NgModule@ annotation and add HttpClientModule to it. This requires importing the symbol from @@angular/common/http@. Your file should look like so:

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

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

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

Now that the HttpClientModule is available in our app, we need to inject it inside the StudentService. To do so, change the Service’s constructor signature in the student.service.ts file:

constructor(private _httpClient: HttpClient) { }

By adding a private attribute of type HttpClient in the constructor’s signature, Angular knows that it needs to inject the service into our StudentService service. (Yeah, services can be injected in other services!)

Using the HttpClient service

Now that we have the HttpClient service available, let’s code a getStudents method that will use it to make a HTTP request to our back-end server in order to retrieve the list of all students.

public getStudents(): Observable<IStudent[]> {
  return this._httpClient.get<IStudent[]>('http://localhost:3000/students');
}

There are a few things that need to be discussed here:

That’s it! Our StudentService is ready to fetch our Student list.

Creating a Students Component

Now that we have a Service to fetch all the students from our back-end server, we want to display it. Remember that in Angular, we use Components and Templates to display data. We are going to create a StudentsComponent and inject our StudentService. This way, the Component will be able to get the students and display it on our app.

Generate a Component with Angular CLI

To generate our component, run the following command:

ng generate component Students

This command creates a students directory inside the src/app folder.

Injecting and consuming the StudentService

First of all, we need to inject the StudentService we previously built into our new Component. To do so, open the students.component.ts file and modify its constructor prototype:

constructor(private _studentsService: StudentService) { }

Now Angular knows it has to inject the StudentService inside our StudentsComponent.

Our Component also need an attribute to store the list of students that will be fetched from the StudentService. Just add it in the class like so:

public students: IStudent[];

The next step is to Observe the Students list from the Service. To do so, we will subscribe to the Observable in the ngOninit method of our Component. Have a look at the following code.

ngOnInit() {
  this._studentsService
    .getStudents()
    .subscribe((students: IStudent[]) => this.students = students);
}

The Observable.subscribe method takes a callback that will be called when the students list has been fetched from the server. The list is then passed as the first argument to the callback, which will set our components internal students list.

At this point, your students.component.ts file should look like this:

import { Component, OnInit } from '@angular/core';
import {StudentService} from '../student.service';
import {IStudent} from '../Student';

@Component({
  selector: 'app-students',
  templateUrl: './students.component.html',
  styleUrls: ['./students.component.scss']
})
export class StudentsComponent implements OnInit {

  public students: IStudent[];

  constructor(private _studentsService: StudentService) { }

  ngOnInit() {
    this._studentsService
      .getStudents()
      .subscribe((students: IStudent[]) => {
        console.log(students);
        this.students = students;
      });
  }

}

Data binding from Component to Template

Now that our StudentsComponent retrieves data from our server through the StudentService, we need to display it in the View (Angular Template). To do so, open the students.component.html file and fill it with the following code:

<h2>Students list</h2>

<ul *ngIf="students && students.length > 0">
  <li *ngFor="let student of students">
    <strong>{{student.firstName}} {{student.lastName | uppercase}}</strong>
    <br>Age: {{student.age}}
    <br>Grade: {{student.grade}}/20
  </li>
</ul>

<p *ngIf="!students || !students.length">
  There are no students!
</p>

Many lines need explanations here.

Using the app-student component

At this point, we have:

Now the last thing we need to do is to use the use the consume the StudentsComponent we have created.

Let’s first go back to the students.component.ts file and notice line 6: selector: 'app-students',. This line declares the HTML tag of the Component. We must add a app-students tag to our app.component.html file to instantiate the StudentsComponent on our app. Let’s do so:

<app-students></app-students>

Save this file, run the ng serve command if needed, and navigate to http://localhost:4200 on your web browser.

You should obtain something like this:

There it is! Our students list has been fetched from our back-end server and displayed on our app!

To go further

This is a very basic app that only displays data. A more serious app would obviously be more stylish and allow editing students, changing their grade etc. Take a deep look at the Official Angular Documentation to learn more and go further with this app!

Credits

This tutorial has been made as an assignment for Mr. Thomas BROUSSARD.

EPITA APPING X 2 2020_