• ASP.NET MVC 开发


    本文提供了一些代码设计准则,目标是帮助ASP.NET MVC 开发人员创建可靠的应用程序,当然,你可根据实际应用程序选择合适的标准。本文由EntLib.com 小组翻译,欢迎分享和交流ASP.NET MVC 项目开发设计思路。

    Model建议 - Model Recommendations

    Model是定义业务领域相关的对象,应该包含业务逻辑(对象如何动作和关联),验证逻辑(验证对象的有效值),数据逻辑(数据对象如何持久化),和会话逻辑(跟踪用户状态)。

    创建独立的Model项目,在ASP.NET MVC 项目中引用Model程序集。

    将所有业务逻辑放置在Model中。

    如将所有业务逻辑放置在Model项目中,可根据实际业务数据来生成ViewController。有如下好处:

    •  减少重复的业务逻辑。
    •  View中减少业务逻辑,View易于理解。
    •  业务逻辑的测试仅仅和Model有关。

    例如,下面需要显示用户的用户名先显示Last Name,在View中代码如下:


    <% if (String.Compare((string)TempData["displayLastNameFirst"], "on"== 0)
           { 
    %>
            Welcome, 
    <%= Model.lastName%><%= Model.firstName%>
       
    <% }
          
    else
           { 
    %>
            Welcome, 
    <%= Model.firstName%> <%= Model.lastName%>
       
    <% } %>

    然而你需要在每一个地方重复这一逻辑。如将这一业务逻辑放置在Model中,可在Model中添加一个属性封装这一逻辑。


    public string combinedName
    {
       
    get
        {
           
    return (displayLastNameFirst ? lastName + " " + firstName : firstName + " " + lastName);
        }
       
    private set
        {
            ;
        }
    }

    这样,可大大简化视图代码:

    <% Welcome, <%= Model.combinedName %> %>

    将所有验证逻辑放置在Model

    所有输入验证应该在Model层,包括Client-side 验证。

    可使用ModelState 添加验证检查,代码如下所示:

    if (String.IsNullOrEmpty(userName))

    {

       ModelState.AddModelError("username", Resources.SignUp.UserNameError);

    不过,更好的办法是使用 System.ComponentModel.DataAnnotations,在Model类的属性上添加attribute,如下所示:

    public class User

    {

       [Required(ErrorMessageResourceName = "nameRequired", ErrorMessageResourceType = typeof(Resources.User))]

       public String userName { get; set; }

           ...

    }

    为数据访问定义接口

    接口用来暴露数据访问类的方法,强化ASP.NET MVC 的松散耦合设计。

    可考虑使用Entity Framework LINQ to SQL 创建对数据库的访问类,Entity Framework LINQ to SQL 都支持存储过程。

    将所有会话逻辑放置在Model中。

    View 建议 - View Recommendations

    View用来展示Model数据,Controller负责选择View。业务逻辑不属于ViewModel负责业务逻辑。View非常灵活,如ModelView可通过HTML显示,同样的Model也可通过XML 视图来呈现。

    HTML放置在ViewPartial View中(不要在Controller中)

    默认的ASP.NET视图引擎提供了如下视图文件:HTML View.aspx),Partial HTML View.ascx)和Master page.master

    如下视图演示了对partial view的调用:

    <%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="System.Web.Mvc.ViewPage" %>

        Below is a list of items submitted by <b>

    <%= Html.Encode(ViewData["name"]) %></b>.

        <p>

       

        ...

        <div id="items">

            <% Html.RenderPartial("ItemsByName");%>

        </div>   

    </asp:content>

    Partial viewItemsByName.ascx)如下所示:

    <%@ Control Language="C#" %>

            <% foreach (Seller.Controllers.Items item in (IEnumerable)ViewData.Model)

               { %>

                <tr>

                    <td>

                        <%= Html.Encode(item.title)%>

                    </td>

                    <td>

                        <%= Html.Encode(item.price)%>

                    </td>              

                </tr>       

            <% } %>

            </table>

          <% } %>

    Partial View 是一个强大的扩展和重用机制。你可在不同的地方包含相同的View,不必编写重复的代码。

    View中使用ViewData访问数据

    ASP.NET 提供了如下机制在View模板中访问数据:

    ViewData.Model 对象Controlleraction方法中,在return语句中传入一个Model对象(return View(myModelObject))。

    ViewData Dictionary – action方法中存入数据(ViewData[“key”] = value),接着在View中方法相同的dictionary

    在可能的情况下,应该是一ViewData Model,而不是ViewData 来访问数据,因为Model 提供了类型安全。此外,你应在View模板中,使用数据访问机制,而不是Request / Session 来访问。

    如需要显示一个对象的多个属性,可使用ViewData.Model,并创建一个强类型View。针对seller详细页面,seller类有namephoneaddressemail等等属性,在呈现View之前,你可在Controller中对ViewData.Model 赋值seller对象实例。但是如果是一些零散的数据,如page#、用户名和current time,则一般使用ViewData字典。

    在使用模型绑定(Model bingding)时,避免在view中访问数据。

    Controller 中访问数据库,在执行View之前,将从数据库中检索的数据复制给轻量的View Model对象,这样,轻量的View Model对象不必在视图执行时检索数据。

    使用(自动生成)客户端验证

    ASP.NET MVC 2 开始,可以很容易添加客户端验证。

    (1) 如前所述,在Model层中添加数据验证逻辑;

    (2) 确保项目中Scripts目录有如下javascript 文件:MicrosoftAjax.js MicrosoftMvcValidation.js

    (3) 在表单提交页面,添加如下代码:

    <script src="<%= Url.Content("~/Scripts/MicrosoftAjax.js") %>" type="text/javascript"></script>

    <script src="<%= Url.Content("~/Scripts/MicrosoftMvcValidation.js") %>" type="text/javascript"></script>

    (4) 在表单中添加如下代码:

    <% Html.EnableClientValidation(); %>

    现在如果编辑表单内容,当输入值不合格时,客户端马上进行验证提醒。

    在模板中插入server-side 注释

    View模板中使用服务端注释,在HTML呈现时,会剔除。

    如下是server-side注释:

    <%-- This is a server side template comment --%>

    不要在View模板中使用HTML 注释,因为这些注释会呈现在web浏览器中,可被用户看到。

    使用HTMLHelper 扩展方法。

    System.Web.Mvc.Html 类中包含了很多有用的HTML 扩展方法。

    Form 表单生成(BeginForm

    输入字段生成(checkboxhiddenradio buttontextbox

    链接URL生成(ActionLink

    XSS保护(Encode

    尽可能使用这些HTML扩展方法,如下是使用route table创建一个链接:

    <%= Html.ActionLink(“Home page”, “Default”) %>

    后续相关文章,可参考如下链接:

    英文原文链接:
    Best Practices for ASP.NET MVC
    http://blogs.msdn.com/b/aspnetue/archive/2010/09/17/second_2d00_post.aspx

    驳“面向对象的基本特性多态”

    在网上常常能看到文章讲面向对象的三大基本特征"继承"、"封装"、"多态",我以为这是坊间流传的最不靠谱的一个说法。本文先谈谈其中讲到的一个特性:多态。多态是一个跟面向对象完全正交的概念,两者之间可以说没有任何必然联系。当然口说无凭,下面是我经过很长时间查找到的一些来源比较可靠的资料对多态的说法。

    最早可查证的关于多态的说法是一篇叫做 Fundamental Concepts in Programming Languages的论文,文中对多态的讨论主要是用于实现运算符的重载版本选择,文中把多态分为两种: ad-hoc多态和参数多态,ad-hoc多态即指系统根据上下文自己决定如何选择运算符的行为,比如各种原生的运算符都在此列。参数多态则是根据参数类型选择。文中对参数多态的解释则是用了一个颇为"函数式"的例子,根据传入的函数类型参数的函数签名来决定返回值类型。 

    1985年左右的一篇论文On Understanding Types, Data Abstraction, and Polymorphis则详细地论述总结了多态性的概念,文中给出了多态的分类:
    polymorphism(多态)
    |-universal

    | |- parametric 

    | \- inclusion

    \-ad-hoc

      |- overloading

      \- coercio 

    这篇文章对多态的论述比较系统,网上也有pdf版本,有兴趣的朋友可以详细阅读。(inclusion多态听起来比较陌生,但是其实它的另一个名称是subtype Polymorphism,这也是唯一一种跟面向对象相关的多态)

    从上面的发展可以看出,多态是一个差不多跟面向对象同时(60年代)诞生的编程概念,有自己独立的体系结构,并且这个概念非常广泛地用于很多种编程语言的设计当中。

    关于面向对象跟多态的关系,下面一段话用来解释非常恰当(来自The C++ programming language), 

    Since both(wintercn注:根据上下文指template和abstract class) allow an algorithm to be expressed once and applied to a variety of types, people sometimes refer to both as polymorphic. 

    意思是:因为template和abstract class两种机制都能允许一个算法表达一次而用在多种不同类型当中,所以人们把两种都称作多态。后文还讲到abstract class提供的是运行时多态,template提供的是编译时多态。(有趣的是,连面向对象的代表性语言之一C++本身都涉及到了一种跟面向对象毫无关系的多态类型。)

    所以事实上,多态并非面向对象的私产,更不是什么面向对象的基本特征,多态和面向对象的关系是:面向对象中的抽象类,提供了一种运行时多态的实现方式。 

  • 相关阅读:
    改进SENet-ECA-Net: Efficient Channel Attention for Deep Convolutional Neural Networks
    组集成网络-Group Ensemble: Learning an Ensemble of ConvNets in a single ConvNet
    轻量级网络-ReXNet:Diminishing Representational Bottleneck on Convolutional Neural Network
    ULSAM:Ultra-Lightweight Subspace Attention Module for Compact Convolutional Neural Networks
    工作中常用的 Shell 命令及技巧
    程序员需要熟悉的英语单词
    程序员基本素养
    Java 基础 —— Lambda 表达式
    将博客搬至CSDN
    IDEA 插件推荐 —— 让你写出好代码的神器!
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/2036085.html
Copyright © 2020-2023  润新知