Hướng dẫn tạo Scaffolded Razor Pages trên ASP.NET Core

0
839

Tiếp tục chuỗi bài hướng dẫn tạo Web App trên cơ bản trên ASP.NET Core trên oktot. Hôm nay oktot sẽ Hướng dẫn tạo Scaffolded Razor Pages trên ASP.NET Core.

Bạn có thể xem lại bài Hướng dẫn tạo Model với ngôn ngữ Razor trong ASP.NET Core trên Visual Studio để có thể hiểu rõ hơn.

Trong bài này chúng ta sẽ sử dụng source code của bài trước bạn có để tải link bên dưới.

Link download Source mẫu:

[vc_btn title=”Download” color=”vista-blue” i_icon_fontawesome=”fa fa-hand-o-right” add_icon=”true” link=”url:https%3A%2F%2Fgithub.com%2Faspnet%2FDocs%2Ftree%2Fmaster%2Faspnetcore%2Ftutorials%2Frazor-pages%2Frazor-pages-start%2Fsample%2FRazorPagesMovie||target:%20_blank|rel:nofollow”]

Html code here! Replace this with any non empty text and that's it.

Còn bây giờ chúng ta bắt đầu chiến đấu nào!

Hướng dẫn tạo View Create, Edit, Delete và Detail

Tạo Pages/Movies/Index.cshtml.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.RazorPages;
using Microsoft.EntityFrameworkCore;
using RazorPagesMovie.Models;

namespace RazorPagesMovie.Pages.Movies
{
    public class IndexModel : PageModel
    {
        private readonly RazorPagesMovie.Models.RazorPagesMovieContext _context;

        public IndexModel(RazorPagesMovie.Models.RazorPagesMovieContext context)
        {
            _context = context;
        }

        public IList<Movie> Movie { get;set; }

        public async Task OnGetAsync()
        {
            Movie = await _context.Movie.ToListAsync();
        }
    }
}

Razor page bắt đầu từ PageModel. Theo quy ước PageModel được gọi bởi <PageName>Model. Lập trình viên sử dụng dependency injection  để thêm RazorPagesMovieContext vào page.

tất cả các “scaffolded” phải tuân thủ cấu trúc cửa DI pattern. Khi yêu cầu khởi tạo một page được thực hiện, phương thức OnGetAsync sẽ trả về danh sách của model “movies” đến View razor page. OnGetAsync hoặc OnGet gọi trên razor page để chuẩn bị thực hiện quá trình đó.

Trong trường hợp này OnGetAsync nhận danh sách dữ liệu của movies model và hiển thị chúng.

When OnGet returns void or OnGetAsync returnsTask, no return method is used. When the return type is IActionResult or Task<IActionResult>, a return statement must be provided. For example, the Pages/Movies/Create.cshtml.cs OnPostAsync method:

khi OnGet trả về giá trình void hoặc OnGetAsyns thì phương thức “no return” đã được sử dụng. Khi chung trả về giá trị kiểu IActionResult hoặcTask<IActionResult>.

Ví dụ: the Pages/Movies/Create.cshtml.cs với phương thức OnPostAsync:

public async Task<IActionResult> OnPostAsync()
{
    if (!ModelState.IsValid)
    {
        return Page();
    }

    _context.Movie.Add(Movie);
    await _context.SaveChangesAsync();

    return RedirectToPage("./Index");
}

Tiếp tục tạo  Pages/Movies/Index.cshtml Razor Page:

@page
@model RazorPagesMovie.Pages.Movies.IndexModel

@{
    ViewData["Title"] = "Index";
}

<h1>Index</h1>

<p>
    <a asp-page="Create">Create New</a>
</p>
<table class="table">
    <thead>
        <tr>
            <th>
                @Html.DisplayNameFor(model => model.Movie[0].Title)
            </th>
            <th>
                @Html.DisplayNameFor(model => model.Movie[0].ReleaseDate)
            </th>
            <th>
                @Html.DisplayNameFor(model => model.Movie[0].Genre)
            </th>
            <th>
                @Html.DisplayNameFor(model => model.Movie[0].Price)
            </th>
            <th></th>
        </tr>
    </thead>
    <tbody>
@foreach (var item in Model.Movie) {
        <tr>
            <td>
                @Html.DisplayFor(modelItem => item.Title)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.ReleaseDate)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.Genre)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.Price)
            </td>
            <td>
                <a asp-page="./Edit" asp-route-id="@item.ID">Edit</a> |
                <a asp-page="./Details" asp-route-id="@item.ID">Details</a> |
                <a asp-page="./Delete" asp-route-id="@item.ID">Delete</a>
            </td>
        </tr>
}
    </tbody>
</table>

Sửa code trong file Pages/Movies/Index.cshtml

@page
@model RazorPagesMovie.Pages.Movies.IndexModel

@{
    ViewData["Title"] = "Index";
}

Sửa code Pages/Shared/_Layout.cshtm

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>@ViewData["Title"] - RazorPagesMovie</title>

    @*Markup removed for brevity.*@

Tạo Pages/Movies/Create.cshtml.cs tương ứng với model Movies

// Unused usings removed.
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.RazorPages;
using RazorPagesMovie.Models;
using System;
using System.Threading.Tasks;

namespace RazorPagesMovie.Pages.Movies
{
    public class CreateModel : PageModel
    {
        private readonly RazorPagesMovie.Models.RazorPagesMovieContext _context;

        public CreateModel(RazorPagesMovie.Models.RazorPagesMovieContext context)
        {
            _context = context;
        }

        public IActionResult OnGet()
        {
            return Page();
        }

        [BindProperty]
        public Movie Movie { get; set; }

        public async Task<IActionResult> OnPostAsync()
        {
            if (!ModelState.IsValid)
            {
                return Page();
            }

            _context.Movie.Add(Movie);
            await _context.SaveChangesAsync();

            return RedirectToPage("./Index");
        }
    }
}

Tạo phương thức OnPostAsync:

public async Task<IActionResult> OnPostAsync()
{
    if (!ModelState.IsValid)
    {
        return Page();
    }

    _context.Movie.Add(Movie);
    await _context.SaveChangesAsync();

    return RedirectToPage("./Index");
}

Tạo  Pages/Movies/Create.cshtml

@page
@model RazorPagesMovie.Pages.Movies.CreateModel

@{
    ViewData["Title"] = "Create";
}

<h1>Create</h1>

<h4>Movie</h4>
<hr />
<div class="row">
    <div class="col-md-4">
        <form method="post">
            <div asp-validation-summary="ModelOnly" class="text-danger"></div>
            <div class="form-group">
                <label asp-for="Movie.Title" class="control-label"></label>
                <input asp-for="Movie.Title" class="form-control" />
                <span asp-validation-for="Movie.Title" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Movie.ReleaseDate" class="control-label"></label>
                <input asp-for="Movie.ReleaseDate" class="form-control" />
                <span asp-validation-for="Movie.ReleaseDate" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Movie.Genre" class="control-label"></label>
                <input asp-for="Movie.Genre" class="form-control" />
                <span asp-validation-for="Movie.Genre" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Movie.Price" class="control-label"></label>
                <input asp-for="Movie.Price" class="form-control" />
                <span asp-validation-for="Movie.Price" class="text-danger"></span>
            </div>
            <div class="form-group">
                <input type="submit" value="Create" class="btn btn-primary" />
            </div>
        </form>
    </div>
</div>

<div>
    <a asp-page="Index">Back to List</a>
</div>

@section Scripts {
    @{await Html.RenderPartialAsync("_ValidationScriptsPartial");}
}

Giao diện code trên visual studio:

Vậy là chúng ta đã có ví dụ cho việc tạo Scaffolded Razor Pages trên ASP.NET Core, bài tiếp theo oktot sẽ hướng dẫn các bạn kết nối với Database.

This site uses Akismet to reduce spam. Learn how your comment data is processed.