AWDnotes
AWDnotes
Nodejs :
1.1 Introduction to Node.js
What is Node.js?
Advantages of Node.js
Advance Web-development 1
2. Run the installer and follow the prompts.
node -v
npm -v
Working in REPL
$ node
>1+2
3
> console.log("Hello, World!")
Hello, World!
Node.js Console
function add(a, b) {
return a + b;
}
console.log(add(2, 3)); // 5
Advance Web-development 2
Buffer
Core Modules
const fs = require('fs');
fs.readFile('file.txt', 'utf8', (err, data) => {
if (err) throw err;
console.log(data);
});
Local Modules
// myModule.js
exports.add = function(a, b) {
return a + b;
};
// app.js
const myModule = require('./myModule');
console.log(myModule.add(2, 3)); // 5
Module Types
Core Modules
Local Modules
Third-party Modules
Module Exports
Advance Web-development 3
module.exports is used to export functions, objects, or values from a module.
// myModule.js
module.exports = {
add: function(a, b) {
return a + b;
}
};
// app.js
const myModule = require('./myModule');
console.log(myModule.add(2, 3)); // 5
Advance Web-development 4
1.5 Creating Web Server
Creating Web Server
Sending Requests
Advance Web-development 5
Use the http module to send HTTP requests.
const fs = require('fs');
fs.readFile('file.txt', 'utf8', (err, data) => {
if (err) throw err;
console.log(data);
});
Writing a File
const fs = require('fs');
fs.writeFile('file.txt', 'Hello, World!', (err) => {
if (err) throw err;
Advance Web-development 6
console.log('File written successfully');
});
Opening a File
const fs = require('fs');
fs.open('file.txt', 'r', (err, fd) => {
if (err) throw err;
fs.read(fd, Buffer.alloc(1024), 0, 1024, 0, (err, bytesRead, buffer) => {
if (err) throw err;
console.log(buffer.toString('utf8', 0, bytesRead));
});
});
Deleting a File
Delete a file.
const fs = require('fs');
fs.unlink('file.txt', (err) => {
if (err) throw err;
console.log('File deleted successfully');
});
Rename a file.
const fs = require('fs');
fs.rename('oldFile.txt', 'newFile.txt', (err) => {
if (err) throw err;
console.log('File renamed successfully');
});
Advance Web-development 7
Write to a file asynchronously.
const fs = require('fs');
fs.writeFile('file.txt', 'Hello, World!', (err) => {
if (err) throw err;
console.log('File written successfully');
});
1.7 Events
Event Emitter Class
Inheriting Events
Advance Web-development 8
const EventEmitter = require('events');
class MyEmitter extends EventEmitter {}
const myEmitter = new MyEmitter();
myEmitter.on('event', () => {
console.log('An event occurred!');
});
myEmitter.emit('event');
1.8 Express.js
Web Development with Express.js
Example:
Advance Web-development 9
Answer: You can create a simple web server using the http module:
Answer: File operations can be handled using the fs module. For example, to
read a file:
const fs = require('fs');
fs.readFile('file.txt', 'utf8', (err, data) => {
if (err) throw err;
console.log(data);
});
Answer: The EventEmitter class is used to handle events in Node.js. It allows you
to create, fire, and listen for your own events.
Advance Web-development 10
console.log('Server running at <http://localhost:3000/>');
});
Advance Web-development 11
In summary, Node.js revolutionizes server-side development by leveraging
JavaScript, an event-driven architecture, and a non-blocking I/O model. These
features make it an ideal choice for building scalable, high-performance
applications, particularly in scenarios requiring real-time data processing or
handling a large number of concurrent connections.
Q2: Explain the Node.js event loop and how it enables non-
blocking I/O operations.
Answer:
The event loop is the core mechanism that enables Node.js to perform non-
blocking I/O operations, despite being single-threaded. It is responsible for
handling asynchronous callbacks and ensuring that the application remains
responsive to incoming requests. The event loop works by continuously
monitoring the call stack and the callback queue, executing tasks in a specific
order.
When a Node.js application starts, it initializes the event loop and processes the
initial synchronous code. During execution, if an asynchronous operation (such as
reading a file, making an HTTP request, or querying a database) is encountered,
Node.js delegates the task to the system kernel or a worker thread. The event loop
then continues processing other tasks without waiting for the asynchronous
operation to complete. Once the operation is finished, a callback function is
placed in the callback queue.
The event loop operates in multiple phases, each designed to handle specific
types of tasks. These phases include:
2. Pending Callbacks: Processes I/O callbacks deferred from the previous cycle.
The event loop continuously cycles through these phases, executing callbacks
from the queue when the call stack is empty. This ensures that asynchronous
operations are handled efficiently without blocking the main thread.
Advance Web-development 12
For example, consider a scenario where a Node.js server receives multiple HTTP
requests. Instead of creating a new thread for each request, the event loop
processes each request asynchronously. If a request involves a time-consuming
operation (e.g., querying a database), the event loop delegates the task and
continues processing other requests. Once the database query is complete, the
corresponding callback is executed, and the response is sent to the client.
In conclusion, the event loop is the backbone of Node.js's non-blocking
architecture. It enables the runtime to handle a large number of concurrent
connections efficiently, making Node.js a powerful tool for building scalable and
high-performance applications.
Q3: What are Node.js modules, and how do they enhance code
organization and reusability?
Answer:
Node.js modules are reusable blocks of code that encapsulate specific
functionality, making it easier to organize and maintain large applications. Each
module is a self-contained unit that can include functions, objects, or variables,
which can be exported and imported into other parts of the application. This
modular approach promotes code reusability, separation of concerns, and
maintainability.
3. Third-Party Modules: These are external modules available through the Node
Package Manager (NPM). They provide a wide range of functionalities, from
web frameworks (e.g., Express.js) to utility libraries (e.g., Lodash).
To create a local module, you define the desired functionality in a separate file and
use module.exports to expose it. For example:
Advance Web-development 13
// mathModule.js
module.exports = {
add: (a, b) => a + b,
subtract: (a, b) => a - b
};
This module can then be imported into another file using the require function:
// app.js
const mathModule = require('./mathModule');
console.log(mathModule.add(2, 3)); // 5
console.log(mathModule.subtract(5, 3)); // 2
Advance Web-development 14
1. Package Installation: NPM allows developers to install packages locally or
globally. Local packages are installed in the node_modules directory of the
project and are listed as dependencies in the package.json file. Global packages
are installed system-wide and can be used across multiple projects.
{
"name": "my-app",
"version": "1.0.0",
"dependencies": {
"lodash": "^4.17.21"
}
}
commonly used for tasks such as starting the application, running tests, or
building the project.
{
"scripts": {
"start": "node app.js",
"test": "mocha"
}
}
Advance Web-development 15
4. Version Control: NPM uses semantic versioning (SemVer) to manage package
versions. This ensures compatibility and allows developers to specify version
ranges for dependencies.
Basic Types
tuple: Fixed-length arrays with specific types (e.g., let user: [string, number] =
["John", 25]; )
enum : Named constants (e.g., enum Color {Red, Green, Blue}; let c: Color = Color.Green; )
Advance Web-development 16
void : Absence of a value (e.g., function log(): void { console.log("Hello"); } )
Example:
Practice Questions:
2. Create an array of strings called fruits with values "Apple", "Banana", and
"Orange".
3. Define a tuple person with types string and number to store a name and age.
TypeScript allows you to define parameter types and return types for
functions.
Syntax:
string = "Guest") ).
Advance Web-development 17
Example:
Practice Questions:
1. Write a function multiply that takes two numbers and returns their product.
2. Create a function greetUser that takes an optional name parameter and logs a
greeting.
Example:
class Person {
name: string;
age: number;
greet(): void {
console.log(`Hello, my name is ${this.name}`);
}
Advance Web-development 18
}
Interfaces
Example:
interface User {
name: string;
age: number;
greet(): void;
}
greet(): void {
console.log(`Hello, my name is ${this.name}`);
}
}
Practice Questions:
1. Create a class Car with properties make and model and a method displayDetails .
Advance Web-development 19
2. Define an interface Animal with properties name and sound and implement it in a
class Dog .
2.4 Generics
Generics
Generics allow you to create reusable components that work with multiple
types.
Example:
Generic Classes
Example:
class Box<T> {
value: T;
constructor(value: T) {
this.value = value;
}
getValue(): T {
return this.value;
}
}
Advance Web-development 20
let box = new Box<number>(42);
console.log(box.getValue());
Practice Questions:
1. Write a generic function reverseArray that takes an array and returns its reverse.
2. Create a generic class Pair that stores two values of the same type.
2.5 Modules
Modules
Example:
// mathModule.ts
export function add(a: number, b: number): number {
return a + b;
}
// app.ts
import { add } from './mathModule';
console.log(add(2, 3)); // 5
Default Exports
Example:
// mathModule.ts
export default function subtract(a: number, b: number): number {
return a - b;
}
// app.ts
Advance Web-development 21
import subtract from './mathModule';
console.log(subtract(5, 3)); // 2
Practice Questions:
1. Create a module stringUtils with a function capitalize and import it in another file.
2. Write a module calculator with default and named exports for basic arithmetic
operations.
2.6 Ambients
Ambient Declarations
Example:
Ambient Modules
Example:
Practice Questions:
Advance Web-development 22
Summary of Practice Questions
1. Declare a variable price of type number and assign it a value.
2. Create an array of strings called fruits with values "Apple", "Banana", and
"Orange".
3. Define a tuple person with types string and number to store a name and age.
4. Write a function multiply that takes two numbers and returns their product.
5. Create a function greetUser that takes an optional name parameter and logs a
greeting.
6. Create a class Car with properties make and model and a method displayDetails .
7. Define an interface Animal with properties name and sound and implement it in a
class Dog .
8. Write a generic function reverseArray that takes an array and returns its reverse.
9. Create a generic class Pair that stores two values of the same type.
10. Create a module stringUtils with a function capitalize and import it in another file.
11. Write a module calculator with default and named exports for basic arithmetic
operations.
13. Create an ambient module for a library mathLib with a function square .
Advance Web-development 23
errors during development rather than at runtime, making the code more robust
and reliable.
One of the key differences between TypeScript and JavaScript is the type system.
In JavaScript, variables can hold values of any type, and their types can change
dynamically. For example:
In TypeScript, types are explicitly defined, and the compiler enforces type
checking:
across projects.
Early Error Detection: Static typing helps catch errors during development,
reducing the likelihood of runtime errors.
Advance Web-development 24
Enhanced Developer Productivity: Features like autocompletion and
refactoring tools improve developer efficiency.
If you attempt to assign a value of the wrong type, the TypeScript compiler will
throw an error:
Advance Web-development 25
The benefits of static typing include:
1. Early Error Detection: Static typing helps catch type-related errors during
development, reducing the likelihood of runtime errors. For example, if a
function expects a number but receives a string, the error will be flagged by
the compiler.
3. Better Tooling Support: Static typing enables advanced tooling features like
autocompletion, refactoring, and inline documentation. These features
improve developer productivity and reduce the likelihood of errors.
With static typing, the compiler ensures that only numbers are passed to the
function:
Advance Web-development 26
Q3: What are interfaces in TypeScript, and how do
they improve code organization?
Answer:
Interfaces in TypeScript are used to define the structure of an object. They act as
a contract that specifies the properties and methods an object must have.
Interfaces do not contain any implementation; they only describe the shape of the
data. This makes them a powerful tool for enforcing consistency and improving
code organization.
For example, consider an interface User that describes the structure of a user
object:
interface User {
id: number;
name: string;
email: string;
isActive: boolean;
}
Any object that implements this interface must adhere to its structure:
interface User {
id: number;
name: string;
Advance Web-development 27
email?: string; // Optional property
}
The compiler ensures that only objects adhering to the User interface are passed
to the function:
Advance Web-development 28
Answer:
Generics in TypeScript allow developers to create reusable components that work
with multiple types. They provide a way to define functions, classes, and
interfaces that can operate on a variety of data types without sacrificing type
safety. Generics are particularly useful when you want to create flexible and
reusable code.
The syntax for generics uses angle brackets ( <> ) to define a type parameter. For
example:
Here, T is a type parameter that can be replaced with any type when the function
is called:
class Box<T> {
value: T;
constructor(value: T) {
this.value = value;
}
getValue(): T {
return this.value;
}
}
Advance Web-development 29
let box1 = new Box<number>(42);
let box2 = new Box<string>("Hello");
1. Reusable Functions: Generics allow you to write functions that work with any
type, such as utility functions for arrays or objects.
Advance Web-development 30
TypeScript is a statically typed superset of JavaScript developed by Microsoft. It
builds on JavaScript by adding optional static typing, classes, interfaces, and
other features that enhance code quality, maintainability, and scalability. Unlike
JavaScript, which is dynamically typed, TypeScript allows developers to define
types for variables, function parameters, and return values. This helps catch
errors during development rather than at runtime, making the code more robust
and reliable.
One of the key differences between TypeScript and JavaScript is the type system.
In JavaScript, variables can hold values of any type, and their types can change
dynamically. For example:
In TypeScript, types are explicitly defined, and the compiler enforces type
checking:
across projects.
Advance Web-development 31
Early Error Detection: Static typing helps catch errors during development,
reducing the likelihood of runtime errors.
Static typing is a feature of TypeScript that allows developers to define the types
of variables, function parameters, and return values at compile time. Unlike
dynamic typing in JavaScript, where types are determined at runtime, static typing
ensures that types are checked during development, reducing the likelihood of
type-related errors.
In TypeScript, you can explicitly specify types using annotations:
Advance Web-development 32
If you attempt to assign a value of the wrong type, the TypeScript compiler will
throw an error:
1. Early Error Detection: Static typing helps catch type-related errors during
development, reducing the likelihood of runtime errors. For example, if a
function expects a number but receives a string, the error will be flagged by
the compiler.
3. Better Tooling Support: Static typing enables advanced tooling features like
autocompletion, refactoring, and inline documentation. These features
improve developer productivity and reduce the likelihood of errors.
With static typing, the compiler ensures that only numbers are passed to the
function:
Advance Web-development 33
In conclusion, static typing is a core feature of TypeScript that enhances code
quality, reduces errors, and improves developer productivity. By enforcing type
constraints at compile time, it ensures that the code is more predictable, reliable,
and maintainable.
interface User {
id: number;
name: string;
email: string;
isActive: boolean;
}
Any object that implements this interface must adhere to its structure:
Advance Web-development 34
interface User {
id: number;
name: string;
email?: string; // Optional property
}
The compiler ensures that only objects adhering to the User interface are passed
to the function:
Advance Web-development 35
Q4: Explain the concept of generics in TypeScript and
their use cases.
Answer:
Generics in TypeScript allow developers to create reusable components that work
with multiple types. They provide a way to define functions, classes, and
interfaces that can operate on a variety of data types without sacrificing type
safety. Generics are particularly useful when you want to create flexible and
reusable code.
The syntax for generics uses angle brackets ( <> ) to define a type parameter. For
example:
Here, T is a type parameter that can be replaced with any type when the function
is called:
class Box<T> {
value: T;
constructor(value: T) {
this.value = value;
}
getValue(): T {
return this.value;
}
Advance Web-development 36
}
1. Reusable Functions: Generics allow you to write functions that work with any
type, such as utility functions for arrays or objects.
Advance Web-development 37
Components are the building blocks of an Angular application.
Creating a Component
This creates:
my-component.component.ts
my-component.component.html
my-component.component.css
Example:
// my-component.component.ts
import { Component } from '@angular/core';
@Component({
selector: 'app-my-component',
templateUrl: './my-component.component.html',
styleUrls: ['./my-component.component.css']
})
export class MyComponent {
title = 'My Component';
}
Advance Web-development 38
<!-- my-component.component.html -->
<h1>{{ title }}</h1>
Using a Component
<app-my-component></app-my-component>
Practice Problems:
Example:
Advance Web-development 39
<!-- ngStyle -->
<div [ngStyle]="{'color': textColor}">Style Binding</div>
Practice Problems:
3.3 Modules
What are Modules?
Every Angular app has at least one module: the root module ( AppModule ).
Example:
// app.module.ts
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { AppComponent } from './app.component';
@NgModule({
declarations: [AppComponent],
imports: [BrowserModule],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule {}
Practice Problems:
Advance Web-development 40
3.4 Data Binding
Types of Data Binding
1. Interpolation: {{ expression }}
Example:
Practice Problems:
1. Bind an input field to a property and display its value using interpolation.
Example:
Advance Web-development 41
<p>{{ 5 + 5 }}</p> <!-- Output: 10 -->
String Interpolation
Example:
Practice Problems:
3.6 Pipes
What are Pipes?
Example:
Common Pipes
Chaining Pipes
Parameterizing Pipes
Advance Web-development 42
<p>{{ 3.14159 | number:'1.2-2' }}</p> <!-- Output: 3.14 -->
Async Pipe
Practice Problems:
2. Chain the uppercase and slice pipes to display the first 3 letters of a string in
uppercase.
Router Outlet
<router-outlet></router-outlet>
Navigation
<a routerLink="/about">About</a>
Advance Web-development 43
Practice Problems:
Example:
Using Bootstrap
Practice Problems:
SPAs load a single HTML page and dynamically update the content as the user
interacts with the app.
Advance Web-development 44
Example:
Practice Problems:
4. Bind an input field to a property and display its value using interpolation.
1. TypeScript Class: Contains the logic and data for the component.
Advance Web-development 45
2. HTML Template: Defines the structure of the view.
Components are reusable and modular, making it easier to manage and scale
large applications. They follow the Component-Based Architecture, where the
application is divided into smaller, self-contained units, each responsible for a
specific functionality.
Creating a Component
To create a component, you can use the Angular CLI:
Example:
// my-component.component.ts
import { Component } from '@angular/core';
@Component({
selector: 'app-my-component',
templateUrl: './my-component.component.html',
styleUrls: ['./my-component.component.css']
})
export class MyComponent {
title = 'My Component';
}
Advance Web-development 46
<h1>{{ title }}</h1>
Using a Component
To use a component, you add its selector to a template:
<app-my-component></app-my-component>
Benefits of Components
Advance Web-development 47
Structural Directives
<ul>
<li *ngFor="let item of items">{{ item }}</li>
</ul>
Attribute Directives
Role of Directives
Example:
Advance Web-development 48
<ul>
<li *ngFor="let user of users">{{ user.name }}</li>
</ul>
In conclusion, Angular directives are powerful tools for manipulating the DOM.
They enable dynamic behavior, improve code reusability, and enhance template
readability.
1. declarations: Lists the components, directives, and pipes that belong to the
module.
2. imports: Specifies other modules whose features are needed in this module.
4. bootstrap: Defines the root component that Angular should bootstrap when
the application starts.
Example:
// app.module.ts
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
Advance Web-development 49
import { AppComponent } from './app.component';
@NgModule({
declarations: [AppComponent],
imports: [BrowserModule],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule {}
Role of Modules
Feature Modules
Feature modules are used to organize the application into functional areas. For
example:
// user.module.ts
import { NgModule } from '@angular/core';
import { UserComponent } from './user.component';
@NgModule({
declarations: [UserComponent],
imports: []
})
export class UserModule {}
Advance Web-development 50
loading, and simplify dependency management.
1. Interpolation: {{ expression }}
Interpolation
Interpolation is used to embed expressions in the template. The expression is
evaluated, and the result is displayed in the view.
Property Binding
Property binding is used to set the value of an element's property based on a
component's property.
<img [src]="imageUrl">
Event Binding
Event binding is used to respond to user actions, such as clicks or keystrokes.
Two-Way Binding
Two-way binding combines property and event binding to keep the component
and view in sync.
Advance Web-development 51
<input [(ngModel)]="name">
<p>Hello, {{ name }}!</p>
Example:
1. Simplified Code: Data binding reduces the need for manual DOM
manipulation.
Advance Web-development 52
What are Services?
They are used to share data and functionality across components, promoting
reusability and separation of concerns.
Example:
// my-service.service.ts
import { Injectable } from '@angular/core';
@Injectable({
providedIn: 'root'
})
export class MyService {
getData(): string {
return 'Hello from Service!';
}
}
// app.component.ts
import { Component } from '@angular/core';
import { MyService } from './my-service.service';
@Component({
selector: 'app-root',
template: `<p>{{ message }}</p>`
})
Advance Web-development 53
export class AppComponent {
message: string;
Example:
// my-service.service.ts
import { Injectable } from '@angular/core';
@Injectable({
providedIn: 'root'
})
export class MyService {
private data: string[] = ['Apple', 'Banana', 'Orange'];
getData(): string[] {
return this.data;
}
Advance Web-development 54
}
}
Example:
// app.module.ts
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { AppComponent } from './app.component';
import { MyService } from './my-service.service';
@NgModule({
declarations: [AppComponent],
imports: [BrowserModule],
providers: [MyService], // Register the service
bootstrap: [AppComponent]
})
export class AppModule {}
Example:
Advance Web-development 55
// app.module.ts
@NgModule({
providers: [
{ provide: MyService, useClass: MyService }
]
})
// app.module.ts
@NgModule({
providers: [
{ provide: 'API_URL', useValue: '<https://api.example.com>' }
]
})
// app.component.ts
import { Component, Inject } from '@angular/core';
@Component({
selector: 'app-root',
template: `<p>{{ apiUrl }}</p>`
})
export class AppComponent {
constructor(@Inject('API_URL') public apiUrl: string) {}
}
Advance Web-development 56
Reactive forms are a model-driven approach to handling form inputs.
// app.component.ts
import { FormBuilder, FormGroup } from '@angular/forms';
<form [formGroup]="form">
<input formControlName="name" placeholder="Name">
<input formControlName="email" placeholder="Email">
</form>
this.form = this.fb.group({
name: ['', Validators.required],
email: ['', [Validators.required, Validators.email]]
});
Advance Web-development 57
<form [formGroup]="form" (ngSubmit)="onSubmit()">
<button type="submit">Submit</button>
</form>
onSubmit(): void {
console.log(this.form.value);
}
4.6.6 Grouping
this.form = this.fb.group({
personalInfo: this.fb.group({
name: [''],
email: ['']
})
});
this.form = this.fb.group({
items: this.fb.array([this.fb.control('')])
});
Advance Web-development 58
4.6.10 Async Validation
this.form = this.fb.group({
email: ['', [], [asyncValidator]]
});
this.form.valueChanges.subscribe(value => {
console.log(value);
});
4.7.2 Promises
fetchData(): Promise<string> {
return new Promise(resolve => {
setTimeout(() => resolve('Data'), 1000);
});
}
fetchData(): Observable<string> {
return of('Data');
}
Advance Web-development 59
4.7.4 EventEmitter
fetchData(): Observable<any> {
return this.http.get('<https://api.example.com/data>');
}
@NgModule({
imports: [HttpClientModule]
})
export class AppModule {}
Advance Web-development 60
Practice Problems
1. Create a service DataService that fetches data from an API using HttpClient .
Advance Web-development 61
@Injectable({
providedIn: 'root'
})
export class MyService {
getData(): string {
return 'Hello from Service!';
}
}
@Component({
selector: 'app-root',
template: `<p>{{ message }}</p>`
})
export class AppComponent {
message: string;
Advance Web-development 62
In conclusion, Angular services and Dependency Injection are fundamental to
building scalable and maintainable applications. They enable developers to
encapsulate functionality, promote reusability, and simplify testing.
onSubmit(): void {
console.log(this.form.value);
Advance Web-development 63
}
}
2. Dynamic Forms: Reactive forms support dynamic form controls (e.g., adding
or removing fields at runtime).
4. Scalability: Reactive forms are better suited for complex forms with nested
controls.
In conclusion, reactive forms provide a powerful and flexible way to handle form
inputs in Angular. They are ideal for complex forms and offer advantages such as
programmatic control, dynamic form handling, and centralized validation.
Advance Web-development 64
1. Observable: Represents a stream of data that can be observed over time.
2. Observer: An object with methods ( next , error , complete ) to handle data, errors,
and completion.
Example:
observable.subscribe({
next: value => console.log(value),
error: err => console.error(err),
complete: () => console.log('Completed')
});
fetchData(): Observable<any> {
return this.http.get('<https://api.example.com/data>');
}
Advance Web-development 65
// Subscribe to the observable
this.fetchData().subscribe(data => console.log(data));
Advantages of Observables
2. Multiple Values: Observables can emit multiple values over time, unlike
promises, which resolve once.
3. Operators: RxJS provides a rich set of operators (e.g., map , filter , merge ) to
transform and combine streams.
Advance Web-development 66
export function customValidator(control: AbstractControl): ValidationErrors | n
ull {
const value = control.value;
return value === 'test' ? { invalid: true } : null;
}
this.form = this.fb.group({
username: ['', [Validators.required, customValidator]]
});
Advance Web-development 67
5.1 Introduction to Next.js
What is Next.js?
Key Features:
5. Built-in CSS Support: Supports CSS modules, Sass, and styled JSX.
Dynamic Pages:
Ideal for pages with dynamic content (e.g., blog posts, user profiles).
Example:
Advance Web-development 68
// pages/posts/[id].js (Dynamic Page)
import { useRouter } from 'next/router';
Example:
/* styles/Home.module.css */
.title {
color: blue;
}
// pages/index.js
import styles from '../styles/Home.module.css';
Advance Web-development 69
5.4.1 Setup
1. Install Next.js:
Example:
// pages/index.js
export default function Home() {
return <h1>Hello, Next.js!</h1>;
}
Example:
// pages/index.js
import Link from 'next/link';
Advance Web-development 70
</div>
);
}
// pages/about.js
export default function About() {
return <h1>About Page</h1>;
}
Example:
// pages/index.js
import Head from 'next/head';
Advance Web-development 71
Example:
// pages/posts.js
export default function Posts({ posts }) {
return (
<ul>
{posts.map(post => (
<li key={post.id}>{post.title}</li>
))}
</ul>
);
}
return {
props: { posts },
};
}
Example:
// pages/posts/[id].js
import { useRouter } from 'next/router';
Advance Web-development 72
return <h1>Post ID: {id}</h1>;
}
Example:
// pages/api/hello.js
export default function handler(req, res) {
res.status(200).json({ message: 'Hello, World!' });
}
npm start
Practice Problems
Problem 1: Create a Static Page
Create a static page about.js that displays "About Us".
Solution:
// pages/about.js
export default function About() {
Advance Web-development 73
return <h1>About Us</h1>;
}
Solution:
/* styles/Home.module.css */
.title {
color: red;
}
// pages/index.js
import styles from '../styles/Home.module.css';
Solution:
// pages/users.js
export default function Users({ users }) {
return (
<ul>
{users.map(user => (
<li key={user.id}>{user.name}</li>
))}
Advance Web-development 74
</ul>
);
}
return {
props: { users },
};
}
Solution:
// pages/users/[id].js
import { useRouter } from 'next/router';
Solution:
Advance Web-development 75
// pages/api/greet.js
export default function handler(req, res) {
res.status(200).json({ message: 'Hello, World!' });
}
Key Features:
5. Built-in CSS Support: Supports CSS modules, Sass, and styled JSX.
Advance Web-development 76
Dynamic Pages:
Ideal for pages with dynamic content (e.g., blog posts, user profiles).
Example:
Example:
/* styles/Home.module.css */
.title {
color: blue;
}
Advance Web-development 77
// pages/index.js
import styles from '../styles/Home.module.css';
Example:
// pages/index.js
export default function Home() {
return <h1>Hello, Next.js!</h1>;
}
Example:
Advance Web-development 78
// pages/index.js
import Link from 'next/link';
// pages/about.js
export default function About() {
return <h1>About Page</h1>;
}
Example:
// pages/index.js
import Head from 'next/head';
Advance Web-development 79
</Head>
<h1>Home Page</h1>
<img src="/vercel.svg" alt="Vercel Logo" />
</div>
);
}
Example:
// pages/posts.js
export default function Posts({ posts }) {
return (
<ul>
{posts.map(post => (
<li key={post.id}>{post.title}</li>
))}
</ul>
);
}
return {
props: { posts },
};
}
Advance Web-development 80
Example:
// pages/posts/[id].js
import { useRouter } from 'next/router';
Example:
// pages/api/hello.js
export default function handler(req, res) {
res.status(200).json({ message: 'Hello, World!' });
}
npm start
Advance Web-development 81
Practice Problems
Problem 1: Create a Static Page
Create a static page about.js that displays "About Us".
Solution:
// pages/about.js
export default function About() {
return <h1>About Us</h1>;
}
Solution:
/* styles/Home.module.css */
.title {
color: red;
}
// pages/index.js
import styles from '../styles/Home.module.css';
Solution:
Advance Web-development 82
// pages/users.js
export default function Users({ users }) {
return (
<ul>
{users.map(user => (
<li key={user.id}>{user.name}</li>
))}
</ul>
);
}
return {
props: { users },
};
}
Solution:
// pages/users/[id].js
import { useRouter } from 'next/router';
Advance Web-development 83
return <h1>User ID: {id}</h1>;
}
Solution:
// pages/api/greet.js
export default function handler(req, res) {
res.status(200).json({ message: 'Hello, World!' });
}
1. Rendering Methods:
Advance Web-development 84
2. Routing:
3. API Routes:
4. Built-in Optimization:
5. Deployment:
Example:
// pages/index.js (Next.js)
export default function Home() {
return <h1>Welcome to Next.js!</h1>;
}
Advance Web-development 85
Q2: Explain the concept of Static Site Generation
(SSG) in Next.js and its benefits.
Answer:
Static Site Generation (SSG) is a pre-rendering technique in Next.js where HTML
pages are generated at build time. This means that the content of the pages is
determined when the application is built, and the same static HTML is served to all
users. SSG is ideal for pages with static or infrequently changing content, such as
blogs, documentation, or marketing websites.
1. Build Time: During the build process, Next.js fetches data and generates
static HTML for each page.
2. Serving Content: The generated HTML is served to users, ensuring fast load
times and reduced server load.
Example:
// pages/posts.js
export default function Posts({ posts }) {
return (
<ul>
{posts.map(post => (
<li key={post.id}>{post.title}</li>
))}
</ul>
);
}
return {
props: { posts },
Advance Web-development 86
};
}
Benefits of SSG:
1. Performance: Static HTML pages load faster since they do not require server-
side processing for each request.
2. Scalability: Static files can be served via CDNs, reducing server load and
improving scalability.
4. Security: Static sites have fewer attack vectors compared to dynamic sites.
2. Request Handling: API Routes handle HTTP requests (GET, POST, PUT,
DELETE) and return JSON responses.
Example:
// pages/api/hello.js
export default function handler(req, res) {
Advance Web-development 87
res.status(200).json({ message: 'Hello, World!' });
}
Example Usage:
// pages/index.js
import { useEffect, useState } from 'react';
useEffect(() => {
fetch('/api/hello')
.then(res => res.json())
.then(data => setMessage(data.message));
}, []);
return <h1>{message}</h1>;
}
Advance Web-development 88
Q4: Explain the role of Dynamic Routes in Next.js and
how they handle dynamic content.
Answer:
Dynamic Routes in Next.js allow developers to create pages with dynamic content
based on URL parameters. This is particularly useful for pages like blog posts,
user profiles, or product details, where the content depends on the URL.
How Dynamic Routes Work:
1. File Naming: Dynamic routes are created using square brackets ( [] ) in the file
name (e.g., pages/posts/[id].js ).
Example:
// pages/posts/[id].js
import { useRouter } from 'next/router';
Example:
// pages/posts/[id].js
export default function Post({ post }) {
return (
<div>
Advance Web-development 89
<h1>{post.title}</h1>
<p>{post.body}</p>
</div>
);
}
return {
props: { post },
};
}
return {
paths,
fallback: false,
};
}
Advance Web-development 90
3. Scalability: Dynamic routes work seamlessly with SSG and SSR.
1. File Naming: CSS Module files use the .module.css extension (e.g.,
Home.module.css ).
2. Scoped Styles: Class names are locally scoped to the component, ensuring
they do not conflict with other styles.
Example:
/* styles/Home.module.css */
.title {
color: blue;
}
// pages/index.js
import styles from '../styles/Home.module.css';
Advance Web-development 91
1. Local Scope: Styles are scoped to the component, preventing global conflicts.
4. Performance: Only the required styles are loaded, reducing the overall CSS
bundle size.
In conclusion, CSS Modules in Next.js provide a clean and efficient way to style
components. They enhance maintainability, reusability, and performance, making
them a valuable tool for modern web development.
Advance Web-development 92