Sunday, July 30, 2023

ASP.NET Core - Example of CRUD operations in a Single Razor Page

In previous post, we have seen that CRUD operations can be performed by using separate razor pages for each CRUD operation like Create, Delete etc. In this post, we will perform all CRUD operations on a single Razor page called Index in this project. The project folders structure after creating the project will be as shown below.


Project
  • Open the Visual Studio. 
  • Create web project using ASP.NET Core Empty template.
  • Project name: RPExercises
  • Solution name: RPExercises
  • .NET Core version: 5.0
  • Add the AddRazorPages() into the IServiceCollection in Startup class.
  • Use MapRazorPages() as terminal middleware in Startup class.
Look at the below updated code in Startup class.
Startup.cs

using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

namespace CascadingDropdownsRP
{
    public class Startup
    {
        // This method gets called by the runtime. Use this method to add services to the container.
        // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddRazorPages();
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }

            app.UseRouting();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapRazorPages();
            });
        }
    }
}
  • Add a new folder and rename it Pages.
  • Add a Razor Page in Pages folder and name it Index. Two files are generated which are Index.cshtml and Index.cshtml.cs
  • Add a folder and rename it Models.
  • In Models folder, create a model class called Student.
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace RPExercises.Models
{
    public class Student
    {
        [Key]
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public int Id { get; set; }
        [Required]
        [MinLength(1)]
        [MaxLength(20)]
        public string Name { get; set; }
        public bool IsPassed { get; set; }
        [Required]
        public Qualification Degree { get; set; }
    }
    public enum Qualification
    {
        BA, MA, BCA, MCA
    }
} 
Install the EF Core packages by running the following commands.
  • Install-Package Microsoft.EntityFrameworkCore -version 5.0
  • Install-Package Microsoft.EntityFrameworkCore.Design -version 5.0
  • Install-Package Microsoft.EntityFrameworkCore.Tools -version 5.0
  • Install-Package Microsoft.EntityFrameworkCore.SqlServer -version 5.0

Add a folder and rename it Data. In this folder, add AppDbContext class as given below.

using Microsoft.EntityFrameworkCore;
using RPExercises.Models;

namespace RPExercises.Data
{
    public class AppDbContext: DbContext
    {
        public AppDbContext(DbContextOptions<AppDbContext> options)
       : base(options)
        {
        }
        public DbSet<Student> tblStudents { get; set; }
    }
}
Add Connection String in appsettings.json file.

{
  "Logging": {
    "LogLevel": {
      "Default": "Information",
      "Microsoft": "Warning",
      "Microsoft.Hosting.Lifetime": "Information"
    }
  },
  "ConnectionStrings": {
    "DBCS": "Data Source=(localdb)\\MSSQLLocalDB;Initial Catalog=Appliedk11;Integrated Security=True;Connect Timeout=30;Encrypt=False;Trust Server Certificate=False;Application Intent=ReadWrite;Multi Subnet Failover=False"
  },
  "AllowedHosts": "*"
}

Next step. Update the Startup class to add DbContext service with SQLServer database. .

public void ConfigureServices(IServiceCollection services)
        {
            services.AddRazorPages();
            services.AddDbContext<AppDbContext>(options =>
            {
                options.UseSqlServer(_cfg.GetConnectionString("DBCS"));
            });
        }
Perform Add-Migration and Update-Database commands in Package Manager Console.

Now update the Index.cshtml file.

@page "{handler?}"
@using RPExercises.Models;
@model RPExercises.Pages.IndexModel
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers

<h2>Create students</h2>
<style type="text/css">
    body {
        margin-left: 8%;
    }

    .myclass {
        padding: 5px;
        border: 2px solid blue;
        background-color: beige;
        width: 30%;
        text-align: left;
    }
</style>
<form method="post" class="myclass">
    <h3> Input student details</h3>
    <label hidden asp-for="student.Id">Id</label>
    <input hidden asp-for="student.Id"  />
    <label asp-for="student.Name" >Name</label>
    <input asp-for="student.Name"  />
    <br />
    <label asp-for="student.IsPassed">IsPassed</label>
    <input asp-for="student.IsPassed"  />
    <br />
    <label asp-for="student.Degree">Highest Degree</label>
    BA<input type="radio" asp-for="student.Degree" value="@Qualification.BA" />
    MA<input type="radio" asp-for="student.Degree" value="@Qualification.MA" />
    BCA<input type="radio" asp-for="student.Degree" value="@Qualification.BCA" />
    MCA<input type="radio" asp-for="student.Degree" value="@Qualification.MCA" />
    <br />
    <br />
    <input type="submit" value="@ViewData["btnLabel"]" style="background-color:green;color:wheat;margin-left:80%" />
</form>

<br />
<hr />
<h2>List students</h2>
Students Count: @Model.students.Count 
<br/>
<table border="1" class="myclass">
    <tr>
        <th>Id</th>
        <th>Name</th>
        <th>Is Passed</th>
        <th>Degree</th>
        <th>Action</th>
    </tr>

    @foreach (Student s in Model.students)
    {
        <tr>
            <td>@s.Id</td>
            <td>@s.Name</td>
            <td>@s.IsPassed</td>
            <td>@s.Degree</td>
            <td>
                <a asp-page-handler="Edit" asp-route-id="@s.Id">Edit</a>|
                <a asp-page-handler="Delete" asp-route-id="@s.Id">Delete</a>
            </td>
        </tr>
    }
</table>
Update the Index.cshtml.cs file.

using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.EntityFrameworkCore;
using RPExercises.Data;
using RPExercises.Models;
using System.Collections.Generic;
using System.Threading.Tasks;

namespace RPExercises.Pages
{
    public class IndexModel : PageModel
    {
        [BindProperty]
        public Student student { get; set; }
        public List<Student> students { get; set; } = new List<Student>();
        private readonly AppDbContext ctx;

        public IndexModel(AppDbContext ctx)
        {
            this.ctx = ctx;
        }
        public async Task<IActionResult> OnGet()
        {
            students = await ctx.tblStudents.ToListAsync();
            ViewData["btnLabel"] = "Create";
            return Page();
        }

        public async Task<IActionResult> OnPost()
        {
            if (student.Id==0)
            {
                await ctx.tblStudents.AddAsync(student);
                await ctx.SaveChangesAsync();
                
            }
            else
            {
                Student studentEdit = await ctx.tblStudents.FindAsync(student.Id);
               
                if (HttpContext.Request.Path.Value.ToLower().Contains("edit"))
                {
                    studentEdit.Id = student.Id;
                    studentEdit.Name = student.Name;
                    studentEdit.IsPassed = student.IsPassed;
                    studentEdit.Degree = student.Degree;
                    ctx.Entry(studentEdit).State = EntityState.Modified;
                }
                if (HttpContext.Request.Path.Value.ToLower().Contains("delete"))
                {
                    ctx.Entry(studentEdit).State = EntityState.Deleted;
                }
                    ctx.SaveChanges();

            }
            return RedirectToPage();
        }

        public async Task<IActionResult> OnGetEdit(int id)
        {
            // get data from table
            Student studentEdit = await ctx.tblStudents.FindAsync(id);
            // update form by updating BindProperty
            student = studentEdit;
            students = await ctx.tblStudents.ToListAsync();
            ViewData["btnLabel"] = "Edit";
            return Page();
        }

        public async Task<IActionResult> OnGetDelete(int id)
        {
            // get data from table
            Student studentDelete = await ctx.tblStudents.FindAsync(id);
            // update form by updating BindProperty
            student = studentDelete;
            students = await ctx.tblStudents.ToListAsync();
            ViewData["btnLabel"] = "Delete";
            return Page();
        }
    }
}
Run the application and do CRUD operations. We get the following output.

No comments:

Post a Comment

Hot Topics