preamble
Our main focus in this chapter is to refine the writing and interface interfacing of the Blazor student management page.
NET 8 operation SQLite Getting Started to practice detailed tutorials
- Day 1 Introduction to SQLite
- Day 2 Configuring the SQLite Environment on Windows
- Day 3 SQLite Quick Start
- Day 4 EasySQLite front-end and back-end project framework construction
- Day 5 introduces SQLite-net ORM and encapsulates common methods.
- Day 6 back-end class management related interface refinement and Swagger customization configuration
- Day 7 BootstrapBlazor UI component library introduction (1)
- Day 7 Blazor class management page writing and interface interfacing (2)
- Day 7 Blazor student management page writing and interface interfacing (3)
EasySQLite project source code address
- GitHub address:/YSGStudyHards/EasySQLite
Blazor Introduction and Quick Start
If you are not familiar with Blazor, you can read this article first to get a general idea.
A Comprehensive Introduction and Quick Start to Core Blazor
Front-end Table page and interface docking code
Mainly common Table data display, data addition, data deletion, data modification and other operations.
@page "/Student"
@using Entity
@using
@using
@using Utility
@using
@using
@inject HttpClient _httpClient;
@inject DataLoaderService _dataLoader;
<Table TItem="StudentViewModel"
AutoGenerateColumns="true"
ShowToolbar="true"
IsMultipleSelect="true"
OnSaveAsync="@OnSaveAsync"
OnQueryAsync="@OnQueryAsync"
OnDeleteAsync="@OnDeleteAsync"
IsStriped="true"
IsBordered="true"
ShowSearch="true"
IsPagination="true"
ShowSearchText="true">
<! --Customize the edit popup by setting EditTemplate, if properties need to be linked they must be encapsulated into a separate component like in this example before placing it into the template -->.
<EditTemplate>
<StudentEditor @bind-Value="context" />
</EditTemplate>
<SearchTemplate>
<GroupBox Title="Search Criteria">
<div class="row g-3 form-inline">
<div class="col-12 col-sm-6">
<BootstrapInput @bind-Value="@" PlaceHolder="Please enter student's name" maxlength="50" ShowLabel="true" DisplayText="Name" />
</div>
</div>
</GroupBox>
</SearchTemplate>
</Table>
@code {
/// <summary>
/// Data queries
/// </summary>
/// <param name="options">options</param>
/// <returns></returns>
private async Task<QueryData<StudentViewModel>> OnQueryAsync(QueryPageOptions options)
{
var searchModel = as StudentViewModel;
var getStudentData = new List<StudentViewModel>();
var getResults = await _httpClient.GetFromJsonAsync<ApiResponse<List<StudentViewModel>>>("api/Student/GetAllStudent").ConfigureAwait(false);
if ()
{
// Fuzzy filtering of data
if (!())
{
getStudentData = (x => ()).ToList();
}
else if (searchModel != null && !())
{
getStudentData = (x => ()).ToList();
}
else
{
getStudentData = ();
}
}
//Load class information
await _dataLoader.LoadSchoolClassDataAsync().ConfigureAwait(false);
// Memory paging
return await (new QueryData<StudentViewModel>()
{
Items = (( - 1) * ).Take().ToList(),
TotalCount = ()
});
}
/// <summary>
/// Simulate data addition and modification operations
/// </summary>
/// <param name="studentInfo">studentInfo</param>
/// <param name="changedType">changedType</param>
/// <returns></returns>
public async Task<bool> OnSaveAsync(StudentViewModel studentInfo, ItemChangedType changedType)
{
if (() == "Update")
{
var addResult = await _httpClient.PutAsJsonAsync($"api/Student/UpdateStudent/{}", studentInfo).ConfigureAwait(false);
if ((addResult))
{
return await (true);
}
else
{
return await (false);
}
}
else if (() == "Add")
{
var addResult = await _httpClient.PostAsJsonAsync("api/Student/CreateStudent", studentInfo).ConfigureAwait(false);
if ((addResult))
{
return await (true);
}
else
{
return await (false);
}
}
return await (true);
}
/// <summary>
/// Data deletion
/// </summary>
/// <param name="items">items</param>
/// <returns></returns>
private async Task<bool> OnDeleteAsync(IEnumerable<StudentViewModel> items)
{
var deleteSuccessNum = 0;
var StudentViewModelList = ();
foreach (var item in StudentViewModelList)
{
var delResult = await _httpClient.DeleteAsync($"api/Student/DeleteStudent/{}").ConfigureAwait(false);
if ((delResult))
{
deleteSuccessNum++;
}
}
if (deleteSuccessNum > 0)
{
return await (true);
}
else
{
return await (false);
}
}
}
Custom Edit Popup Templates
:
@using Entity
@using
@using
@inject HttpClient _httpClient;
@inject DataLoaderService _dataLoader;
@inject IMemoryCache _memoryCache;
<div class="row g-3 form-inline">
<div class="col-12">
<BootstrapInput @bind-Value="@" IsDisabled maxlength="50" />
</div>
<div class="col-12">
<Select @bind-Value="@" OnSelectedItemChanged="OnSelectedItemChanged" Items="Items" />
</div>
<div class="col-12">
<BootstrapInput @bind-Value="@" placeholder="Please enter a student name" maxlength="50" required />
</div>
<div class="col-12">
<Select @bind-Value="@" Items="GenderItems" required />
</div>
<div class="col-12">
<BootstrapInput @bind-Value="@" placeholder="Please enter an age" maxlength="50" />
</div>
</div>
:
using System;
using ;
using ;
using ;
using ;
using ;
using Entity;
using ;
using ;
using ;
using ;
using ;
namespace
{
public partial class StudentEditor
{
[Parameter]
public StudentViewModel Value { get; set; }
[Parameter]
public EventCallback<StudentViewModel> ValueChanged { get; set; }
[NotNull]
private List<SelectedItem>? Items { get; set; }
[NotNull]
private List<SelectedItem>? GenderItems { get; set; }
protected override async void OnInitialized()
{
();
List<SchoolClass>? getSchoolClass;
if (_memoryCache.TryGetValue("SchoolClassData", out string data))
{
getSchoolClass = <List<SchoolClass>>(data);
}
else
{
getSchoolClass = await _dataLoader.LoadSchoolClassDataAsync().ConfigureAwait(false);
}
Items = [];
foreach (var item in (x => ).ToList())
{
(new SelectedItem { Value = (), Text = });
}
if (())
{
= ().Text;
= Convert.ToInt32(().Value);
}
GenderItems = [new SelectedItem { Value = "male", Text = "male" }, new SelectedItem { Value = "women", Text = "women" }];
if (())
{
= ().Text;
}
}
/// <summary>
/// Triggered when a dropdown box option is changed.
/// </summary>
/// <param name="item">item</param>
/// <returns></returns>
async Task OnSelectedItemChanged(SelectedItem item)
{
await (1);
= Convert.ToInt32();
}
}
}
back-end API interface
using AutoMapper;
using Entity;
using ;
using ;
using Utility;
namespace
{
/// <summary>
/// Student Management
/// </summary>
[ApiController]
[Route("api/[controller]/[action]")]
public class StudentController : ControllerBase
{
private readonly IMapper _mapper;
private readonly SQLiteAsyncHelper<Student> _studentHelper;
private readonly SQLiteAsyncHelper<SchoolClass> _schoolClassHelper;
/// <summary>
/// Dependency Injection
/// </summary>
/// <param name="mapper">mapper</param>
/// <param name="studentHelper">studentHelper</param>
/// <param name="schoolClassHelper">schoolClassHelper</param>
public StudentController(IMapper mapper, SQLiteAsyncHelper<Student> studentHelper, SQLiteAsyncHelper<SchoolClass> schoolClassHelper)
{
_mapper = mapper;
_studentHelper = studentHelper;
_schoolClassHelper = schoolClassHelper;
}
/// <summary>
/// Create a new student record
/// </summary>
/// <param name="student"> added student information </param>
/// <returns></returns>
[HttpPost]
public async Task<ApiResponse<int>> CreateStudent([FromBody] Student student)
{
var response = new ApiResponse<int>();
try
{
var insertNumbers = await _studentHelper.InsertAsync(student).ConfigureAwait(false);
if (insertNumbers > 0)
{
= true;
= "Added successfully".
}
else
{
= false;
= "Insertion failed".
}
}
catch (Exception ex)
{
= false;
= ;
}
return response;
}
/// <summary>
/// Query all student records
/// </summary>
/// <returns></returns>
[HttpGet]
public async Task<ApiResponse<List<StudentViewModel>>> GetAllStudent()
{
var response = new ApiResponse<List<StudentViewModel>>();
try
{
var students = await _studentHelper.QueryAllAsync().ConfigureAwait(false);
var studentsListDto = await GetStudentClassInfo(students).ConfigureAwait(false);
= true;
= studentsListDto ?? new List<StudentViewModel>();
}
catch (Exception ex)
{
= false;
= ;
}
return response;
}
private async Task<List<StudentViewModel>?> GetStudentClassInfo(List<Student> students)
{
var studentsListDto = _mapper.Map<List<StudentViewModel>>(students);
if (studentsListDto?.Count > 0)
{
var classIDs = (x => ).Distinct().ToList();
var querySchoolClassList = await _schoolClassHelper.QueryAsync(x => ()).ConfigureAwait(false);
if (querySchoolClassList?.Count > 0)
{
foreach (var studentItem in studentsListDto)
{
var getClassInfo = (x => == );
if (getClassInfo != null)
{
= ;
}
}
}
}
return studentsListDto;
}
/// <summary>
/// Query student information by student ID
/// </summary>
/// <param name="studentID"> studentID</param>
/// <returns></returns>
[HttpGet("{studentID}")]
public async Task<ApiResponse<StudentViewModel>> GetStudentById(int studentID)
{
var response = new ApiResponse<StudentViewModel>();
try
{
var student = await _studentHelper
.QuerySingleAsync(x => == studentID)
.ConfigureAwait(false);
if (student != null)
{
var studentsDto = await GetStudentClassInfo(new List<Student> { student }).ConfigureAwait(false);
= true;
= ();
}
else
{
= false;
= "No student information found".
}
}
catch (Exception ex)
{
= false;
= ;
}
return response;
}
/// <summary>
/// Updating Student Records
/// </summary>
/// <param name="studentID"> studentID</param>
/// <param name="editstudent"> Updated student information </param>
/// <returns></returns>
[HttpPut("{studentID}")]
public async Task<ApiResponse<int>> UpdateStudent(
int studentID,
[FromBody] Student editstudent
)
{
var response = new ApiResponse<int>();
try
{
var student = await _studentHelper
.QuerySingleAsync(x => == studentID)
.ConfigureAwait(false);
if (student != null)
{
= ;
= ;
= ;
= ;
int updateResult = await _studentHelper
.UpdateAsync(student)
.ConfigureAwait(false);
if (updateResult > 0)
{
= true;
= "Student information updated successfully".
}
else
{
= false;
= "Failed to update student information".
}
}
else
{
= false;
= "No student information found".
}
}
catch (Exception ex)
{
= false;
= ;
}
return response;
}
/// <summary>
/// Delete Student Record
/// </summary>
/// <param name="studentID"> studentID</param>
/// <returns></returns>
[HttpDelete("{studentID}")]
public async Task<ApiResponse<int>> DeleteStudent(int studentID)
{
var response = new ApiResponse<int>();
try
{
int deleteResult = await _studentHelper
.DeleteAsync(studentID)
.ConfigureAwait(false);
if (deleteResult > 0)
{
= true;
= "Deleted successfully".
}
else
{
= false;
= "No student information found".
}
}
catch (Exception ex)
{
= false;
= ;
}
return response;
}
}
}