Introduction In this step by step tutorial, I'm going to perform Login and CRUD operations in ASP.NET Web API using Angular 9 Web applic...

Login and CRUD operations in ASP.NET Web API Using Angular 9 Web application

Wednesday, July 08, 2020 0 Comments


Introduction
In this step by step tutorial, I'm going to perform Login and CRUD operations in ASP.NET Web API using Angular 9 Web application. The backend is a Microsoft SQL Server database. A Web API is used to provide data connectivity between the database and the front end application. On the UI side, I will use the Angular Material to create a rich, interactive, and device-independent user experience.

In this article, we will learn the step by step process of creating login and crud operations in ASP.NET Web API using Angular 9 using the following technologies: 
1.) ASP.NET Web API.
2.) Angular 9.
3.) Microsoft SQL Server
4.) Angular Material
5.) Bootstrap 

Download Requirements:
1.) Basic knowledge of Angular and Web API.
2.) Visual Studio Code and Visual Studio should be installed.
3.) MS SQL Server and SQL Server Management Studio should be installed.
4.) Nodejs should be installed.
Step 1: 
Open SQL Server Management Studio, create a database named Employee, and in this database, create a three table. 
Give that table a name like Employeemaster, Employees and Departments.
Open new query and run this code in query section: 
1.) Create Database named as Employee
 

2.) Create table Employeemaster using query or design any of these:
CREATE TABLE [dbo].[Employeemaster](  
    [UserId] [int] IDENTITY(1,1) NOT NULL,  
    [UserName] [varchar](50) NOT NULL,  
    [LoginName] [varchar](50) NULL,  
    [Password] [varchar](50) NOT NULL,  
    [Email] [varchar](50) NULL,  
    [ContactNo] [varchar](15) NULL,  
    [Address] [varchar](50) NULL,  
    [IsApporved] [int] NULL,  
    [Status] [int] NULL,  
    [TotalCnt] [int] NULL,  
PRIMARY KEY CLUSTERED   
(  
    [UserId] ASC  
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]  
) ON [PRIMARY]  
GO  
Or  
Create design table in database: 
 


3.) Now, for Login purpose create a stored procedure with the name, Usp_Login for adding the login functionality:
create proc  [dbo].[Usp_Login]  
@UserName varchar(50)='',  
@Password varchar(50)=''  
as begin  
    declare @UserId int =0,@TotalCnt int =0  
    select @UserId=UserId,@TotalCnt=TotalCnt from  Employeemaster um   
    where LoginName=@UserName and Password=@Password and Status<>3 and IsApporved=1  
    if(@TotalCnt>=5)  
    begin  
       select 0 UserId,'' UserName,'' LoginName,'' Password,'' Email,'' ContactNo,   
    ''Address,0 IsApporved,-1 Status  
    end  
    if(@UserId>0)  
    begin  
        select UserId, UserName, LoginName, Password, Email, ContactNo,   
        Address, IsApporved, Status from  Employeemaster um   
        where UserId=@UserId   
        --update  Employeemaster  set  Status=2 where UserId=@UserId   
    end  
    else  
    begin  
       Update Employeemaster set @TotalCnt=TotalCnt+1    
       where LoginName=@UserName and Status=1 and IsApporved=1  
       select 0 UserId,'' UserName,'' LoginName,'' Password,'' Email,'' ContactNo,   
    ''Address,0 IsApporved,0 Status  
    end    end  
 

4.)  Create table Employee
 

5.) Create table Department

 
Step 2. 
Open Visual Studio >> File >> New >> Project >> Select Web Application. After that click OK and you will see the templates. Select the Web API template and click OK. You will see like this: 
 

Step 3. 
Now, Select Models folder >> Right click >>Add >> New Item >> select Data in left panel >>ADO.NET Entity Data Model,
Click on the ADO.NET Entity Data Model option and click Add.
Select EF designer from the database and click the Next button.
Add the connection properties, select database name on the next page, and click OK.
Check the Tables and Stored procedure checkboxes. 
The internal options will be selected by default. Now, click the Finish button.
Our data model is created now like this:
  
 



Step 4. 
Again Right-click on the Models folder and add two classes — Login and Response respectively. 
Response.cs:
public class Response
{
     public string Status { set; get; }
     public string Message { set; get; }
    }

Login.cs:
public class Login
    {
        public string UserName { set; get; }
        public string Password { set; get; }
    }
    public class Registration : Employeemaster { }

Now, paste the following codes in these classes. 
using LoginAPI.Models;   



Step 5.
Go to the Controller folder in our API Application and right click >> Add >> Controller >> Select Web API 2 Controller-Empty and then add a new controller. Name it as Logincontroller, DepartmentController, EmployeeController.
Now, we will go to the Login controller with the following lines of code:

using LoginAPI.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;
namespace LoginAPI.Controllers
{
    public class LoginController : ApiController
    {
        //For user login   
        [Route("Api/Login/UserLogin")]
        [HttpPost]
        public Response Login(Login Lg)
        {
            EmployeeEntities DB = new EmployeeEntities();
            var Obj = DB.Usp_Login(Lg.UserName, Lg.Password).ToList<Usp_Login_Result>().FirstOrDefault();
            if (Obj.Status == 0)
                return new Response { Status = "Invalid", Message = "Invalid User." };
            if (Obj.Status == -1)
                return new Response { Status = "Inactive", Message = "User Inactive." };
            else
                return new Response { Status = "Success", Message = Lg.UserName };
        }

        //For new user Registration  
        [Route("Api/Login/UserRegistration")]
        [HttpPost]
        public object createcontact(Registration Lvm)
        {
            try
            {
                EmployeeEntities1 db = new EmployeeEntities1();
                Employeemaster Em = new Employeemaster();
                if (Em.UserId == 0)
                {
                    Em.UserName = Lvm.UserName;
                    Em.LoginName = Lvm.LoginName;
                    Em.Password = Lvm.Password;
                    Em.Email = Lvm.Email;
                    Em.ContactNo = Lvm.ContactNo;
                    Em.Address = Lvm.Address;
                    Em.IsApporved = Lvm.IsApporved;
                    Em.Status = Lvm.Status;
                    db.Employeemasters.Add(Em);
                    db.SaveChanges();
                    return new Response
                    { Status = "Success", Message = "SuccessFully Saved." };
                }
            }
            catch (Exception)
            {
                throw;
            }
            return new Response
            { Status = "Error", Message = "Invalid Data." };
        }
    }
}

Now, we will go to the Department controller with the following lines of code:
using LoginAPI.Models;
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;

namespace LoginAPI.Controllers
{
    [RoutePrefix("Api/Department")]
    public class DepartmentController : ApiController
    {
        private EmployeeEntities objEntity = new EmployeeEntities();

        [HttpGet]
        [Route("AllDepartments")]
        public IQueryable<Department> GetDepartment()
        {
            try
            {
                return objEntity.Departments;
            }
            catch (Exception)
            {
                throw;
            }
        }

        [HttpGet]
        [Route("GetDepartmentsById/{DepartmentID}")]
        public IHttpActionResult GetDepartmentById(string DepartmentID)
        {
            Department objDep = new Department();
            int ID = Convert.ToInt32(DepartmentID);
            try
            {
                objDep = objEntity.Departments.Find(ID);
                if (objDep == null)
                {
                    return NotFound();
                }

            }
            catch (Exception)
            {
                throw;
            }

            return Ok(objDep);
        }

        [HttpPost]
        [Route("InsertDepartments")]
        public IHttpActionResult PostDepartment(Department data)
        {

            if (!ModelState.IsValid)
            {
                return BadRequest(ModelState);
            }
            try
            {
                objEntity.Departments.Add(data);
                objEntity.SaveChanges();
            }
            catch (Exception)
            {
                throw;
            }

            return Ok(data);
        }

        [HttpPut]
        [Route("UpdateDepartments")]
        public IHttpActionResult PutDepartment (Department department)
        {
            if (!ModelState.IsValid)
            {
                return BadRequest(ModelState);
            }

            try
            {
                Department objDep = new Department();
                objDep = objEntity.Departments.Find(department.DepartmentID);
                if (objDep != null)
                {
                    objDep.DepartmentName = department.DepartmentName;
                }
                int i = this.objEntity.SaveChanges();

            }
            catch (Exception)
            {
                throw;
            }
            return Ok(department);
        }

        [HttpDelete]
        [Route("DeleteDepartments")]
        public IHttpActionResult DeleteDepartment (int id)
        {
            //int empId = Convert.ToInt32(id);  
            Department department = objEntity.Departments.Find(id);
            if (department == null)
            {
                return NotFound();
            }

            objEntity.Departments.Remove(department);
            objEntity.SaveChanges();

            return Ok(department);
        }
    }
}
 
Now, we will go to the Employee controller with the following lines of code:
using LoginAPI.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Web.Http;
namespace LoginAPI.Controllers
{
    [RoutePrefix("Api/Employee")]
    public class EmployeeController : ApiController
    {
        private EmployeeEntities objEntity = new EmployeeEntities();

        [HttpGet]
        [Route("AllEmployees")]
        public IQueryable<Employee> GetEmployee()
        {
            try
            {
                return objEntity.Employees;
            }
            catch (Exception)
            {
                throw;
            }
        }

        [HttpGet]
        [Route("Department")]
        public IQueryable<Department> GetDepartment()
        {
            try
            {
                return objEntity.Departments;
            }
            catch (Exception)
            {
                throw;
            }
        }

        [HttpGet]
        [Route("GetEmployeesById/{employeeId}")]
        public IHttpActionResult GetEmployeeById(string employeeId)
        {
            Employee objEmp = new Employee();
            int ID = Convert.ToInt32(employeeId);
            try
            {
                objEmp = objEntity.Employees.Find(ID);
                if (objEmp == null)
                {
                    return NotFound();
                }

            }
            catch (Exception)
            {
                throw;
            }

            return Ok(objEmp);
        }

        [HttpPost]
        [Route("InsertEmployees")]
        public IHttpActionResult PostEmployee (Employee data)
        {

            if (!ModelState.IsValid)
            {
                return BadRequest(ModelState);
            }
            try
            {
                objEntity.Employees.Add(data);
                objEntity.SaveChanges();
            }
            catch (Exception)
            {
                throw;
            }

            return Ok(data);
        }

        [HttpPut]
        [Route("UpdateEmployees")]
        public IHttpActionResult PutEmployee (Employee employee)
        {
            if (!ModelState.IsValid)
            {
                return BadRequest(ModelState);
            }

            try
            {
                Employee objEmp = new Employee();
                objEmp = objEntity.Employees.Find(employee.EmployeeID);
                if (objEmp != null)
                {
                    objEmp.EmployeeName = employee.EmployeeName;
                    objEmp.Department = employee.Department;
                    objEmp.MailID = employee.MailID;
                    objEmp.DOJ = employee.DOJ;
                    objEmp.Address = employee.Address;
                    objEmp.Phone = employee.Phone;
                    objEmp.Salary = employee.Salary;
                    objEmp.Age = employee.Age;

                }
                int i = this.objEntity.SaveChanges();

            }
            catch (Exception)
            {
                throw;
            }
            return Ok(employee);
        }

        [HttpDelete]
        [Route("DeleteEmployees")]
        public IHttpActionResult DeleteEmployee (int id)
        {
            //int empId = Convert.ToInt32(id);  
            Employee employee = objEntity.Employees.Find(id);
            if (employee == null)
            {
                        return NotFound();
            }

            objEntity.Employees.Remove(employee);
            objEntity.SaveChanges();

            return Ok(employee);
        }
    }
}

Step 6.
If you consume the Web API, Angular blocks the URL and we called this issue CORS(Cross OriginResource Sharing)
First, let's resolve this problem.
Go to the Web API project.
Download a Nuget package for CORS. Go to NuGet Package Manager and download the following file.
After that, go to App_Start folder in Web API project and open WebApiConfig.cs class. Here, modify the Register method with the below code.
Add namespace  
using System.Web.Http.Cors;  

// for JSON data into test data in POSTMAN
config.Formatters.JsonFormatter.SupportedMediaTypes.Add(new 
MediaTypeHeaderValue("text/html"));

// enable cors helps to connect with angular using http request
EnableCorsAttribute cors = new EnableCorsAttribute("*", "*", "*");
config.EnableCors(cors);

Step 7.
Build UI Application using Angular 9 Angular CLI and angular material that will consume Web API.
Now, open Visual Studio Code and create a project add bootstrap to this project:
Open TERMINAL in Visual Studio Code and type the following syntax to create a new project. Using command: 
ng new login                 // create your login  project 
cd login                        // location to login project
ng add @angular/material             // add  angular material 
npm install bootstrap –save            // add bootstrap
ng serve –open              // opens your project at localhost://4200

Now, write the following command that will create a components, services, models.
ng g c dashboard
Now, open dashboard.component.html and add the following lines.
<div>
  <div class="row">
    <div class="col-sm-12 btn btn-primary">
      Welcome to DashBoard
    </div>
    <div class="row">
      <div class="col-sm-12">
        <nav class="navbar navbar-expand-sm bg-light navbar-dark">
          <ul class="navbar-nav">
            <li class="nav-item">
              <a routerLink="/Dashboard" routerLinkActive="active"
                class="m-1 btn btn-light btn-outline-primary">Dashboard</a>
            </li>
          </ul>
          <ul class="navbar-nav">
            <li class="nav-item">
              <a routerLink="department" routerLinkActive="active"
                class="m-1 btn btn-light btn-outline-primary">Departments</a>
            </li>
          </ul>
          <ul class="navbar-nav">
            <li class="nav-item">
              <a routerLink="employee" routerLinkActive="active"
                class="m-1 btn btn-light btn-outline-primary">Employees</a>
            </li>
          </ul>
        </nav>
      </div>
    </div>
  </div>
  <router-outlet></router-outlet>
</div>


Now, open dashboard.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';

@Component({
  selector: 'app-dashboard',
  templateUrl: './dashboard.component.html',
  styleUrls: ['./dashboard.component.css']
})
export class DashboardComponent implements OnInit {
  
  constructor( ) { }

  ngOnInit(): void {
  }

}



ng g c login
Now, open login.component.html and add the following lines.
<div class="container" style="padding-top:60px;">
  <div class="row">
    <div class="col-md-6 mx-auto">
      <div class="card-group">
        <div class="card p-4">
          <div class="card-body">
            <form class="form-horizontal" class="login" [formGroup]="loginForm" (ngSubmit)="login()">
              <div class="form-group row" [ngClass]="{'has-error': (loginForm.get('UserName').touched || loginForm.get('UserName').dirty) &&
          !loginForm.get('UserName').valid }">
                <label class="col-sm-3">
                  <strong>UserName * </strong>
                </label>
                <div class="col-sm-8">
                  <i style="position: relative;top: 24px;right: -300px;cursor: pointer;" class="fa fa-envelope"></i>
                  <input type="text" formControlName="UserName" class="form-control form-control-sm"
                    placeholder="Your UserName">
                  <span class="text-danger" *ngIf="(loginForm.get('UserName').touched || loginForm.get('UserName').dirty) && 
                  loginForm.get('UserName').errors">
                    <span *ngIf="loginForm.get('UserName').errors.required">Please enter your UserName
                      address.</span></span>
                </div>
              </div>

              <div class="form-group row" [ngClass]="{'has-error': (loginForm.get('Password').touched || loginForm.get('Password').dirty)
               &&
          !loginForm.get('Password').valid }">
                <label class="col-sm-3">
                  <strong>Password * </strong>
                </label>

                <div class="col-sm-8">
                  <input type="{{password ? 'text' : 'password' }}" formControlName="Password"
                    class="form-control form-control-sm" placeholder="Your Password" required>
                  <span class="form-control-password" style="float:right;"
                    (click)="togglePassword()">{{password ? 'Hide': 'Show'}}</span>
                  <span class="text-danger" *ngIf="(loginForm.get('Password').touched || loginForm.get('Password').dirty) && 
loginForm.get('Password').errors">
                    <span *ngIf="loginForm.get('Password').errors.required">Please enter your Password.</span>
                    <span *ngIf="loginForm.get('Password').errors.minlength">The Password must be longer than 4
                      characters.</span>
                    <span *ngIf="loginForm.get('Password').errors.maxlength">The Password must be not longer than 30
                      characters.</span>
                  </span>
                </div>
              </div>
              <div>
                <p style="color:#E92626;font-size:20px;font-weight:normal" Class="success" align="left">
                  {{errorMessage}}
                </p>
              </div>
              <div class="text-center">
                <button type="submit" class="btn btn-success active" [disabled]="!loginForm.valid"
                  style="margin-right: 8px; cursor: pointer;">Login</button>
                <a>Forgot Password ?</a>
                <hr>
                <button type="button" class="btn btn-success btn-lg btn-block px-12"
                  [routerLink]="['/register']">Register</button>
              </div>
            </form>
          </div>
        </div>
      </div>
    </div>
  </div>
</div>


Now, open login.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';
import { FormsModule, FormBuilder, Validators, FormGroup } from '@angular/forms';
import { LoginService } from '../services/login.service';
import { MatSnackBar } from '@angular/material/snack-bar';
import { Register } from '../models/register';
@Component({
  selector: 'app-login',
  templateUrl: './login.component.html',
  styleUrls: ['./login.component.css']
})
export class LoginComponent {
  password: boolean = false;
  loginForm: FormGroup;
  model: any = {};
  errorMessage: string;
  constructor(private router: Router, 
    private LoginService: LoginService,
    private fb: FormBuilder,
    public snackBar: MatSnackBar,
 ) { }

  ngOnInit() {
    this.loginForm = this.fb.group({
      UserName: [null, [Validators.required]],
      Password: [null, [Validators.required, Validators.minLength(4), Validators.maxLength(30)]],
    });

    sessionStorage.removeItem('UserName');
    sessionStorage.clear();
  }

  togglePassword() {
    this.password = !this.password;
  }

  login() {
    this.LoginService.Login(this.model).subscribe(
      data => {
        if (data.Status == "Success") {
          this.router.navigate(['/Dashboard']);
          let snackBarRef = this.snackBar.open('loggedin Successfully!',
      'Got it!', {
        duration: 3000,
        verticalPosition: 'top',
        horizontalPosition: 'right',
      });
        }
        else {
          this.errorMessage = data.Message;
        }
      },
      error => {
        this.errorMessage = error.message;
      });
  };
}     

Now, open login.component.css and add the following lines.
    .form-control-password {
      position: relative;
      top: -27px;
      left: -4px;
      cursor: pointer;
  }


ng g c register
Now, open register.component.html and add the following lines.
<div class="container" style="padding-top:40px;">
  <div class="row">
    <div class="col-md-6 mx-auto">
      <div class="card mx-4">
        <div class="card-body p-4">
          <form class="form-horizontal" [formGroup]="registerForm" (ngSubmit)="register()" novalidate>
          <h1 style="text-align:center">Register</h1>
          <!-- start UserName -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('UserName').touched || registerForm.get('UserName').dirty) &&
            !registerForm.get('UserName').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>User Name * </strong>
            </label>
            <div class="col-sm-8">
              <i style="position: relative;top: 24px;right: -310px;cursor: pointer;" class="fa fa-user"></i>
              <input type="text" formControlName="UserName" class="form-control form-control-sm"
                placeholder="Your UserName">
              <span class="text-danger" *ngIf="(registerForm.get('UserName').touched || registerForm.get('UserName').dirty) && 
                 registerForm.get('UserName').errors">
                <span *ngIf="registerForm.get('UserName').errors.required">Please enter your user name.</span>
                <span *ngIf="registerForm.get('UserName').errors.minlength">The user name must be longer than 3
                  characters.</span>
              </span>
            </div>
          </div>
          <!-- start UserName -->
          <!-- start LoginName -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('LoginName').touched || registerForm.get('LoginName').dirty) &&
                  !registerForm.get('LoginName').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>Login Name * </strong>
            </label>
            <div class="col-sm-8">
              <i style="position: relative;top: 24px;right: -310px;cursor: pointer;" class="fa fa-user"></i>
              <input type="text" formControlName="LoginName" class="form-control form-control-sm"
                placeholder="Your LoginName">
              <span class="text-danger" *ngIf="(registerForm.get('LoginName').touched || registerForm.get('LoginName').dirty) && 
                       registerForm.get('LoginName').errors">
                <span *ngIf="registerForm.get('LoginName').errors.required">Please enter your login name.</span>
                <span *ngIf="registerForm.get('LoginName').errors.minlength">The login name must be longer than 3
                  characters.</span>
              </span>
            </div>
          </div>
          <!-- start LoginName -->

          <!-- start email -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('Email').touched || registerForm.get('Email').dirty) &&
                  !registerForm.get('Email').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>Email * </strong>
            </label>
            <div class="col-sm-8">
              <i style="position: relative;top: 24px;right: -310px;cursor: pointer;" class="fa fa-envelope"></i>
              <input type="text" formControlName="Email" class="form-control form-control-sm" placeholder="Your Email">
              <span class="text-danger" *ngIf="(registerForm.get('Email').touched || registerForm.get('Email').dirty) && 
                      registerForm.get('Email').errors">
                <span *ngIf="registerForm.get('Email').errors.required">Please enter your Email address.</span>
                <br>
                <span *ngIf="registerForm.get('Email').errors.Email">Please enter a valid Email address.</span>
              </span>
            </div>
          </div>
          <!-- end email -->

          <!-- start password -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('Password').touched || registerForm.get('Password').dirty) &&
                  !registerForm.get('Password').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>Password * </strong>
            </label>
            <div class="col-sm-8">
              <!-- <i style="position: relative;top: 24px;right: -300px;cursor: pointer;" class="fa fa-eye"></i> -->
              <input type="{{password ? 'text' : 'password' }}" formControlName="Password"
                class="form-control form-control-sm" placeholder="Your Password" required>
              <span class="form-control-password" style="float:right;"
                (click)="togglePassword()">{{password ? 'Hide': 'Show'}}</span>
              <span class="text-danger" *ngIf="(registerForm.get('Password').touched || registerForm.get('Password').dirty) && 
                      registerForm.get('Password').errors">
                <span *ngIf="registerForm.get('Password').errors.required">Please enter your Password.</span>
                <span *ngIf="registerForm.get('Password').errors.minlength">The Password must be longer than 4
                  characters.</span>
                <span *ngIf="registerForm.get('Password').errors.maxlength">The Password must be not longer than 30
                  characters.</span>
              </span>
            </div>
          </div>
          <!-- end password -->

          <!-- start ContactNo -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('ContactNo').touched || registerForm.get('ContactNo').dirty) &&
             !registerForm.get('ContactNo').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>ContactNo * </strong>
            </label>
            <div class="col-sm-8">
              <i style="position: relative;top: 24px;right: -310px;cursor: pointer;" class="fa fa-user-plus"></i>
              <input type="text" formControlName="ContactNo" class="form-control form-control-sm"
                placeholder="Your ContactNo">
              <span class="text-danger" *ngIf="(registerForm.get('ContactNo').touched || registerForm.get('ContactNo').dirty) && 
                  registerForm.get('ContactNo').errors">
                <span *ngIf="registerForm.get('ContactNo').errors.required">Please enter your ContactNo.</span>
              </span>
            </div>
          </div>
          <!-- end ContactNo -->

          <!-- start Address -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('Address').touched || registerForm.get('Address').dirty) &&
              !registerForm.get('Address').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>Address * </strong>
            </label>
            <div class="col-sm-8">
              <i style="position: relative;top: 24px;right: -310px;cursor: pointer;" class="fa fa-user-plus"></i>
              <input type="text" formControlName="Address" class="form-control form-control-sm"
                placeholder="Your Address">
              <span class="text-danger" *ngIf="(registerForm.get('Address').touched || registerForm.get('Address').dirty) && 
                   registerForm.get('Address').errors">
                <span *ngIf="registerForm.get('Address').errors.required">Please enter your role.</span>
              </span>
            </div>
          </div>
          <!-- end Address -->

          <!-- start status -->
          <div class="form-group row" [ngClass]="{'has-error': (registerForm.get('Status').touched || registerForm.get('Status').dirty) &&
                  !registerForm.get('Status').valid }">
            <label class="col-sm-3 col-form-label">
              <strong>Status * </strong>
            </label>
            <div class="col-sm-8">
              <input type="number" formControlName="Status" class="form-control form-control-sm"
                placeholder="Your Status" required>
              <span class="text-danger" *ngIf="(registerForm.get('Status').touched || registerForm.get('Status').dirty) && 
                      registerForm.get('Status').errors">
                <span *ngIf="registerForm.get('Status').errors.required">Please enter your Status greater or equals than 1.</span>
              </span>
            </div>
          </div>
          <!-- end status -->

          <!-- start actions -->
          <div class="text-center">
            <button type="submit" class="btn btn-success active" style="margin-right: 8px;cursor:pointer;"
              [disabled]="!registerForm.valid">Register</button>
            <button class="btn btn-warning active" style="cursor:pointer;" (click)="cancel()">Cancel</button>
          </div>
          <!-- end actions -->
          </form>
        </div>
      </div>
    </div>
  </div>
</div>


Now, open register.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';

import { FormBuilder, FormGroup, Validators } from '@angular/forms';
import { Router } from '@angular/router';
import { LoginService } from '../services/login.service';
import { Register } from '../models/register';
import { MatSnackBar } from '@angular/material/snack-bar';

@Component({
  selector: 'app-register',
  templateUrl: './register.component.html',
  styleUrls: ['./register.component.css']
})
export class RegisterComponent implements OnInit {
  password: boolean = false;
  registerForm: FormGroup;
  data = false;
  massage: string;

  constructor(private router: Router, 
    private formbulider: FormBuilder, 
    private loginService: LoginService,
    public snackBar: MatSnackBar,) { }

  ngOnInit() {
    this.registerForm = this.formbulider.group({
      UserName: ['', [Validators.required, Validators.minLength(3)]],
      LoginName: ['', [Validators.required, Validators.minLength(3)]],
      Password: ['', [Validators.required, Validators.minLength(4), Validators.maxLength(30)]],
      Email: ['', [Validators.required, Validators.email]],
      ContactNo: ['', [Validators.required]],
      Address: ['', [Validators.required]],
      Status: ['', [Validators.required]],
    });
  }

   togglePassword() {
        this.password = !this.password;
    }

    register() {
    const user = this.registerForm.value;
    this.createEmployee(user);
    // let snackBarRef = this.snackBar.open('Registerd Successfully!',
    // 'Got it!', {
    //     duration: 3000,
    //     verticalPosition: 'top',
    //     horizontalPosition: 'right',
    // });
  }

  createEmployee(register: Register) {
    this.loginService.CreateUser(register).subscribe(
      (x) => {
        this.data = true;
        this.router.navigate(['/login']);
        this.massage = 'Data saved Successfully';
        this.registerForm.reset();
      });
  }

  cancel() {
    this.router.navigate(['/register']);
}
}    

Now, open register.component.css and add the following lines.
.form-control-password {
    position: relative;
    top: -27px;
    left: -4px;
    cursor: pointer;
}


ng g c employee 
Now, open employee.component.html and add the following lines.
<app-show-emp></app-show-emp>




Now, open employee.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';

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

  constructor() { }

  ngOnInit(): void {
  }

}


ng g c employee/add-emp
Now, open add-emp.component.html and add the following lines.
<div class="d-flex justify-content-between">
    <h4>Add New Employee</h4>
    <button mat-button (click)="onClose()">
        <mat-icon>close</mat-icon>
    </button>
</div>

<div style="overflow: auto; height: 450px;">
    <form #form="ngForm" (submit)="onSubmit(form)" autocomplete="off">
        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Employee Name</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="EmployeeName" #EmployeeName="ngModel"
                [(ngModel)]="service.formData.EmployeeName" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Department</span>
            </div>
            <select required class="form-control" name="Department" #Department="ngModel"
                [(ngModel)]="service.formData.Department">
                <option *ngFor="let dl of listItems" [value]="dl">
                    {{dl}}
                </option>
            </select>
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">MailID</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="MailID" #MailID="ngModel"
                [(ngModel)]="service.formData.MailID" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">DOJ</span>
            </div>
            <input required [matDatepicker]="picker" type="text" class="form-control" name="DOJ" #DOJ="ngModel"
                [(ngModel)]="service.formData.DOJ" />
            <mat-datepicker-toggle matsuffix [for]="picker"></mat-datepicker-toggle>
            <mat-datepicker #picker></mat-datepicker>
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Age</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Age" #Age="ngModel"
                [(ngModel)]="service.formData.Age" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Salary</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Salary" #Salary="ngModel"
                [(ngModel)]="service.formData.Salary" />
        </div>
        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Address</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Address" #Address="ngModel"
                [(ngModel)]="service.formData.Address" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Phone</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Phone" #Phone="ngModel"
                [(ngModel)]="service.formData.Phone" />
        </div>
        <button class="mt-4" mat-raised-button color="primary" type="submit" [disabled]="form.invalid">
            Add Employee
        </button>
    </form>
</div>

Now, open add-emp.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { MatDialogRef } from '@angular/material/dialog';
import { EmployeeService } from 'src/app/services/employee.service';
import { MatSnackBar } from '@angular/material/snack-bar';
import { NgForm, FormControl } from '@angular/forms';
import { element } from 'protractor';

@Component({
  selector: 'app-add-emp',
  templateUrl: './add-emp.component.html',
  styleUrls: ['./add-emp.component.css']
})
export class AddEmpComponent implements OnInit {
  constructor(public dialogbox: MatDialogRef<AddEmpComponent>,
    public service: EmployeeService,
    private snackBar: MatSnackBar) { }
  public listItems: Array<string> = [];
  ngOnInit(): void {
    this.resetForm();
    this.dropdownRefresh();
  }

  dropdownRefresh() {
    this.service.getDepDropDownValues().subscribe(data => {
      console.log(data);
      data.forEach(element => {
        this.listItems.push(element["DepartmentName"]);
      })
    })
  }

  resetForm(form?: NgForm) {
    if (form != null)
      form.resetForm();

    this.service.formData = {
      EmployeeID: 0,
      EmployeeName: '',
      Department: '',
      MailID: '',
      DOJ: null,
      Address: '',
      Phone: null,
      Age: null,
      Salary: null,
    }
  }

  onClose() {
    this.dialogbox.close();
    this.service.filter('registert Click');
  }

  onSubmit(form: NgForm) {
    console.log(form.value);
    this.service.addEmployee(form.value).subscribe((res) => {
      this.resetForm();
      this.snackBar.open(res.toString(), 'Added Sucessfully!', {
        verticalPosition: 'top',
        duration: 3000
      });
    })
  }
}



ng g c employee/edit-emp
Now, open edit-emp.component.html and add the following lines.
<div class="d-flex justify-content-between m-3">
    <h4>Edit Employee</h4>
    <button mat-button (click)="onClose()">
        <mat-icon>close</mat-icon>
    </button>
</div>

<div style="overflow: auto; height: 450px;">
    <form #form="ngForm" (submit)="onSubmit(form)" autocomplete="off">
        <div class="m-3 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Employee ID</span>
            </div>
            <input readonly="readonly" type="text" class="form-control" name="EmployeeID" #EmployeeID="ngModel"
                [(ngModel)]="service.formData.EmployeeID" />
        </div>

        <div class="m-3 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Employee Name</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="EmployeeName" #EmployeeName="ngModel"
                [(ngModel)]="service.formData.EmployeeName" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Department</span>
            </div>
            <select required class="form-control" name="Department" #Department="ngModel"
                [(ngModel)]="service.formData.Department">
                <option *ngFor="let dl of listItems" [value]="dl">
                    {{dl}}
                </option>
            </select>
        </div>

        <div class="m-3 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">MailID</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="MailID" #MailID="ngModel"
                [(ngModel)]="service.formData.MailID" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">DOJ</span>
            </div>
            <input required [matDatepicker]="picker" type="text" class="form-control" name="DOJ" #DOJ="ngModel"
                [(ngModel)]="service.formData.DOJ" />
            <mat-datepicker-toggle matsuffix [for]="picker"></mat-datepicker-toggle>
            <mat-datepicker #picker></mat-datepicker>
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Age</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Age" #Age="ngModel"
                [(ngModel)]="service.formData.Age" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Salary</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Salary" #Salary="ngModel"
                [(ngModel)]="service.formData.Salary" />
        </div>
        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Address</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Address" #Address="ngModel"
                [(ngModel)]="service.formData.Address" />
        </div>

        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Phone</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="Phone" #Phone="ngModel"
                [(ngModel)]="service.formData.Phone" />
        </div>

        <button class="m-3" mat-raised-button color="primary" type="submit" [disabled]="form.invalid">
            Update Employee
        </button>
    </form>
</div>

Now, open edit-emp.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { EmployeeService } from 'src/app/services/employee.service';
import { MatSnackBar } from '@angular/material/snack-bar';
import { NgForm, FormControl } from '@angular/forms';
import { MatDialogRef } from '@angular/material/dialog';

@Component({
  selector: 'app-edit-emp',
  templateUrl: './edit-emp.component.html',
  styleUrls: ['./edit-emp.component.css']
})
export class EditEmpComponent implements OnInit {
  constructor(public dialogbox: MatDialogRef<EditEmpComponent>,
    public service: EmployeeService,
    private snackBar: MatSnackBar) { }
  public listItems: Array<string> = [];
  ngOnInit(): void {
    this.dropdownRefresh();
  }

  dropdownRefresh() {
    this.service.getDepDropDownValues().subscribe(data => {
      console.log(data);
      data.forEach(element => {
        this.listItems.push(element["DepartmentName"]);
      })
    })
  }

  onClose() {
    this.dialogbox.close();
    this.service.filter('registert Click');
  }

  onSubmit(form: NgForm) {
    console.log(form.value);
    this.service.updateEmployee(form.value).subscribe((res) => {
      this.snackBar.open(res.toString(), 'Updated Sucessfully!', {
        verticalPosition: 'top',
        duration: 3000
      });
    })
  }
}



ng g c employee/delete-emp
Now, open delete-emp.component.ts and add the following lines.
import { Component, Input } from '@angular/core';
import { MatSnackBar } from '@angular/material/snack-bar';
import { MatDialogRef } from '@angular/material/dialog';

@Component({
  template: `
  <div style="text-align: center;">
  <h1 mat-dialog-title>Confirm</h1><hr>
  <div mat-dialog-content>{{confirmMessage}}</div>
  <div mat-dialog-actions style="justify-content: center;">
    <button mat-button style="color: #fff;background-color: #153961;" 
    (click)="dialogRef.close(true)">Confirm</button>
    <button  mat-button (click)="dialogRef.close(false)">Cancel</button>
  </div>
  </div>
  `,
})
export class DeleteEmpComponent {
  constructor(
    public snackBar: MatSnackBar,
    public dialogRef: MatDialogRef<DeleteEmpComponent>) { }
  confirmMessage: string = "Are you sure you want to delete?";
}

ng g c employee/show-emp
Now, open show-emp.component.html and add the following lines.
<div fxLayout fxLayoutAlign="center center">
    <mat-form-field fxFlex="40%">
        <input matInput type="text" (keyup)="applyFiler($event.target.value)" placeholder="Search">
    </mat-form-field>
    <div style="float: right;">
        <button class="btn btn-success" mat-raised-button (click)="onAdd()">
            Add Employee
        </button>
        <button mat-raised-button class="btn btn-success" (click)="downloadPDF()">Download PDF</button>
        <button mat-raised-button (click)="exportToExcel()" class="btn btn-success">Export To Excel</button>
    </div>
</div>
<div style="overflow: auto;">
    <div class="mat-elevation-z8">
        <div id="pdfTable" #pdfTable>
            <mat-table [dataSource]="listData" matSort>
                <mat-header-row *matHeaderRowDef="displayedColumns"></mat-header-row>
                <mat-row *matRowDef="let row; columns: displayedColumns;"></mat-row>

                <ng-container matColumnDef="EmployeeID">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>EmployeeID</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.EmployeeID}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="EmployeeName">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>EmployeeName</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.EmployeeName}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Department">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>Department</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.Department}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="MailID">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>MailID</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.MailID}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="DOJ">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>DOJ</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.DOJ}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Address">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>Address</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.Address}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Phone">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>Phone</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.Phone}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Salary">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>Salary</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.Salary}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Age">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>Age</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.Age}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Options">
                    <mat-header-cell *matHeaderCellDef>Options</mat-header-cell>
                    <mat-cell *matCellDef="let row">
                        <button mat-icon-button (click)="onEdit(row)">
                            <mat-icon>launch</mat-icon>
                        </button>
                        <button mat-icon-button color="warn" (click)="onDelete(row.EmployeeID)">
                            <mat-icon>delete_outline</mat-icon>
                        </button>
                    </mat-cell>
                </ng-container>
            </mat-table>
        </div>
        <mat-paginator [pageSize]="4" [pageSizeOptions]="[2, 4, 6, 10, 20, 30, 50, 100]">
        </mat-paginator>
    </div>
</div>

Now, open show-emp.component.ts and add the following lines.
import { Component, OnInit, ViewChild, ElementRef } from '@angular/core';
import { EmployeeService } from 'src/app/services/employee.service';
import { MatDialog, MatDialogConfig } from '@angular/material/dialog';
import { MatSnackBar } from '@angular/material/snack-bar';
import { MatTableDataSource } from '@angular/material/table';
import { MatSort } from '@angular/material/sort';
import { AddEmpComponent } from '../add-emp/add-emp.component';
import { EditEmpComponent } from '../edit-emp/edit-emp.component';
import { Employee } from 'src/app/models/employee-model';
import { MatPaginator } from '@angular/material/paginator';
import * as jsPDF from 'jspdf';
import * as xlsx from 'xlsx';
import { SelectionModel } from '@angular/cdk/collections';
import { DeleteEmpComponent } from '../delete-emp/delete-emp.component';

@Component({
  selector: 'app-show-emp',
  templateUrl: './show-emp.component.html',
  styleUrls: ['./show-emp.component.css']
})
export class ShowEmpComponent implements OnInit {

  constructor(private service: EmployeeService,
    private dialog: MatDialog,
    private snackBar: MatSnackBar
  ) {
    this.service.listen().subscribe((m) => {
      console.log(m);
      this.RefreshEmpLsit();
    })
  }

  listData: MatTableDataSource<any>;
  displayedColumns: string[] = ['EmployeeID', 'EmployeeName', 'Department', 'MailID', 'DOJ', 'Address', 'Phone', 'Salary', 'Age', 'Options']
  @ViewChild(MatSort) sort: MatSort;
  @ViewChild(MatPaginator) paginator: MatPaginator;
  @ViewChild('pdfTable', { static: false }) pdfTable: ElementRef;

  ngOnInit(): void {
    this.RefreshEmpLsit();
  }

  RefreshEmpLsit() {
    this.service.getEmpList().subscribe(data => {
      this.listData = new MatTableDataSource(data);
      this.listData.sort = this.sort;
      this.listData.paginator = this.paginator;
      console.log(data);
    });
  }

  applyFiler(filterValue: string) {
    this.listData.filter = filterValue.trim().toLocaleLowerCase();
  }

  onAdd() {
    //debugger;
    const dialogConfig = new MatDialogConfig();
    dialogConfig.disableClose = true;
    dialogConfig.autoFocus = true;
    dialogConfig.width = "70%";
    this.dialog.open(AddEmpComponent, dialogConfig);
  }

  onEdit(emp: Employee) {
    //debugger;
    console.log(emp);
    this.service.formData = emp;
    const dialogConfig = new MatDialogConfig();
    dialogConfig.disableClose = true;
    dialogConfig.autoFocus = true;
    dialogConfig.width = "70%";
    this.dialog.open(EditEmpComponent, dialogConfig);
  }

  onDelete(id: number) {
    console.log(id);
    let dialogRef = this.dialog.open(DeleteEmpComponent, {
      disableClose: true,
      width: '400px',
      height: '200px',
  });

  dialogRef.afterClosed().subscribe(result => {
    if (result) {
      this.service.deleteEmployee(id).subscribe((res) => {
        this.RefreshEmpLsit();
        this.snackBar.open(res.toString(), 'Deleted Sucessfully!', {
          verticalPosition: 'top',
          duration: 3000
        });
      })
    };
});

    // if (confirm('Are you sure want to delete?')) {
      // this.service.deleteEmployee(id).subscribe((res) => {
      //   this.RefreshEmpLsit();
      //   this.snackBar.open(res.toString(), 'Deleted Sucessfully!', {
      //     verticalPosition: 'top',
      //     duration: 3000
      //   });
      // })
    // }
  }

  public downloadPDF(): void {
    const doc = new jsPDF();
    const specialElementHandlers = {
      '#editor': function (element, renderer) {
        return true;
      }
    };
    const pdfTable = this.pdfTable.nativeElement;
    doc.fromHTML(pdfTable.innerHTML, 15, 15, {
      width: 190,
      'elementHandlers': specialElementHandlers
    });
    doc.save('tableToPdf.pdf');
  }

  exportToExcel() {
    const workSheet = xlsx.utils.json_to_sheet(this.listData.data, { header: ['dataprop1', 'dataprop2'] });
    const workBook: xlsx.WorkBook = xlsx.utils.book_new();
    xlsx.utils.book_append_sheet(workBook, workSheet, 'SheetName');
    xlsx.writeFile(workBook, 'filename.xlsx');
  }
}




Now, open show-emp.component.css and add the following lines.
table {
    width: 100%;
    overflow-x: auto;
    overflow-y: hidden;
    min-width: 500px;
}



ng g c department
Now, open department.component.html and add the following lines.
<app-show-dep></app-show-dep>


Now, open department.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';

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

  constructor() { }

  ngOnInit(): void {
  }

}


ng g c department /add-dep
Now, open add-dep.component.html and add the following lines.
<div class="d-flex justify-content-between">
    <h4>Add New Department</h4>
    <button mat-button (click)="onClose()">
        <mat-icon>close</mat-icon>
    </button>
</div>

<div style="overflow: auto; height: 450px;">
    <form #form="ngForm" (submit)="onSubmit(form)" autocomplete="off">
        <div class="mt-4 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Department Name</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="DepartmentName"
                #DepartmentName="ngModel" [(ngModel)]="service.formData.DepartmentName" />
        </div>
        <button class="mt-4" mat-raised-button color="primary" type="submit" [disabled]="form.invalid">
            Add Department
        </button>
    </form>
</div>

Now, open add-dep.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { MatDialogRef } from '@angular/material/dialog';
import { DepartmentService } from 'src/app/services/department.service';
import { NgForm } from '@angular/forms';
import { MatSnackBar } from '@angular/material/snack-bar';

@Component({
  selector: 'app-add-dep',
  templateUrl: './add-dep.component.html',
  styleUrls: ['./add-dep.component.css']
})
export class AddDepComponent implements OnInit {

  constructor(public dialogbox: MatDialogRef<AddDepComponent>,
    public service: DepartmentService,
    private snackBar: MatSnackBar) { }

  ngOnInit(): void {
    this.resetForm();
  }

  resetForm(form?: NgForm) {
    if (form != null)
      form.resetForm();

    this.service.formData = {
      DepartmentID: 0,
      DepartmentName: ''
    }
  }

  onClose() {
    this.dialogbox.close();
    this.service.filter('registert Click');
  }

  onSubmit(form: NgForm) {
    console.log(form.value);
    this.service.addDepartment(form.value).subscribe((res) => {
      this.resetForm();
      this.snackBar.open(res.toString(), 'Added Sucessfully!', {
        verticalPosition: 'top',
        duration: 3000
      });
    })
  }
}



ng g c department /edit-dep
Now, open edit-dep.component.html and add the following lines.
<div class="d-flex justify-content-between m-3">
    <h4>Edit Department</h4>
    <button mat-button (click)="onClose()">
        <mat-icon>close</mat-icon>
    </button>
</div>

<div style="overflow: auto; height: 450px;">
    <form #form="ngForm" (submit)="onSubmit(form)" autocomplete="off">
        <div class="m-3 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Department ID</span>
            </div>
            <input readonly="readonly" type="text" class="form-control" name="DepartmentID" #DepartmentID="ngModel"
                [(ngModel)]="service.formData.DepartmentID" />
        </div>

        <div class="m-3 input-group">
            <div class="input-group-prepend">
                <span class="input-group-text">Department Name</span>
            </div>
            <input required minlength="2" type="text" class="form-control" name="DepartmentName"
                #DepartmentName="ngModel" [(ngModel)]="service.formData.DepartmentName" />
        </div>
        <button class="m-3" mat-raised-button color="primary" type="submit" [disabled]="form.invalid">
            Update Department
        </button>
    </form>
</div>

Now, open edit-dep.component.ts and add the following lines.
import { Component, OnInit } from '@angular/core';
import { MatDialogRef } from '@angular/material/dialog';
import { DepartmentService } from 'src/app/services/department.service';
import { MatSnackBar } from '@angular/material/snack-bar';
import { NgForm } from '@angular/forms';

@Component({
  selector: 'app-edit-dep',
  templateUrl: './edit-dep.component.html',
  styleUrls: ['./edit-dep.component.css']
})
export class EditDepComponent implements OnInit {

  constructor(public dialogbox: MatDialogRef<EditDepComponent>,
    public service: DepartmentService,
    private snackBar: MatSnackBar) { }

  ngOnInit(): void {
  }

  onClose() {
    this.dialogbox.close();
    this.service.filter('registert Click');
  }

  onSubmit(form: NgForm) {
    console.log(form.value);
    this.service.updateDepartment(form.value).subscribe((res) => {
      this.snackBar.open(res.toString(), 'Updated Sucessfully!', {
        verticalPosition: 'top',
        duration: 3000
      });
    })
  }
}



ng g c department /delete-dep
Now, open delete-dep.component.ts and add the following lines.
import { Component, Input } from '@angular/core';
import { MatSnackBar } from '@angular/material/snack-bar';
import { MatDialogRef } from '@angular/material/dialog';

@Component({
  template: `
  <div style="text-align: center;">
  <h1 mat-dialog-title>Confirm</h1><hr>
  <div mat-dialog-content>{{confirmMessage}}</div>
  <div mat-dialog-actions style="justify-content: center;">
    <button mat-button style="color: #fff;background-color: #153961;" 
    (click)="dialogRef.close(true)">Confirm</button>
    <button  mat-button (click)="dialogRef.close(false)">Cancel</button>
  </div>
  </div>
  `,
})
export class DeleteDepComponent {
  constructor(
    public snackBar: MatSnackBar,
    public dialogRef: MatDialogRef<DeleteDepComponent>) { }
  confirmMessage: string = "Are you sure you want to delete?";
}


ng g c department /show-dep
Now, open show-dep.component.html and add the following lines.
<div fxLayout fxLayoutAlign="center center">
    <mat-form-field fxFlex="40%">
        <input matInput type="text" (keyup)="applyFiler($event.target.value)" placeholder="Search">
    </mat-form-field>
    <div style="float: right;">
        <button class="btn btn-success" mat-raised-button (click)="onAdd()">
            Add Department
        </button>
        <button mat-raised-button class="btn btn-success" (click)="downloadPDF()">Download PDF</button>
        <button mat-raised-button (click)="exportToExcel()" class="btn btn-success">Export To Excel</button>
    </div>
</div>
<div style="overflow: auto;">
    <div class="mat-elevation-z8">
        <div id="pdfTable" #pdfTable>
            <mat-table [dataSource]="listData" matSort>
                <mat-header-row *matHeaderRowDef="displayedColumns"></mat-header-row>
                <mat-row *matRowDef="let row; columns: displayedColumns;"></mat-row>

                <ng-container matColumnDef="DepartmentID">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>DepartmentID</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.DepartmentID}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="DepartmentName">
                    <mat-header-cell *matHeaderCellDef mat-sort-header>DepartmentName</mat-header-cell>
                    <mat-header-cell *matCellDef="let element">{{element.DepartmentName}}</mat-header-cell>
                </ng-container>

                <ng-container matColumnDef="Options">
                    <mat-header-cell *matHeaderCellDef>Options</mat-header-cell>
                    <mat-cell *matCellDef="let row">
                        <button mat-icon-button (click)="onEdit(row)">
                            <mat-icon>launch</mat-icon>
                        </button>
                        <button mat-icon-button color="warn" (click)="onDelete(row.DepartmentID)">
                            <mat-icon>delete_outline</mat-icon>
                        </button>
                    </mat-cell>
                </ng-container>
            </mat-table>
        </div>
        <mat-paginator [pageSize]="4" [pageSizeOptions]="[2, 4, 6, 10, 20]">
        </mat-paginator>
    </div>
</div>

Now, open show-dep.component.ts and add the following lines.
import { Component, OnInit, ViewChild, ElementRef } from '@angular/core';
import { MatTableDataSource } from '@angular/material/table';
import { Department } from 'src/app/models/department-model';
import { DepartmentService } from 'src/app/services/department.service';
import { MatSort } from '@angular/material/sort';
import { MatDialog, MatDialogConfig } from '@angular/material/dialog';
import { AddDepComponent } from '../add-dep/add-dep.component';
import { MatSnackBar } from '@angular/material/snack-bar';
import { EditDepComponent } from '../edit-dep/edit-dep.component';
import { MatPaginator } from '@angular/material/paginator';
import * as jsPDF from 'jspdf';
import * as xlsx from 'xlsx';
import { DeleteDepComponent } from '../delete-dep/delete-dep.component.ts';

@Component({
  selector: 'app-show-dep',
  templateUrl: './show-dep.component.html',
  styleUrls: ['./show-dep.component.css']
})
export class ShowDepComponent implements OnInit {

  constructor(private service: DepartmentService,
    private dialog: MatDialog,
    private snackBar: MatSnackBar
  ) {
    this.service.listen().subscribe((m) => {
      console.log(m);
      this.RefreshDepLsit();
    })
  }

  listData: MatTableDataSource<any>;
  displayedColumns: string[] = ['DepartmentID', 'DepartmentName', 'Options']
  @ViewChild(MatSort) sort: MatSort
  @ViewChild(MatPaginator) paginator: MatPaginator;
  @ViewChild('pdfTable', { static: false }) pdfTable: ElementRef;

  ngOnInit(): void {
    this.RefreshDepLsit();
  }

  RefreshDepLsit() {
    this.service.getDepList().subscribe(data => {
      this.listData = new MatTableDataSource(data);
      this.listData.sort = this.sort;
      this.listData.paginator = this.paginator;
    });
  }

  applyFiler(filterValue: string) {
    this.listData.filter = filterValue.trim().toLocaleLowerCase();
  }

  onAdd() {
    const dialogConfig = new MatDialogConfig();
    dialogConfig.disableClose = true;
    dialogConfig.autoFocus = true;
    dialogConfig.width = "70%";
    this.dialog.open(AddDepComponent, dialogConfig);
  }

  onEdit(dep: Department) {
    console.log(dep);
    this.service.formData = dep;
    const dialogConfig = new MatDialogConfig();
    dialogConfig.disableClose = true;
    dialogConfig.autoFocus = true;
    dialogConfig.width = "70%";
    this.dialog.open(EditDepComponent, dialogConfig);
  }

  onDelete(id: number) {
    console.log(id);
    let dialogRef = this.dialog.open(DeleteDepComponent, {
      disableClose: true,
      width: '400px',
      height: '200px',
  });

  dialogRef.afterClosed().subscribe(result => {
    if (result) {
      this.service.deleteDepartment(id).subscribe((res) => {
        this.RefreshDepLsit();
        this.snackBar.open(res.toString(), 'Deleted Sucessfully!', {
          verticalPosition: 'top',
          duration: 3000
        });
      })
    };
});

    // console.log(id);
    // if (confirm('Are you sure want to delete?')) {
    //   this.service.deleteDepartment(id).subscribe((res) => {
    //     this.RefreshDepLsit();
    //     this.snackBar.open(res.toString(), 'Deleted Sucessfully!', {
    //       verticalPosition: 'top',
    //       duration: 3000
    //     });
    //   })
    // }
  }

  public downloadPDF(): void {
    const doc = new jsPDF();
    const specialElementHandlers = {
      '#editor': function (element, renderer) {
        return true;
      }
    };
    const pdfTable = this.pdfTable.nativeElement;
    doc.fromHTML(pdfTable.innerHTML, 15, 15, {
      width: 190,
      'elementHandlers': specialElementHandlers
    });
    doc.save('tableToPdf.pdf');
  }

  exportToExcel() {
    const workSheet = xlsx.utils.json_to_sheet(this.listData.data, { header: ['dataprop1', 'dataprop2'] });
    const workBook: xlsx.WorkBook = xlsx.utils.book_new();
    xlsx.utils.book_append_sheet(workBook, workSheet, 'SheetName');
    xlsx.writeFile(workBook, 'filename.xlsx');
  }
}


Now, open show-dep.component.css and add the following lines.

table {
    width: 100%;
    overflow-x: auto;
    overflow-y: hidden;
    min-width: 500px;
}



ng g s login
Now, open login.service.ts and first import necessary class and libraries and then make calls to the WebAPI methods.
import { Injectable } from '@angular/core';  
import {HttpClient} from '@angular/common/http';  
import {HttpHeaders} from '@angular/common/http';  
import { from, Observable } from 'rxjs'; 
import { Register } from '../models/register';

@Injectable({  
  providedIn: 'root'  
})  
export class LoginService {  
  Url :string;  
  token : string;  
  header : any;  
  constructor(private http : HttpClient) {   
    this.Url = 'http://localhost:55075/api/Login'; 
    const headerSettings: {[name: string]: string | string[]; } = {};  
    this.header = new HttpHeaders(headerSettings);  
  }  

  Login(model : any){  
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json' }) };  
   return this.http.post<any>(this.Url+'/UserLogin',model,{ headers: this.header});  
  }  

   CreateUser(register:Register)  {  
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json' }) };  
    return this.http.post<Register[]>(this.Url + '/UserRegistration', register, 
httpOptions)  
   }  
}  

ng g s department
Now, open department.service.ts and first import necessary class and libraries and then make calls to the WebAPI methods.
import { Injectable } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { Department } from '../models/department-model';
import { HttpClient, HttpHeaders } from '@angular/common/http';

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

  formData: Department;
  constructor(private http:HttpClient) { }

  readonly APIUrl = 'http://localhost:55075/api/Department';

  getDepList(): Observable<Department[]> {
    return this.http.get<Department[]>(this.APIUrl + '/AllDepartments');
  }

  getSingleDepList(id: number): Observable<Department[]> {
    return this.http.get<Department[]>(this.APIUrl + '/GetDepartmentsById' + id);
  }

  addDepartment(dep:Department){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.post(this.APIUrl+'/InsertDepartments', dep, httpOptions);
  }

  deleteDepartment(id: number){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.delete(this.APIUrl+'/DeleteDepartments?id='+id, httpOptions);
  }



  updateDepartment(dep:Department){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.put(this.APIUrl+'/UpdateDepartments', dep, httpOptions);
  }

  private _listener = new Subject<any>();
  listen(): Observable<any>{
    return this._listener.asObservable();
  }

  filter(filterBy: string){
    this._listener.next(filterBy);
  }
}



ng g s employee
Now, open employee.service.ts and first import necessary class and libraries and then make calls to the WebAPI methods.
import { Injectable } from '@angular/core';
import { Employee } from '../models/employee-model';
import { HttpClient, HttpHeaders } from '@angular/common/http';
import { Observable, Subject } from 'rxjs';
import { Department } from '../models/department-model';

@Injectable({
  providedIn: 'root'
})
export class EmployeeService {
  
  formData: Employee;
  constructor(private http:HttpClient) { }

  readonly APIUrl = 'http://localhost:55075/api/Employee';

  getEmpList(): Observable<Employee[]> {
    return this.http.get<Employee[]>(this.APIUrl + '/AllEmployees');
  }

  getSingleEmpList(id: number): Observable<Employee[]>{
    return this.http.get<Employee[]>(this.APIUrl + '/GetEmployeesById/' + id) 
  }

  addEmployee(emp:Employee){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.post(this.APIUrl+'/InsertEmployees', emp, httpOptions);
  }

  updateEmployee(emp:Employee){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.put(this.APIUrl+'/UpdateEmployees', emp,httpOptions);
  }

  deleteEmployee(id: number){
    const httpOptions = { headers: new HttpHeaders({ 'Content-Type': 'application/json'}) };  
    return this.http.delete(this.APIUrl+'/DeleteEmployees?id='+ id, httpOptions);
  }
 
  getDepDropDownValues(){
    return this.http.get<Department[]>(this.APIUrl+'/Department');
  }
  
  private _listener = new Subject<any>();
  listen(): Observable<any>{
    return this._listener.asObservable();
  }

  filter(filterBy: string){
    this._listener.next(filterBy);
  }
}


ng g class Register
Now, write all properties of the Register class related to an register that matches with the database.
export class Register {  
    UserName:string;  
    LoginName:string;  
    Password:string;  
    Email:string;  
    ContactNo:string;  
    Address:string;
    Status: string;  
    // IsApproved: string;
}  

ng g class Department
Now, write all properties of the Department class related to an department that matches with the database.
export class Department {
    DepartmentID: number;
    DepartmentName: string;
}

ng g class Employee
Now, write all properties of the Employee class related to an employee that matches with the database.
export class Employee {
    EmployeeID: number;
    EmployeeName: string;
    Department: string;
    MailID: string;
    DOJ: Date;
    Salary: number;
    Age: number;
    Address: string;
    Phone: number;
}

app-routing.module.ts
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { DashboardComponent } from './dashboard/dashboard.component';
import { LoginComponent } from './login/login.component';
import { RegisterComponent } from './register/register.component';
import { DepartmentComponent } from './department/department.component';
import { EmployeeComponent } from './employee/employee.component';

export const routes: Routes = [
  {
    path: '',
    redirectTo: 'login',
    pathMatch: 'full',
  },
  {
    path: 'login',
    component: LoginComponent,
    data: {
      title: 'Login Page'
    }
  },
  {
    path: 'register',
    component: RegisterComponent,
    data: {
      title: 'Register Page'
    }
  },
  {
    path: 'Dashboard',
    component: DashboardComponent,
    data: {
      title: 'Dashboard Page'
    },
    children: [
      {
        path: 'employee',
        component: EmployeeComponent,
        data: {
          title: 'Employee Page'
        },
     },
     {
      path: 'department',
      component: DepartmentComponent,
      data: {
        title: 'Department Page'
      },
     },
 ]
  },
];

@NgModule({
  imports: [RouterModule.forRoot(routes),  RouterModule.forChild(routes)],
  exports: [RouterModule]
})
export class AppRoutingModule { }    

app.component.html
<div class="container">
  <router-outlet></router-outlet>
</div>

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

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


app.module.ts

import { NgModule } from '@angular/core';
import { RouterModule } from '@angular/router';
import { HttpClientModule } from '@angular/common/http';
import { FormsModule, ReactiveFormsModule } from '@angular/forms';
import { BrowserModule } from '@angular/platform-browser';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { CommonModule } from '@angular/common';

import { LoginService } from './services/login.service';
import { DepartmentService } from './services/department.service';
import { EmployeeService } from './services/employee.service';

import { MatButtonModule } from  '@angular/material/button';
import { MatMenuModule } from  '@angular/material/menu';
import { MatDatepickerModule } from  '@angular/material/datepicker';
import { MatIconModule } from  '@angular/material/icon';
import { MatCardModule } from  '@angular/material/card';
import { MatSidenavModule } from  '@angular/material/sidenav';
import { MatFormFieldModule } from  '@angular/material/form-field';
import { MatInputModule } from  '@angular/material/input';
import { MatTooltipModule } from  '@angular/material/tooltip';
import { MatToolbarModule } from  '@angular/material/toolbar';
import { MatNativeDateModule } from '@angular/material/core';
import { MatRadioModule } from '@angular/material/radio';  
import { MatTableModule } from '@angular/material/table';
import { MatSortModule } from '@angular/material/sort';
import { MatDialogModule } from '@angular/material/dialog';
import { MatSnackBarModule } from '@angular/material/snack-bar';
import { MatPaginatorModule } from '@angular/material/paginator';

import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { LoginComponent } from './login/login.component';
import { RegisterComponent } from './register/register.component';
import { DashboardComponent } from './dashboard/dashboard.component';
import { EmployeeComponent } from './employee/employee.component';
import { DepartmentComponent } from './department/department.component';
import { ShowEmpComponent } from './employee/show-emp/show-emp.component';
import { EditEmpComponent } from './employee/edit-emp/edit-emp.component';
import { AddEmpComponent } from './employee/add-emp/add-emp.component';
import { ShowDepComponent } from './department/show-dep/show-dep.component';
import { EditDepComponent } from './department/edit-dep/edit-dep.component';
import { AddDepComponent } from './department/add-dep/add-dep.component';
import { DeleteEmpComponent } from './employee/delete-emp/delete-emp.component';
import { DeleteDepComponent } from './department/delete-dep/delete-dep.component.ts';

@NgModule({
  declarations: [
    AppComponent,
    LoginComponent,
    RegisterComponent,
    DashboardComponent,
    EmployeeComponent,
    DepartmentComponent,
    ShowEmpComponent,
    EditEmpComponent,
    AddEmpComponent,
    ShowDepComponent,
    EditDepComponent,
    AddDepComponent,
    DeleteEmpComponent,
    DeleteDepComponent
  ],
  imports: [
    BrowserModule,  
    AppRoutingModule,
    FormsModule,  
    CommonModule, 
    RouterModule,
    ReactiveFormsModule,  
    HttpClientModule,  
    BrowserAnimationsModule,  
    MatButtonModule,  
    MatMenuModule,  
    MatDatepickerModule,  
    MatNativeDateModule,  
    MatIconModule,  
    MatRadioModule,  
    MatCardModule,  
    MatSidenavModule,  
    MatFormFieldModule, 
    MatTableModule, 
    MatSortModule,
    MatPaginatorModule,
    MatDialogModule,
    MatSnackBarModule, 
    MatInputModule,  
    MatTooltipModule,  
    MatToolbarModule,  
    
  ],
  providers: [AppRoutingModule, LoginService, EmployeeService, DepartmentService],
  bootstrap: [AppComponent],
  entryComponents: [AddDepComponent,EditDepComponent,DeleteDepComponent, DeleteEmpComponent, AddEmpComponent, EditEmpComponent],
})
export class AppModule { }


index.html

<!doctype html>
<html lang="en">

<head>
  <meta charset="utf-8">
  <title>Home</title>
  <base href="/">
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <link rel="icon" type="image/x-icon" href="favicon.ico">
  <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css"
    integrity="sha384-Gn5384xqQ1aoWXA+058RXPxPg6fy4IWvTNh0E263XmFcJlSAwiGgFAW/dAiS6JXm" crossorigin="anonymous">
  <link href="https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap" rel="stylesheet">
  <link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">

</head>

<body class="mat-typography">
  <app-root></app-root>
  <script src="https://code.jquery.com/jquery-3.2.1.slim.min.js"
    integrity="sha384-KJ3o2DKtIkvYIK3UENzmM7KCkRr/rE9/Qpg6aAZGJwFDMVNA/GpGFF93hXpG5KkN"
    crossorigin="anonymous"></script>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js"
    integrity="sha384-ApNbgh9B+Y1QKtv3Rn7W3mgPxhU9K/ScQsAP7hUibX39j7fakFPskvXusvfa0b4Q"
    crossorigin="anonymous"></script>
  <script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"
    integrity="sha384-JZR6Spejh4U02d8jOt6vLEHfe/JQGiRRSQQxSfFWpi1MquVdAyjUar5+76PVCmYl"
    crossorigin="anonymous"></script>
</body>

</html>


Once created, the project should look like this.

 

We have completed all needed code functionality for our Login and  CRUD operations using ASP.NET Web API.Before running the application, first, make sure to save your hard work.
Now, let's run the app and see how it works. 
Open TERMINAL and write the following command to run the program.

ng serve -open
The output looks like the following image. It's a stunning UI created with CRUD operations. 
Congratulations!
 






You've finished a completed Login and ASP.NET Web API with CRUD functionality. The App uses a Web API to provide data access from a MS SQL Server. 
Thank you for reading this article.

Summary
In this article, we have discussed the process of Login and CRUD operations in ASP.NET Web API using Angular 9 Web application.

Reference: 
2.) Project Link:  https://github.com/Ukmandal/Employee-Management-Portial
1.) https://dzone.com/articles/login-and-registration-aspnet-web-api-using-angula

0 Comments: