0% found this document useful (0 votes)
9 views

Angular

Angular is a TypeScript-based development platform that provides a component-based framework, integrated libraries, and developer tools for building scalable web applications. It evolved from AngularJS, which introduced significant features like MVC architecture and two-way data binding, but was eventually succeeded by Angular in 2016 due to the need for modernization. The platform supports a modular architecture, dynamic data management, and two-way data binding, making it suitable for both small and enterprise-level applications.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
9 views

Angular

Angular is a TypeScript-based development platform that provides a component-based framework, integrated libraries, and developer tools for building scalable web applications. It evolved from AngularJS, which introduced significant features like MVC architecture and two-way data binding, but was eventually succeeded by Angular in 2016 due to the need for modernization. The platform supports a modular architecture, dynamic data management, and two-way data binding, making it suitable for both small and enterprise-level applications.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 54

Angular

1
Angular
Angular is a development platform, built on TypeScript. As a platform, Angular includes:

A component-based framework for building scalable web applications


A collection of well-integrated libraries that cover a wide variety of features, including routing, forms management, client-
server communication, and more
A suite of developer tools to help you develop, build, test, and update your code

With Angular, you're taking advantage of a platform that can scale from single-developer projects to enterprise-level
applications. Angular is designed to make updating as straightforward as possible, so take advantage of the latest
developments with minimal effort. Best of all, the Angular ecosystem consists of a diverse group of over 1.7 million developers,
library authors, and content creators.

According to the 2022 StackOverflow survey, 23 percent of software engineers apply the framework to create user interfaces.

2
History of Angular
Its history traces back to 2009 when Misko Hevery and Adam Abrons, Google engineers, developed the framework known as
AngularJS and officially released it in 2010.

AngularJS revolutionized web development by providing a convenient way to build dynamic, single-page applications (SPAs).

Designing complex dynamic web pages with pure or vanilla JavaScript is time-consuming. Not to mention that, in big projects
involving many programmers, the front-end is a challenge to understand and maintain. So, the key idea behind AngularJS was
to simplify SPA development by introducing several considerable advantages.

MVC architecture: AngularJS divides your web app into three distinct parts — Model (data), View (the UI layer), and Controller
(business logic). The three units can be developed in parallel and separately tested. As a result, the code becomes easier to
understand, maintain, and extend.

Two-way data binding: The JavaScript framework synchronizes the Model and the View by applying a two-way data binding
technique. As the data in the Model changes, the View does too. This allows engineers to reduce development time as it
doesn’t require writing additional code to provide continual View and Model synchronization.

3
History of Angular
Dependency injection (DI): AngularJS comes with a built-in mechanism to pass (inject) dependencies — or rules defining how
pieces of code interact with each other and behave under certain conditions — instead of creating them inside the
components. This enables developers to change or configure dependencies without altering an app module as well as reuse
them across multiple modules. All in all, DI simplifies testing and contributes to the reusability and maintainability of app
components.

Featuring a prominent set of benefits, AngularJS quickly grew in popularity. But unfortunately for the framework, technologies
developed even faster. Before long, the platform stopped meeting the rising requirements of the web and lost its position to
newer competitors. So, in 2014, Google decided to completely rewrite it.

For several years, AngularJS has existed side by side with its successor simply named Angular. But in 2022, it, at last, reaches the
end of life, i.e., the community will no longer maintain the framework. That said, devoted users can still find support from third
parties, and AngularJS code will remain on GitHub.

4
AngularJS vs Angular
In September 2016, Google released Angular 2. The difference between the old AngularJS and the new version was so radical
that you couldn’t just update from one to the other. The main changes are as follows.

TypeScript instead of JavaScript: Unlike its JS-based predecessor, Angular uses TypeScript.

Better performance: Both AngularJS and Angular significantly reduce development time. However, due to the component-
based architecture and more effective data binding, Angular apps can be five times faster than AngularJS.

Introducing CLI AngularJS doesn’t have its own command line interface (CLI). Angular 2+, on the other hand, comes with a CLI
that allows for quick generation of components, services, directives, etc.

Mobile-friendliness AngularJS was not designed with mobile browsers in mind. When developing Angular, Google took into
account this gap so the new framework got the support for mobile web and native mobile apps.

Ver 18 was relased on May 22th 2024

5
Setting up the development environment
You can use the Angular CLI to create projects, generate application and library code, and perform a variety of ongoing
development tasks such as testing, bundling, and deployment.

To install the Angular CLI, open a terminal window and run the following command: npm install -g @angular/cli

To create a new workspace and initial starter app:

Run the CLI command ng new and provide the name my-app: ng new my-app

The ng new command prompts you for information about features to include in the initial app. Accept the defaults by
pressing the Enter or Return key.

The Angular CLI includes a server, for you to build and serve your app locally.

cd my-app
ng serve --open

6
The ng serve command launches the server, watches your files, and rebuilds the app as you make changes to those files.

The --open (or just -o ) option automatically opens your browser to http://localhost:4200/.

If the installation and setup was successful, you should see a page similar to the following.

App

7
Project Architecture
.vscode: Includes VS Code configuration files

node_modules: Includes npm packages needed for development and running the Angular application

src: Contains the source files of the application

.editorconfig: Defines coding styles for your editor

.gitignore: Specifies files and folders that Git should not track

angular.json: The main configuration file of the Angular CLI workspace

package.json and package-lock.json: Provide definitions of npm packages, along with their exact versions, which are
needed to develop, test, and run the Angular application

README.md: A README file that is automatically generated from the Angular CLI

tsconfig.app.json: TypeScript configuration that is specific to the Angular application

tsconfig.json: TypeScript configuration that is specific to the Angular CLI workspace

tsconfig.spec.json: TypeScript configuration that is specific to unit tests


8
Project Architecture
When we develop an Angular application, we’ll likely interact with the src folder. It is where we write the code and tests of our
application. It is also where we define the styles of our application and any static assets we use, such as icons, images, and
JSON files. It contains the following:

app: Contains all the Angular-related files of the application. You interact with this folder most of the time during
development.

assets: Contains static assets such as fonts, images, and icons.

favicon.ico: The icon displayed in the tab of your browser, along with the page title.

index.html: The main HTML page of the Angular application.

main.ts: The main entry point of the Angular application.

styles.css: Contains application-wide styles. These are CSS styles that apply globally to the Angular application. The
extension of this file depends on the stylesheet format you choose when creating the application

9
Project Architecture
The app folder contains the actual source code we write for our application. Developers spend most of their time inside that
folder. The Angular application that is created automatically from the Angular CLI contains the following files:

app.component.css: Contains CSS styles specific for the sample page

app.component.html: Contains the HTML content of the sample page

app.component.spec.ts: Contains unit tests for the sample page

app.component.ts: Defines the presentational logic of the sample page

app.module.ts: Defines the main module of the Angular application

10
Angular Essentials
Components
Managing dynamic data
Rendering dynamic templates
Conditional and loops
Handling User Interaction
Sharing logic

11
Components
Components provide structure for organizing your project into easy-to-understand parts with clear responsibilities so that your
code is maintainable and scalable.

Here is an example of how a Todo application could be broken down into a tree of components.

12
Defining a component
Every component has the following core properties:

A @Componentdecorator that contains some configuration


An HTML template that controls what renders into the DOM
A CSS selector that defines how the component is used in HTML
A TypeScript class with behaviors such as managing state, handling user input, or fetching data from a server.

// todo-list-item.component.ts
@Component({
standalone: true,
selector: 'todo-list-item',
template: ` <li>(TODO) Read Angular Essentials Guide</li> `,
styles: `li {
color: red;
font-weight: 300;
}`,
})
export class TodoListItem {
/* Component behavior is defined in here */
}
13
Separating HTML and CSS into separate files:
// todo-list-item.component.ts
@Component({
standalone: true,
selector: 'todo-list-item',
templateUrl: './todo-list-item.component.html',
styleUrl: './todo-list-item.component.css',
})
export class TodoListItem {
/* Component behavior is defined in here */
}

<!-- todo-list-item.component.html -->


<li>(TODO) Read Angular Essentials Guide</li>

/* todo-list-item.component.css */
li {
color: red;
font-weight: 300;
}

14
Using a Component
One advantage of component architecture is that your application is modular. In other words, components can be used in
other components.

To use a component, you need to:

Import the component into the file


Add it to the component's imports array
Use the component's selector in the template

// todo-list.component.ts
import {TodoListItem} from './todo-list-item.component.ts';
@Component({
standalone: true,
imports: [TodoListItem],
template: `
<ul>
<todo-list-item></todo-list-item>
</ul>
`,
})
export class TodoList {}
15
Managing Dynamic Data
Define component state (i.e. component's data) and behavior to manage dynamic data.

To define state, you use class fields syntax inside of your component.

When you want to update state, this is typically accomplished by defining methods in the component class that can access the
various class fields with the this keyword.

// todo-list-item.component.ts
@Component({ ... })
export class TodoListItem {
taskTitle = '';
isComplete = false;
completeTask() {
this.isComplete = true;
}
updateTitle(newTitle: string) {
this.taskTitle = newTitle;
}
}

16
Rendering dynamic data
When you need to display dynamic content in your template, Angular uses the double curly brace syntax in order to distinguish
between static and dynamic content.

Here is a simplified example from a TodoListItem component.

@Component({
selector: 'todo-list-item',
template: `
<p>Title: {{ taskTitle }}</p>
`,
})
export class TodoListItem {
taskTitle = 'Read cup of coffee';
}

This syntax declares an interpolation between the dynamic data property inside of the HTML. As a result, whenever the data
changes, Angular will automatically update the DOM reflecting the new value of the property.

17
Dynamic Properties
When you need to dynamically set the value of standard DOM properties on an HTML element, the property is wrapped in
square brackets to inform Angular that the declared value should be interpreted as a JavaScript-like statement (with some
Angular enhancements) instead of a plain string.

@Component({
selector: 'sign-up-form',
template: `
<button type="submit" [disabled]="formIsInvalid">Submit</button>
`,
})
export class SignUpForm {
formIsInvalid = true;
}

18
Dynamic Attributes
In the event you want to dynamically bind custom HTML attributes (e.g., aria-, data-, etc.), you might be inclined to wrap the
custom attributes with the same square brackets.

@Component({
standalone: true,
template: `
<button [attr.data-test-id]="testId">Primary CTA</button>
`,
})
export class AppBanner {
testId = 'main-cta';
}

19
Conditionals and Loops
We can create a feature module called orders

One of the advantages of using a framework like Angular is that it provides built-in solutions for common problems that
developers encounter. Examples of this include: displaying content based on a certain condition, rendering a list of items based
on application data, etc.

To solve this problem, Angular uses built-in control flow blocks, which tell the framework when and how your templates should
be rendered.

20
Conditional rendering

@if block
Similar to JavaScript's if statement, Angular uses @if control flow blocks to conditionally hide and show part of a template
and its contents.

@else block
While the @if block can be helpful in many situations, it's common to also show fallback UI when the condition is not met.

// user-controls.component.ts
@Component({
standalone: true,
selector: 'user-controls',
template: `@if (isAdmin) {
<button>Erase database</button>
} @else {
<p>You are not authorized.</p>
}`,
})
export class UserControls { isAdmin = true; } 21
Rendering a list

@for block
<!-- ingredient-list.component.html -->
<ul>
@for (ingredient of ingredientList; track ingredient.name) {
<li>{{ ingredient.quantity }} - {{ ingredient.name }}</li>
}
</ul>

track property
When Angular renders a list of elements with @for , those items can later change or move. Angular needs to track each
element through any reordering, usually by treating a property of the item as a unique identifier or key.

This ensures any updates to the list are reflected correctly in the UI and tracked properly within Angular, especially in the case
of stateful elements or animations.

To accomplish this, we can provide a unique key to Angular with the track keyword.
22
Event Handling
You can add an event handler to an element by:

1. Adding an attribute with the events name inside of parentheses


2. Specify what JavaScript statement you want to run when it fires

// text-transformer.component.ts
@Component({
standalone: true,
selector: 'text-transformer',
template: `
<p>{{ announcement }}</p>
<button (click)="transformText()">Abracadabra!</button>
`,
})
export class TextTransformer {
announcement = 'Hello again Angular!';
transformText() {
this.announcement = this.announcement.toUpperCase();
}
}
23
Event Handling
Other common examples of event listeners include:

<input (keyup)="validateInput()" />


<input (keydown)="updateInput()" />

If you need to access the event object, Angular provides an implicit $event variable that you can pass to a function:

<button (click)="createUser($event)">Submit</button>

24
Sharing Code
When you need to share logic between components, Angular leverages the design pattern of dependency injection that allows
you to create a “service” which allows you to inject code into components while managing it from a single source of truth.

What are services?


Services are reusable pieces of code that can be injected

Similar to defining a component, services are comprised of the following:

A TypeScript decorator that declares the class as an Angular service via @Injectable and allows you to define what part of
the application can access the service via the providedIn property (which is typically 'root' ) to allow a service to be
accessed anywhere within the application.
A TypeScript class that defines the desired code that will be accessible when the service is injected

25
import {Injectable} from '@angular/core';
@Injectable({
providedIn: 'root',
})
export class CalculatorService {
add(x: number, y: number) {
return x + y;
}
}

26
Services
When you want to use a service in a component, you need to:

1. Import the service


2. Declare a class field where the service is injected. Assign the class field to the result of the call of the built-in function inject
which creates the service

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


import { CalculatorService } from './calculator.service';
@Component({
selector: 'app-receipt',
template: `<h1>The total is {{ totalCost }}</h1>`,
})
export class Receipt {
private calculatorService = inject(CalculatorService);
totalCost = this.calculatorService.add(50, 25);
}

27
Two way binding
Angular, two-way data binding is typically used with form controls, allowing you to bind the value of an input field to a
property in your component.

Here's a breakdown of how two-way data binding works:

Property Binding [property] : Binds a property of a DOM element to a property in your component.

Event Binding (event) : Listens for events emitted by a DOM element and triggers a method in your component.

By combining these two bindings with [(ngModel)] , you create a two-way binding, where changes in the input field
immediately update the component property, and changes to the component property immediately update the input field.

28
Two way binding
Developers commonly use two-way binding to keep component data in sync with a form control as a user interacts with the
control.

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


import { FormsModule } from '@angular/forms';
@Component({
standalone: true,
imports: [FormsModule],
template: `
<main>
<h2>Hello {{ firstName }}!</h2>
<input type="text" [(ngModel)]="firstName" />
</main>
`
})
export class AppComponent {
firstName = 'Ada';
}

29
@Input & Custom property binding
In Angular, @Input() is a decorator that allows you to pass data from a parent component to a child component. It is
commonly used to create a communication channel between components, enabling the parent component to pass data down
to its child components.

import { Component, Input } from '@angular/core'; // child.component.ts


@Component({
selector: 'app-child',
template: '<p>{{ childMessage }}</p>', })
export class ChildComponent {
@Input() childMessage: string;
}

import { Component } from '@angular/core'; // parent.component.ts


@Component({
selector: 'app-parent',
template: ` <app-child [childMessage]="parentMessage"></app-child>
<input [(ngModel)]="parentMessage" placeholder="Enter message in parent">`, })
export class ParentComponent {
parentMessage: string = 'Hello from parent!';
}
30
@Input & Custom property binding
In the ChildComponent, the @Input() decorator is used to create a property (childMessage) that can receive data from the
parent component.

In the ParentComponent, the child component ( <app-child> ) is used, and the [childMessage] binding is used to pass the
value of parentMessage to the childMessage property in the child component.

Changes to parentMessage in the parent component will automatically update the childMessage in the child component due
to the data binding.

31
@Output & Custom event binding
In Angular, the @Output() decorator is used to create an output property in a component. Output properties enable a child
component to emit events that a parent component can listen to. This mechanism allows child components to communicate
with their parent components.

import { Component, EventEmitter, Output } from '@angular/core'; // child.component.ts


@Component({
selector: 'app-child',
template: '<button (click)="sendMessage()">Send Message</button>',
})
export class ChildComponent {
@Output() messageEvent = new EventEmitter<string>();
sendMessage() { this.messageEvent.emit('Hello from child!'); } }

import { Component } from '@angular/core'; // parent.component.ts


@Component({
selector: 'app-parent',
template: ` <app-child (messageEvent)="receiveMessage($event)"></app-child>
<p>{{ receivedMessage }}</p>`,
})
export class ParentComponent {
receivedMessage: string;
receiveMessage(message: string) { this.receivedMessage = message; } }
32
@Output & Custom event binding
In the ChildComponent, the @Output() decorator is used to create an output property named messageEvent. It is an instance
of the EventEmitter class, which will emit events containing a string message.

The sendMessage() method in the ChildComponent is called when the button is clicked, and it emits the message through the
messageEvent output property.

In the ParentComponent, the child component ( <app-child> ) is used, and the (messageEvent) event binding is used to listen
for events emitted by the child component. The receiveMessage($event) method is called when the event occurs, and it
updates the receivedMessage property in the parent component.

The parent component template displays the received message.

33
Two way communication
Using @Input and @Output for the same variable allows you to establish a two-way communication between a parent
component and a child component in Angular. This is often referred to as two-way binding, and it can be achieved by
combining the use of @Input and @Output on the same property.

// child.component.ts
import { Component, EventEmitter, Input, Output } from '@angular/core';

@Component({
selector: 'app-child',
template: `
<input [(ngModel)]="childMessage" placeholder="Enter message in child">
<button (click)="sendMessage()">Send Message to Parent</button>`,
})
export class ChildComponent {
@Input() childMessage: string; // Input property
@Output() childMessageChange = new EventEmitter<string>(); // Output property

sendMessage() {
this.childMessageChange.emit(this.childMessage);
}
} 34
// parent.component.ts

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

@Component({
selector: 'app-parent',
template: `
<app-child [(childMessage)]="parentMessage"></app-child>
<p>Parent Message: {{ parentMessage }}</p>
`,
})
export class ParentComponent {
parentMessage: string = 'Hello from parent!';
}

35
Content projection with ng-content
You often need to create components that act as containers for different types of content. For example, you may want to create
a custom card component:
You can use the <ng-content> element as a placeholder to mark where content should go:

// Component source
@Component({
selector: 'custom-card',
template: '<div class="card-shadow"> <ng-content /> </div>',
})
export class CustomCard {/* ... */}

<!-- Using the component -->


<custom-card>
<p>This is the projected content</p>
</custom-card>

<!-- The rendered DOM -->


<custom-card>
<div class="card-shadow">
<p>This is the projected content</p>
</div>
</custom-card> 36
Content projection with ng-content
Angular supports projecting multiple different elements into different <ng-content> placeholders based on CSS selector.

<!-- Component template -->


<div class="card-shadow">
<ng-content select="card-title"></ng-content>
<div class="card-divider"></div>
<ng-content select="card-body"></ng-content>
</div>

<!-- Using the component -->


<custom-card>
<card-title>Hello</card-title>
<card-body>Welcome to the example</card-body>
</custom-card>

<!-- Rendered DOM -->


<custom-card>
<div class="card-shadow">
<card-title>Hello</card-title>
<div class="card-divider"></div>
<card-body>Welcome to the example</card-body>
</div>
37
</custom-card>
Local template variables with @let
@let name = user.name;
@let greeting = 'Hello, ' + name;
@let data = data$ | async;
@let pi = 3.1459;
@let coordinates = {x: 50, y: 100};
@let longExpression = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit ' +
'sed do eiusmod tempor incididunt ut labore et dolore magna ' +
'Ut enim ad minim veniam...';

Each @let block can declare exactly one variable. You cannot declare multiple variables in the same block with a comma.

38
Attribute directives
Change the appearance or behavior of DOM elements and Angular components with attribute directives.
ng generate directive highlight

import {Directive, ElementRef, HostListener} from '@angular/core';


import {Input} from '@angular/core';
@Directive({
standalone: true,
selector: '[appHighlight]',
})
export class HighlightDirective {
constructor(private el: ElementRef) {
//this.el.nativeElement.style.backgroundColor = 'yellow';
}
@HostListener('mouseenter') onMouseEnter() { this.highlight('yellow'); }
@HostListener('mouseleave') onMouseLeave() { this.highlight(''); }
private highlight(color: string) { this.el.nativeElement.style.backgroundColor = color; }
}

<!--src/app/app.component.html-->
<p appHighlight>Highlight me!</p>
39
Routing
In a single-page app, you change what the user sees by showing or hiding portions of the display that correspond to particular
components, rather than going out to the server to get a new page.

Import the routes into app.config.ts and add it to the provideRouter function. The following is the default
ApplicationConfig using the CLI.

export const appConfig: ApplicationConfig = {


providers: [provideRouter(routes)]
};

1. Set up a Routes array for your routes

import { Routes } from '@angular/router';


export const routes: Routes = [];

2. Define your routes in your Routes array

const routes: Routes = [


{ path: 'first-component', component: FirstComponent },
{ path: 'second-component', component: SecondComponent },
];
40
Routing
3. Add your routes to your application

<h1>Angular Router App</h1>


<nav>
<ul>
<li><a routerLink="/first-component" routerLinkActive="active" ariaCurrentWhenActive="page">First Component</a></li>
<li><a routerLink="/second-component" routerLinkActive="active" ariaCurrentWhenActive="page">Second Component</a></li>
</ul>
</nav>
<!-- The routed views render in the <router-outlet>-->
<router-outlet></router-outlet>

41
Routing
You also need to add the RouterLink, RouterLinkActive, and RouterOutlet to the imports array of AppComponent.

@Component({
selector: 'app-root',
standalone: true,
imports: [CommonModule, RouterOutlet, RouterLink, RouterLinkActive],
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
title = 'routing-app';
}

42
Routing
Displaying a 404 page:

To display a 404 page, set up a wildcard route with the component property set to the component you'd like to use for your
404 page as follows:

const routes: Routes = [


{ path: 'first-component', component: FirstComponent },
{ path: 'second-component', component: SecondComponent },
{ path: '**', component: PageNotFoundComponent }, // Wildcard route for a 404 page
];

The last route with the path of ** is a wildcard route. The router selects this route if the requested URL doesn't match any of
the paths earlier in the list and sends the user to the PageNotFoundComponent .

43
Forms
Angular provides two different approaches to handling user input through forms: reactive and template-driven. Both capture
user input events from the view, validate the user input, create a form model and data model to update, and provide a way to
track changes.

Template-Driven Forms:

Simpler to use.
Driven by directives in the template.
Two-way data binding with ngModel.

Reactive Forms:

More explicit and flexible.


Driven by form controls and groups created programmatically.
Allows dynamic control over form structure and validation.

44
Template-Driven Forms:
Template-driven forms are a simpler way to work with forms in Angular. They are driven by directives in the template and
require less explicit code.

1. Import the FormsModule in your Angular module.


2. Create a Form in the Template: Use the ngModel directive for two-way data binding to bind form controls to properties in
your component.

<!-- app.component.html -->

<form #myForm="ngForm" (ngSubmit)="submitForm()">


<label for="name">Name:</label>
<input type="text" id="name" name="name" [(ngModel)]="formData.name" required>

<label for="email">Email:</label>
<input type="email" id="email" name="email" [(ngModel)]="formData.email" required>

<button type="submit">Submit</button>
</form>

45
// app.component.ts

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

@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
formData: any = {}; // Object to store form data

submitForm(): void {
console.log('Form submitted:', this.formData);
// Add logic to process the form data
}
}

46
Reactive Forms
Reactive forms offer a more explicit and flexible way to work with forms in Angular. They are driven by form control instances
that you create programmatically in the component. Here are the basic steps for using reactive forms:

1. First, go to the src/app/app.component.ts file and import ReactiveFormsModule : import { FormsModule, NgForm,
ReactiveFormsModule } from '@angular/forms';

2. Next, add them to the imports array of the component:


3. Create Form Controls and Form Group in the Component:

47
// app.component.ts

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


import { NgForm, ReactiveFormsModule, FormBuilder, FormGroup, Validators } from '@angular/forms';

@Component({
selector: 'app-root',
standalone: true,
imports: [RouterOutlet, FormsModule, ReactiveFormsModule],
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent implements OnInit {
myForm: FormGroup;

constructor(private fb: FormBuilder) {}

ngOnInit(): void {
this.myForm = this.fb.group({
name: ['', Validators.required],
email: ['', [Validators.required, Validators.email]],
});
}

submitForm(): void {
console.log('Form submitted:', this.myForm.value);
// Add logic to process the form data
}
}

48
3. Bind Form Controls to Template:

<!-- app.component.html -->

<form [formGroup]="myForm" (ngSubmit)="submitForm()">


<label for="name">Name:</label>
<input type="text" id="name" formControlName="name">

<label for="email">Email:</label>
<input type="email" id="email" formControlName="email">

<button type="submit">Submit</button>
</form>

Both template-driven and reactive forms have their use cases, and the choice between them depends on the requirements of
your application. Reactive forms are often preferred for larger and more complex forms due to their explicit nature and ease of
unit testing.

49
HttpClient
In Angular, the HttpClient module is used to make HTTP requests to a server and handle the responses. It provides a higher-
level API for sending and receiving data over HTTP/HTTPS and is part of the @angular/common/http module.

HttpClient is provided using the provideHttpClient helper function, which most apps include in the application providers
in app.config.ts .

You can then inject the HttpClient service as a dependency of an application class in a service:

50
HTTPClient
import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { catchError, retry } from 'rxjs/operators';

@Injectable({
providedIn: 'root',
})
export class RestApiService {
constructor(private http: HttpClient) { }
// Define API
private apiUrl = 'https://jsonplaceholder.typicode.com';
// Http Options
httpOptions = {
headers: new HttpHeaders({
'Content-Type': 'application/json',
}),
};

getData(): Observable<any> {
return this.http.get(`${this.apiUrl}/posts/1`);
}

postData(data: any): Observable<any> {


return this.http.post(`${this.apiUrl}/posts`, data);
}
}

51
Observables are a fundamental part of RxJS and are used to represent asynchronous data streams. They can be used for
handling events, promises, HTTP responses, and more.

Here's a basic example of using observables in an Angular component:

// my-component.component.ts

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


import { MyApiService } from './my-api.service';

@Component({
selector: 'app-my-component',
template: '<div>{{ responseData | json }}</div>',
})
export class MyComponent implements OnInit {
responseData: any;

constructor(private myApiService: MyApiService) {}

ngOnInit() {
this.getData();
}

getData(): void {
this.myApiService.getData().subscribe((data) => {
this.responseData = data;
});
}
}
52
Observable streams can emit errors, and RxJS provides operators like catchError for handling errors.

import { catchError } from 'rxjs/operators';

// ...

getData(): void {
this.myApiService.getData().pipe(
catchError((error) => {
console.error('Error:', error);
throw error; // Rethrow the error or return a fallback value
})
).subscribe((data) => {
this.responseData = data;
});
}

53
TP
Create a CRUD application for Shows
A show have a title, a discription and the number of episodes.
Use Json server to get a full fake REST API

54

You might also like