Продолжим работу с проектом из прошлой темы и добавим в него функционал по редактированию и удалению данных. Итак, добавим в папку Pages новую страницу Razor Edit.cshtml, которая будет предназначена для редактирования данных.
Вначале изменим файл связанного кода Edit.cshtml.cs:
using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using RazorPagesApp.Models; namespace RazorPagesApp.Pages { [IgnoreAntiforgeryToken] public class EditModel : PageModel { ApplicationContext context; [BindProperty] public User? Person { get; set; } public EditModel(ApplicationContext db) { context = db; } public async Task<IActionResult> OnGetAsync(int id) { Person = await context.Users.FindAsync(id); if (Person == null) return NotFound(); return Page(); } public async Task<IActionResult> OnPostAsync() { context.Users.Update(Person!); await context.SaveChangesAsync(); return RedirectToPage("Index"); } } }
В методе OnGetAsync через параметр получаем id пользователя, по этому id получаем из базы данных объект и передаем его в свойство Person.
Поскольку к свойству Person применяется атрибут [BindProperty], то данные из запроса будут автоматически связаны со свойствами объекта Person.
В методе OnPostAsync сохраняем изменения в базе данных и выполняем переадресацию на страницу Index. Обратите внимание, что в данном случае при обновлении к объекту Person применяется оператор !.
Хотя данное свойство может представлять значение null, но поскольку оно автоматически связывается с данными запроса, и даже если в запросе не будет отправлено никаких данных,
все равно будет создан объект User, и свойство Person не будет равно null. Поэтому в данном случае мы можем написать context.Users.Update(Person!);
, тем самым указывая, что
Person не равен null. Однако в других условиях и сценариях может потребоваться проверять объект перед обновлением на null.
Также изменим файл Edit.cshtml:
@page "{id:int}" @model RazorPagesApp.Pages.EditModel <h2>Редактирование пользователя</h2> <form method="post"> <input name="id" value="@Model.Person?.Id" type="hidden" /> <p> <label>Имя</label><br /> <input name="name" value="@Model.Person?.Name" /> </p> <p> <label>Возраст</label><br /> <input name="age" value="@Model.Person?.Age" type="number" /> </p> <input type="submit" value="Сохранить" /> </form>
Чтобы параметр id передавался как параметр маршрута, после директивы page указан шаблон параметров маршрута "{id:int}". И далее идет форма для редактирования, все поля которой привязаны к свойствам модели EditModel.
В итоге весь проект будет выглядеть следующим образом:
Также изменим код IndexModel в файле Index.cshtml.cs:
using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.EntityFrameworkCore; using RazorPagesApp.Models; namespace RazorPagesApp.Pages { public class IndexModel : PageModel { ApplicationContext context; public ListUsers { get; private set; } = new(); public IndexModel(ApplicationContext db) { context = db; } public void OnGet() { Users = context.Users.AsNoTracking().ToList(); } public async Task<IActionResult> OnPostDeleteAsync(int id) { var user = await context.Users.FindAsync(id); if (user != null) { context.Users.Remove(user); await context.SaveChangesAsync(); } return RedirectToPage(); } } }
По сравнению с кодом из прошлой темы здесь добавлен обработчик OnPostDeleteAsync, который обрабатывает запросы post и который принимает id объекта на удаление. Затем, если объект найден, производится его удаление. Хотя также можно было бы для удаления создать отдельную страницу, но в данном случае это будет избыточно.
И также изменим файл Index.cshtml:
@page @addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers @model RazorPagesApp.Pages.IndexModel <h2>Список пользователей</h2> <p><a href="/Create">Добавить пользователя</a></p> <table> <tr><th>Имя</th><th>Возраст</th><th></th></tr> @foreach (var user in Model.Users) { <tr> <td>@user.Name</td ><td>@user.Age</td> <td> <form method="post"> <a asp-page="Edit" asp-route-id="@user.Id">Изменить</a> <button type="submit" asp-page-handler="delete" asp-route-id="@user.Id"> Удалить </button> </form> </td> </tr> } </table>
В форму в отдельном столбце помещены ссылка на редактирование и кнопка, по нажатию на которую будет идти post-запрос к обработчику delete (OnPostDeleteAsync) на текущей странице.
В итоге страница со списком пользователей будет выглядеть следующим образом:
По нажатию на кнопку объект будет удален, а по нажатию на ссылку приложение перейдет к странице редактирования: