ASP.NET Razor 标记(超详细)

更新时间:

💡一则或许对你有用的小广告

欢迎加入小哈的星球 ,你将获得:专属的项目实战 / 1v1 提问 / Java 学习路线 / 学习打卡 / 每月赠书 / 社群讨论

截止目前, 星球 内专栏累计输出 90w+ 字,讲解图 3441+ 张,还在持续爆肝中.. 后续还会上新更多项目,目标是将 Java 领域典型的项目都整一波,如秒杀系统, 在线商城, IM 即时通讯,权限管理,Spring Cloud Alibaba 微服务等等,已有 3100+ 小伙伴加入学习 ,欢迎点击围观

前言

在 Web 开发领域,开发者常常需要将静态的 HTML 与动态的后端逻辑无缝结合。ASP.NET Razor 标记正是为此而生——它通过简洁的语法,让开发者能够在 HTML 中直接嵌入 C# 代码,实现视图层与业务逻辑的高效协作。无论是编程初学者还是有一定经验的开发者,掌握这一工具都能显著提升开发效率。本文将从基础到进阶,结合实际案例,带您全面理解 ASP.NET Razor 标记的核心功能与应用场景。


基础语法:HTML 与 C# 的“共生关系”

什么是 Razor 标记?

Razor 是 ASP.NET 提供的一种语法,允许开发者在 HTML 文件中直接编写 C# 代码。它通过 @ 符号区分 HTML 内容和代码块,例如:

<p>当前时间:@DateTime.Now</p>

这段代码会将服务器的当前时间动态渲染到页面中。

核心概念:代码块与表达式

Razor 的语法分为两类:

  1. 表达式(Expression):以 @ 开头,直接输出结果。例如:
    <div>用户数量:@UserCount</div>  
    
  2. 代码块(Code Block):用 @{ ... } 包裹,执行复杂逻辑。例如:
    @{
        var message = "欢迎访问!";
        if (IsLoggedIn) { message += " 请开始您的探索!"; }
    }
    <h1>@message</h1>
    

形象比喻:Razor 是 HTML 的“智能翻译官”

想象 HTML 是一本静态的书,而 Razor 就像一个能理解 C# 的翻译官,它读取代码并将其转化为动态内容。例如,当用户访问页面时,Razor 会将 @DateTime.Now 翻译成实际的时间值,再将结果插入到 HTML 中。


条件判断与循环:动态内容的“指挥棒”

条件语句:根据逻辑展示不同内容

通过 @if@else if@else 结构,开发者可以控制页面元素的显示。例如:

@{
    var userRole = "admin";
}
@if (userRole == "admin") {
    <div>您有管理员权限</div>
} else if (userRole == "guest") {
    <div>请登录以解锁更多功能</div>
} else {
    <div>未知角色</div>
}

案例:用户权限控制

假设一个电商网站需要根据用户角色显示不同的菜单项:

<ul>
    @if (User.IsInRole("Admin")) {
        <li><a href="/admin">管理后台</a></li>
    }
    @if (User.IsAuthenticated) {
        <li><a href="/orders">我的订单</a></li>
    }
</ul>

循环结构:批量渲染列表数据

通过 @foreach,可以遍历集合并生成 HTML 元素。例如:

<ul>
    @foreach (var product in products) {
        <li>@product.Name - @product.Price 元</li>
    }
</ul>

实际场景:显示商品列表

假设有一个 Product 对象列表:

public class Product {
    public string Name { get; set; }
    public decimal Price { get; set; }
}

在 Razor 视图中,可以这样渲染:

<table>
    <thead>
        <tr><th>名称</th><th>价格</th></tr>
    </thead>
    <tbody>
        @foreach (var product in Model.Products) {
            <tr>
                <td>@product.Name</td>
                <td>@product.Price</td>
            </tr>
        }
    </tbody>
</table>

表单处理与数据绑定:用户交互的“枢纽”

基础表单:收集用户输入

通过 Razor 的 Html.BeginForm() 辅助方法,可以快速生成表单。例如:

@using (Html.BeginForm("Submit", "Home", FormMethod.Post)) {
    <label>姓名:@Html.TextBoxFor(m => m.Name)</label>
    <label>邮箱:@Html.TextBoxFor(m => m.Email)</label>
    <input type="submit" value="提交" />
}

此代码会生成一个提交到 Home/Submit 的表单,并自动绑定模型(Model)中的 NameEmail 属性。

强类型视图:模型驱动的开发

使用 @model 指令声明视图绑定的模型类型,例如:

@model MyProject.Models.UserRegistrationViewModel

这允许开发者直接访问模型属性,例如:

<p>欢迎,@Model.UserName!</p>

案例:用户注册表单

假设有一个 UserRegistrationViewModel 模型:

public class UserRegistrationViewModel {
    [Required]
    public string UserName { get; set; }
    [EmailAddress]
    public string Email { get; set; }
}

对应的视图代码可以这样编写:

@model UserRegistrationViewModel

@using (Html.BeginForm()) {
    @Html.LabelFor(m => m.UserName)
    @Html.TextBoxFor(m => m.UserName)
    @Html.ValidationMessageFor(m => m.UserName)

    @Html.LabelFor(m => m.Email)
    @Html.TextBoxFor(m => m.Email)
    @Html.ValidationMessageFor(m => m.Email)

    <input type="submit" value="注册" />
}

布局与继承:模块化开发的“蓝图”

布局页(Layout):统一页面结构

通过 _Layout.cshtml 文件,可以定义网站的通用结构(如导航栏、页脚)。例如:

<!-- _Layout.cshtml -->
<!DOCTYPE html>
<html>
<head>
    <title>@ViewBag.Title</title>
</head>
<body>
    <nav>
        <ul>
            <li>@Html.ActionLink("首页", "Index", "Home")</li>
            <li>@Html.ActionLink("关于", "About", "Home")</li>
        </ul>
    </nav>
    <div>
        @RenderBody()  <!-- 子视图内容插入点 -->
    </div>
    <footer>© 2023 My Website</footer>
</body>
</html>

子视图继承布局页

在子视图中通过 Layout 指令指定布局页:

@{
    Layout = "~/Views/Shared/_Layout.cshtml";
}
<!-- 子视图内容 -->
<h1>欢迎来到首页</h1>

部分视图(Partial View):复用组件

通过 Html.Partial()Html.RenderPartial() 渲染共享组件。例如:

<!-- _CommentList.cshtml 部分视图 -->
@foreach (var comment in Model) {
    <div class="comment">
        <p>@comment.Content</p>
        <small>by @comment.Author</small>
    </div>
}

在主视图中调用:

@Html.Partial("_CommentList", Model.Comments)

高级用法:Razor 的隐藏能力

自定义 HTML 辅助方法

通过扩展 HtmlHelper,可以封装常用功能。例如,一个分页导航辅助方法:

public static class HtmlHelpers {
    public static IHtmlContent Pagination(this HtmlHelper html, int currentPage, int totalPages) {
        var sb = new StringBuilder();
        sb.Append("<ul class='pagination'>");
        for (int i = 1; i <= totalPages; i++) {
            sb.Append($"<li class='page-item { (i == currentPage ? "active" : "") }'>");
            sb.Append($"<a class='page-link' href='?page={i}'>{i}</a>");
            sb.Append("</li>");
        }
        sb.Append("</ul>");
        return new HtmlString(sb.ToString());
    }
}

在视图中使用:

@Html.Pagination(CurrentPage, TotalPages)

静态资源引用:@Url.Content()

通过 @Url.Content() 辅助方法引用静态资源,确保路径正确:

<link rel="stylesheet" href="@Url.Content("~/css/styles.css")" />

常见问题与解决方案

1. 代码块未闭合导致解析错误

现象:页面显示错误提示“未找到分隔符 }”。
解决:检查 @{ ... } 内部的代码是否缺少 },或使用缩进确保代码块结构清晰。

2. 动态内容未渲染

现象:页面显示 @DateTime.Now 而非实际时间。
原因:视图未正确绑定模型或未使用 Razor 标记。
解决:确保代码位于 .cshtml 文件中,并检查 @ 符号是否被转义。

3. 表单提交后数据丢失

现象:表单提交后,页面刷新时输入内容消失。
解决:在 POST 动作中重新传递模型数据,或使用 TempData 临时存储。


案例实战:构建用户管理系统

需求描述

创建一个简单的用户管理页面,包含以下功能:

  • 显示用户列表
  • 添加新用户
  • 编辑用户信息

代码实现

1. 用户模型

public class User {
    public int Id { get; set; }
    public string Name { get; set; }
    public string Email { get; set; }
}

2. 控制器

public class UserController : Controller {
    private List<User> Users = new List<User>();

    public ActionResult Index() {
        return View(Users);
    }

    [HttpPost]
    public ActionResult Add(User user) {
        Users.Add(user);
        return RedirectToAction("Index");
    }
}

3. Razor 视图(Index.cshtml)

@model List<User>

@{
    ViewBag.Title = "用户列表";
}

<h1>用户管理</h1>

<!-- 添加用户表单 -->
<form method="post" action="/User/Add">
    <input type="text" name="Name" placeholder="用户名" required />
    <input type="email" name="Email" placeholder="邮箱" required />
    <button type="submit">添加用户</button>
</form>

<!-- 用户列表 -->
<table>
    <thead>
        <tr><th>名称</th><th>邮箱</th></tr>
    </thead>
    <tbody>
        @foreach (var user in Model) {
            <tr>
                <td>@user.Name</td>
                <td>@user.Email</td>
            </tr>
        }
    </tbody>
</table>

结论

ASP.NET Razor 标记通过简洁的语法和强大的功能,为动态 Web 开发提供了高效且直观的解决方案。从基础的条件判断、循环结构,到高级的布局继承和自定义辅助方法,它始终以“让 HTML 与 C# 自然协作”为核心目标。无论是构建简单的表单,还是复杂的管理系统,Razor 都能帮助开发者快速实现需求,同时保持代码的可维护性与可读性。

掌握这一工具后,开发者可以进一步探索 ASP.NET Core 的更多特性,如中间件、依赖注入等,从而构建出更健壮、可扩展的 Web 应用。希望本文能成为您学习 ASP.NET Razor 标记的起点,并在实际项目中发挥价值。

最新发布