- Angular Tutorial
- Angular - Home
- Angular - Overview
- Angular - Features
- Angular - Advantages & Disadvantages
- Angular Basics
- Angular - Environment setup
- Angular - First Application
- Angular - MVC Architecture
- Angular Components
- Angular - Components
- Angular - Component Lifecycle
- Angular - View Encapsulation
- Angular - Emulated Encapsulation
- Angular - ShadowDom Encapsulation
- Angular - Component Interaction
- Angular - Using @Input Decorator
- Angular - Using @Output Decorator
- Angular - Using Local Variable
- Angular - Using @ViewChild Decorator
- Angular - Using Services
- Angular - Component Styles
- Angular - Nested Components
- Angular - Content projection
- Angular - Single-slot Content Projection
- Angular - Multi-slot Content Projection
- Angular - Conditional Content Projection
- Angular - Dynamic components
- Angular - Using NgComponentOutlet
- Angular - Using ViewContainerRef
- Angular - Elements
- Angular Templates
- Angular - Templates
- Angular - Template statements
- Angular - Template Variables
- Angular - SVG as Templates
- Angular Binding
- Angular - Data Binding
- Angular - Interpolation
- Angular - Event Binding
- Angular - Property Binding
- Angular - Attribute Binding
- Angular - Class Binding
- Angular - Style Binding
- Angular - Two-way Binding
- Angular Directives
- Angular - Directives
- Angular - Attribute Directives
- Angular - Structural Directives
- Angular - Custom Directives
- Angular Pipes
- Angular - Pipes
- Angular - Built-in Pipes
- Angular - Custom Pipes
- Angular Forms
- Angular - Forms
- Angular - Template Driven Forms
- Angular - Reactive Forms
- Angular - Form Validation
- Angular - Dynamic Forms
- Angular Dependency Injection
- Angular - Dependency Injection
- Angular - Injectable Service
- Angular Routing
- Angular - Routing
- Angular - Dynamic Routes
- Angular - Wildcard Routes
- Angular - Nested Routes
- Angular - Navigation
- Angular - Routing in SPA
- Angular - Custom Route Matches
- Angular - Router Reference
- Angular HTTP Client programming
- Angular - Services
- Angular - HTTP Client
- Angular - Express based REST API
- Angular - Request
- Angular - Request Response Workflow
- Angular - Response
- Angular - Express based Upload API
- Angular - GET
- Angular - POST
- Angular - PUT
- Angular - DELETE
- Angular - JSONP
- Angular - CRUD Operations Using HTTP
- Angular Modules
- Angular - Introduction to Modules
- Angular - Root Module
- Angular - Feature Module
- Angular - Sharing Module
- Angular - Routing Module
- Angular - NgModules
- Angular Animation
- Angular - Animations
- Angular Service Workers & PWA
- Angular - Service Workers & PWA
- Angular Testing
- Angular - Testing Overview
- Angular Design Patterns
- Angular - Design Patterns
- Angular - Lazy Loading
- Angular - Singleton Pattern
- Angular - Observer Pattern
- Angular Libraries
- Angular - Libraries
- Angular - Angular Material
- Angular - PrimeNG
- Angular - RxJS
- Angular Advanced
- Angular - Signals
- Angular - Authentication & Authorization
- Angular - Internationalization
- Angular - Standalone Component
- Angular - Accessibility
- Angular - Web Workers
- Angular - Server Side Rendering
- Angular - Ivy Compiler
- Angular - Building with Bazel
- Angular - Backward Compatibility
- Angular - Reactive Programming
- Angular Tools
- Angular - CLI
- Angular Material UI Elements
- Angular - Paginator
- Angular - Datepicker
- Angular - Select Drop-down
- Angular Miscellaneous
- Angular - Third Party Controls
- Angular - Configuration
- Angular - Displaying Data
- Angular - Decorators & Metadata
- Angular - Basic Example
- Angular - Error Handling
- Angular - Testing & Building a Project
- Angular - Lifecycle Hooks
- Angular - User Input
- Angular - What's New?
- Angular Useful Resources
- Angular - Quick Guide
- Angular - Useful Resources
- Angular - Discussion
Angular - Request Response Workflow
The HttpClient provides several methods to start an HTTP request. All methods return an observable with an optional type variable (Observable<T>).
The observable need to be subscribed to to start the request. Once the observable is subscribed, it starts the request, passes it through a series of registered interceptors, and finally reaches the server. The response is then received from the server and published to the subscribed function.
The workflow of the request is as follows −
- The user creates a new HttpClient instance, say HTTP through the component constructor:
constructor(private http: HttpClient) { }
- The user calls any one of the HttpClient methods, say request() by passing the resource information:
let req = this.http.request(<action>, <url>, <body>, <option>)
- The request() method will create an observable, say request (req) using the given resource information:
let req = this.http.request(<action>, <url>, <body>, <option>)
- The user will subscribe a callback function to the observable using the subscribe() method:
req.subscribe((data) => console.log(data));
Once a user subscribes to the Observable, it passes the request to the registered interceptors in the order in which the interceptors are registered.
Once the request passes all registered interceptors, Observable will send the request to the server.
Observable waits for the server response, and once receives the response from the server, it returns the response to the subscribed function.
The subscribed function will do the necessary business logic and set the output to the components variable.
The component will render its template using the output of the HttpClient.
A sample request is as follows −
let req = this.http.request('GET', 'http://localhost:8000/api/expense/1')
req.subscribe(data => this.myexpense = data);
Here,
The this.http is the HttpClient instance
The request()is the method use to create observable, when subscribed, starts the request.
The subscribe() is the method use to subscribe to the returned observable and to subsequently start the request and fetch the response.
Finally, the argument to the subscribe method is the callback function used to get the actual responses body content.
HttpClient Arguments
Arguments supported by HttpClients methods are as follows −
- Resource URI − It is the URL / endpoint representing the resource.
- Request body − It is the data to be sent to the server along with the request. The data can be either in query string format or JSON format.
- Request options − It is all other data sent along with the request. It contains query strings, headers, cookies, etc.
Resource URI
All method accept url / endpoint as one of the argument. It represents the resource to be fetched from the server. In our sample application, the url starts with http://localhost:8000/ and one of the possible option is http://localhost:8000/api/expenses. This endpoint will fetch all expenses from the server and send it back to the client in json format.
Request body
All methods accept URL / endpoint as one of the arguments. It represents the resource to be fetched from the server. In our sample application, the URL starts with http://localhost:8000/, and one of the possible options is http://localhost:8000/api/expenses. This endpoint will fetch all expenses from the server and send it back to the client in JSON format −
Form data. MIME-type is application/x-www-form-URL-encoded
Form data with uploads. MIME type is multipart/form-data
Plain text. MIME-type is text/plain
JSON. MIME-type is application/json
HttpParams class
Form data can be created using the HttpParams class provided by Angular. HttpParams accepts data in query string format (key/value as key=value and each key/value separated by &). It has methods to add one or more parameters as a sequence by chaining methods together. All methods create a copy of the instance add/remove the parameter (key/value pair) in the copied instance, and return it.
The signature of the HttpParams constructor is as follows −
constructor(options: HttpParamsOptions = {} as HttpParamsOptions)
Where,
The HttpParamsOptionsobject can be created using the below properties:
- fromString?: string
- fromObject?: {}
The sample code to create a HttpParams object using a constructor is as follows −
/* using fromString option */
let httpParams = new HttpParams( { fromString: 'a=b*b=c' } )
/* using fromObject option */
let httpParams = new HttpParams( { fromObject: { a: "b", c: "d" } )
The methods supported by HttpParams are as follows −
set(): Accepts a parameter and value. Add a new parameter with the given value.
delete(): Accepts a parameter. Delete the given parameter.
has(): Accepts a parameter. Returns true/false based on the availability of the given parameter.
keys(): Accepts nothing. Returns all parameters.
get(): Accepts a parameter. Returns the first value of the given parameter.
getAll(): Accepts a parameter. Returns all values of the given parameter.
append(): Accepts a parameter. Append the value to the given parameter.
appendAll(): Accepts an object with multiple parameters. Append the value to all parameters.
toString(): Accepts nothing. Returns the object in query string format.
The sample code to create a HttpParams object is as follows −
let formData = new HttpParams();
formData = formData
.set('item', 'Modified')
.set('amount', 25);
console.log(formData.toString()) // item=Modified&amount=25
Request options
Irrespective of the method, options are one common argument accepted by all methods and used to represent the request options. Option is a JavaScript object (or hash) with a standard set of request data. Options can have the below entries and represent different aspects of the request and response:
- observe
- responseType
- headers
- params
- context
- reportProgress
- withCredentials
- transferCache
Let us learn one by one in the upcoming chapters:
observe
Theobserveoption is used to specify which part of the response has to be observed during the server communication and send back the data to the subscribed function.
Based on the observe option, either the full or part of the response will be returned. The possible values are events, body, and response.
events
Theeventsare used to return the events fired in the response stream from the server. It will return the response as Observable<HttpEvent<R>> type. Here, R is the type of the actual data (response body) to be returned.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'events',
responseType : 'json'
});
Here,
- JSONis the format used to interpret the response body.
- Expenseis the type used to convert and return the responses body. Otherwise, it will return the responses body as a generic JavaScript object.
response
The response option is used to return the complete response from the server. It will return the response as Observable<HttpResponse<R>> type. Here, R is the type of the actual data (responses body) to be returned.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'response',
responseType : 'json'
});
Here,
- JSONis the format used to interpret the responses body.
- Expenseis the type used to convert and return the responses body. Otherwise, it will return the responses body as a generic JavaScript object.
body
The body is used to return only the body content of the response from the server. It will return the response asObservable<HttpResponse<R>>type, Here, R is a type of the actual data (responses body) to be returned.
let req = this.http.request<Expense>( 'GET','http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json'
});
Here,
- JSONis the format used to interpret the response's body
- Expenseis the type used to convert and return the responses body. Otherwise, it will return the response's body as a generic JavaScript object.
responseType
The responseType is used to interpret the response's body. It can have four possible values as shown below −
- arraybuffer
- blob
- text
- json
Let us understand the values and their usage one by one:
arraybuffer
The arraybuffer interprets the response's body as a generic raw binary data buffer and returns Observable. It can be used to stream audio/video content.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'arraybuffer'
});
blob
The blob interprets the response's body as the binary format and returns Observable. It can be used to download large files.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'blob'
});
text
The text interprets the response's body as plain text format and returns Observable. It can be used to represent text-based data.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'text'
});
json
The JSON interprets the response's body in JSON format and returns Observable, where R is the requested type (Expense) of data. It can be used to represent the result in JSON format. It can be further encoded into any type by specifying the type variable (R) in the method as shown below −
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json'
});
Based on the observe and responseType, Httpclient will return Observable with a different type variable. Let us check a few combinations of observe and responseType to better understand the concept.
-
observe => body and responseType => JSON
Returns the Observable R represents the type variable.
-
observe => response and responseType => JSON
Returns the Observable<HttpResponse>. R represents the type variable and encodes the response body.
-
observe => events and responseType => JSON
Returns the Observable<HttpEvent>. R represents the type variable and encodes the response body.
-
observe => events and responseType => arraybuffer
Returns the Observable<HttpEvent>. The Response body is encoded as ArrayBuffer.
-
observe => response and responseType => blob
Returns the Observable<HttpEvent>. The Response body is encoded as ArrayBuffer.
-
observe => response and responseType => text
Returns the Observable<HttpResponse>. The Response body is encoded as ArrayBuffer.
We can combineobserveandresponseTypeto create many more combinations as we need.
headers
The headers specify the HTTP headers. It can include a standard HTTP header as a key/value pair or can encode the data using the HttpHeaders class. A sample header as a key/value pair is as follows:
{ 'Content-type': 'application/json' }
It specifies that the request content type is JSON.
Angular provides a special class,HttpHeadersto compose header details. It accepts header information as an anonymous object and initializes it.
It has methods (set(), append(), and delete()) to add/remove one or more headers in a sequence by chaining methods together.
All methods create a copy of the instance add/remove the header information in the copied instance, and return it.
let httpHeaders = new HttpHeaders( { 'Content-Type': 'application/json' })
httpHeaders = httpHeaders
.set('Accept-Language', 'en-US,en;q=0.5')
.set('Accept-Encoding', 'gzip, deflate, br');
let options = { 'headers': httpHeaders }
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', options );
req.subscribe( (data: Expense) => this.myexpense = data );
Here,
- httpHeaders is an object used to enclose the HTTP header information to be send to the server. It was created using HttpHeaders class.
- options is an object enhanced with header information.
The methods supported by HttpHeaders are as follows −
- set(): Accepts a header and value. Add a new header with the given value.
- delete(): Accepts a header. Delete the given parameter.
- has(): Accepts a parameter. Returns true / false based on the availability of the given header.
- keys(): Accepts nothing. Returns all parameters.
- get(): Accepts a parameter. Returns first value of the given parameter.
- getAll(): Accepts a header. Returns all values of the given parameter.
- append(): Accepts a parameter. Append the value to the given header.
- appendAll(): Accepts an object with multiple parameter. Append the value to all header.
- toString(): Accepts nothing. Returns the object in query-string format.
params
Theparamsallow the query string to be set using the HttpParams class. Please check the Request body section for more aboutthe "HttpParams"class.
The sample code to create a HttpParams object and set it in the request is as follows −
let formData = new HttpParams();
formData = formData
.set('item', 'Modified')
.set('amount', 25);
console.log(formData.toString()) // item=Modified&amount=25
let req = this.http.request<Expense>('GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json',
params: formData
});
context
The Context is used to send arbitrary values as key/value pairs with type safety and without key conflict. It is used as a source of information for interceptors acting as middleware between client and server. Angular provides a special class, HttpContext to encode the context information. A sample context is as follows −
// create a key using HttpContextToken
export const IS_AUTH_ENABLED = new HttpContextToken<boolean>(() => false);
// set data for the context
let authContext = new HttpContext().set(IS_AUTH_ENABLED, true)
let req = this.http.request<Expense>('GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json',
context: authContext
});
Here,
- HttpContextToken class is used to create the key of the context. It has the option to specify the value type as well.
- IS_AUTH_ENABLED is the key, and its type is boolean.
- IS_AUTH_ENABLED is set to true.
We can get the context value using the get() method by passing the token as shown below −
let contextValue = req.context.get<boolean>(IS_AUTH_ENABLED) // true
reportProgress
The reportProgress specifies whether to get the progress of the request (communication) from the server. It can be used to show the progress of large file uploads through web API.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'events',
responseType : 'json',
reportProgress: true
});
withCredentials
The withCredential specifies whether the request should be sent with outgoing credentials (cookies). It accepts a boolean value.
this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json'
withCredentials: true
});
transferCache
The transferCache specifies whether the request should be cached. It accepts the boolean value orHttpTransferCacheOptionsvalue. HttpTransferCacheOptions is used to encode dynamic logic to filter requests to be cached based on a custom filter function and override default cache behavior.
let req = this.http.request<Expense>( 'GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json',
transferCache: true
});
HttpClient methods
Methods provided by the HttpClient class for client-server communication are as follows −
- request()
- head()
- get()
- post()
- put()
- patch()
- delete()
- jsonp()
- options()
Let us learn generic request() method in this chapter and other method in subsequent chapters.
The request() method
The request()is the generic method that sends a request to the server with every possible HTTP verb like get, post, patch, etc. It has many overloads. Let us check two main overload functions, one using the Generic option and another one using the HttpRequest object.
- Generic option − Accepts url, http verb, body content and options object.
- HttpRequest option − Accepts HttpRequest object
HttpRequest option
Angular provides a class, HttpRequest to represent the complete HTTP request. It has the built-in option to include URL, HTTP method/verb, response type, headers, params, etc.
var httpRequest = new HttpRequest<Expense>('GET', 'https://localhost:8000/api/expense/1', {
responseType : 'json'
});
Here,
- The this.http is HttpClient instance.
- GET method is used as HTTP verbs.
- The endpoint (http://localhost/api/expense/1) will return the expense with an id equal to 1 from the server.
- The responseType is set as JSON. This will return the body of the response as JSON.
The above sample request object can be used as below to send the request to the server:
var req = this.http.request<Expense>(httpRequest);
req.subscribe(data : HttpEvent<Expense> => {
this.myexpense = (data as HttpResponse<Expense>).body as Expense;
}
Here,
- The request returns the HttpEvent, which is the union of multiple type as shown below −
type HttpEvent<T> = HttpSentEvent | HttpHeaderResponse | HttpResponse<T> | HttpProgressEvent | HttpUserEvent<T>;
- As we have provided responseType as JSON and set Expense as an object to return, the observable will return HttpResponse<Expense> in the body. So, we converted the returned data object into a HttpResponse<Expense> object and then got the expense from the body property.
Generic option
It accepts four arguments as shown below in the given order:
- HTTP method / verb
- url
- body (optional)
- options
A sample request is as follows −
let req = this.http.request<Expense>('GET', 'http://localhost:8000/api/expense/1', {
observe: 'body',
responseType : 'json',
});
req.subscribe(data => { this.myexpense = data });