为什么Asp.NET MVC优于Asp.NET Web窗体

Sma*_*ack 12 asp.net-mvc webforms asp.net-mvc-3 asp.net-mvc-4 asp.net-mvc-5

我是asp.net Web Forms开发人员,我知道Asp.net MVC的基础知识.开发人员谈论MVC的优点,但我没有遇到过使用MVC而不是Asp.NET的明确或引人注目的描述.

这不是重复的问题,我已经经历了几乎所有类似的问题,但没有得到更清楚的描述更多与现实生活的例子.我很欣赏并希望用现实生活中的例子解释下面提到的每一个问题,请不要将其标记为重复.

我知道你不能用Asp.NET MVC取代Asp.NET Web Forms,我们在MVC中仍有以下优势:

  1. 关注点分离(SoC):我们也可以在asp.net中实现它,实际上在MVC中添加BAL组件我们必须将业务逻辑与控制器操作方法隔离开来.SoC只适用于MVC中的模型 - 视图 - 控制器分离吗?然后是业务逻辑呢?请提供将考虑Web窗体和MVC的真实示例.
  2. 启用对呈现HTML的完全控制:Web Forms还提供对Html的控制不是吗?它认为Web窗体中的html渲染比html辅助方法在MVC中做的更抽象.任何人都可以通过考虑Web Forms和MVC的例子来解释它,因为我在这一点上变得更加困惑.
  3. 启用测试驱动开发(TDD):如果您已将业务逻辑分离为BAL,那么您已实现TDD?是否存在MVC在webforms上的准确选择?请提供相同的示例
  4. 没有ViewState和PostBack事件:我们可以在Web窗体中管理viewstate,这需要付出很多努力,因为在MVC中我们可以通过使用Viewbag维护状态,Tempdata因为web是无状态的,所以有一些机制,MVC将其状态保持为Web的隐藏字段然后形成MVC如何在状态良好方面改进性能和页面大小?通过考虑Web Forms和MVC的例子表示赞赏
  5. 与jQuery轻松集成:"Asp.NET Web Forms为控件生成自定义ID"这是JavaScript框架易于集成的唯一考虑因素吗?如果是,那么我们可以在Web窗体的asp.net控件中使用ClientIDMode

小智 12

1.分离关注点

MVC中的SoC不是关于从UI分离业务逻辑.更重要的是,它为Controller提供了主要功能:

  • 域模型填充视图模型 ;
  • 处理View活动;
  • 根据域逻辑显示视图.

View仅负责MVC中的数据表示.

它使测试非常简单,因为Controller运行纯View模型类,而不是运行事件和Form的WebForms.

在WebForms View中,处理所有UI活动,它基本上就场景流做出决策.

在这里,我想提一下视图模型域模型的术语是不同的.域模型是一个描述所有服务的术语,业务逻辑和隐藏在Controller中的 DAL,具有一些外观.而视图模型是通过封装需要查看数据的类.在简单的情况下,域模型可以共享它.为什么两个班?

以下是ASP.NET MVC和WebForms执行相同操作的类似代码片段:1)获取数据2)处理数据提交.在这两种情况下,我都认为IDomainModel是注入的.

MVC:

public class SomeController : Controller
{
    // injected
    public IDomainModel Domain { get; set; }

    public ViewResult Edit()
    {
        var record = Domain.GetRecord(1);
        var dictionary = Domain.GetSomeDictionary();
        var model = new SomeViewModel(record, dictionary);

        return View(model);
    }

    [HttpPost]
    public ActionResult Edit(SomeViewModel model)
    {
        if (ModelState.IsValid)
            // save
            return RedirectToAction("Result");
        else
            return View(model);
    }
}
Run Code Online (Sandbox Code Playgroud)

WebForms的:

public partial class SomePage : System.Web.UI.Page
{
    // injected
    public IDomainModel Domain { get; set; }

    protected void Page_Load(object sender, EventArgs e)
    {
        var record = Domain.GetRecord(1);
        var dictionary = Domain.GetSomeDictionary();

        RecordId.Text = record.Id.ToString();
        RecordName.Text = record.Name;
        RecordDescription.Text = record.Description;

        DicValue.DataSource = dictionary;
        DicValue.DataValueField = "Id";
        DicValue.DataTextField = "Value";
        DicValue.SelectedValue = record.DictionaryEntryId.ToString();
        DicValue.DataBind();
    }

    protected void btnSave_Click(object sender, EventArgs e)
    {
        var record = new RecordModel
        {
            Id = Int32.Parse(this.RecordId.Text),
            Name = this.RecordName.Text,
            Description = this.RecordDescription.Text,
            DictionaryEntryId = Int32.Parse(this.DicValue.Text)
        };
        // save
    }
}
Run Code Online (Sandbox Code Playgroud)

测试MVC控制器EditGET非常简单:

[TestMethod]
public void EditGetTest()
{
    SomeController target = new SomeController();

    var record = new RecordModel { Id = 1, Name = "name1", Description = "desc1", DictionaryEntryId = 1 };
    var dictionary = new List<SomeDictionaryEntry>
    {
        new SomeDictionaryEntry { Id = 1, Value = "test" }
    };

    target.Domain = new SimpleMVCApp.Models.Fakes.StubIDomainModel()
    {
        GetRecordInt32 = (id) => { return record; },
        GetSomeDictionary = () => { return dictionary; }
    };

    var result = target.Edit();

    var actualModel = (SomeViewModel)result.Model;
    Assert.AreEqual(1, actualModel.Id);
    Assert.AreEqual("name1", actualModel.Name);
    Assert.AreEqual("desc1", actualModel.Description);
    Assert.AreEqual(1, actualModel.DictionaryEntryId);
}
Run Code Online (Sandbox Code Playgroud)

要测试WebForms事件,我们需要做出很多改变和假设:我们需要公开方法,我们需要初始化Form及其控件.它会导致严重的硬读取测试,这对于3)TDD是不可能的.

2.启用对呈现的HTML的完全控制

我觉得这句话有点夸张.只有HTML才能完全控制呈现的HTML.至于HtmlHelpers,DisplayTemplates和EditorTemplates,尽管团队对框架的6个版本进行了重大改进,但将anotherViewData转换为html属性仍然有些烦人.
例如,要将一些html属性传递给您无法使用的输入@Html.EditorFor,您必须使用@Html.TextBoxFor.
在ASP.NET中,您可以在任何元素上指定任何属性,它们只会呈现.

MVC:

错误:

@Html.EditorFor(m => m.Name, new { MySuperCustomAttribute = "Hello" })
Run Code Online (Sandbox Code Playgroud)

正确:

@Html.TextBoxFor(m => m.Name, new { MySuperCustomAttribute = "Hello" })
Run Code Online (Sandbox Code Playgroud)

ASP.NET:

<asp:TextBox runat="server" ID="RecordName" MySuperCustomAttribute="hello"></asp:TextBox>
Run Code Online (Sandbox Code Playgroud)

3.启用测试驱动开发(TDD)

我认为这个声明是关于Controller vs Code-Behind的测试.我在1中介绍了这一点.

4.没有ViewState和PostBack事件

ViewBag和ViewData是弱类型的工具,用于在Controller和Views之间传递数据.它们被渲染为元素,与ViewState无关.例如,在我的View中初始化ViewBag.Title = "EditView";允许我在Layout页面上使用此字符串:<title>@ViewBag.Title - My ASP.NET MVC Application</title>.在页面上看起来就像这样<title>EditView - My ASP.NET MVC Application</title>

对于TempData,Session和Application,它们存储在服务器端.它根本没有呈现为页面.

5.与JQuery轻松集成

我不认为与JQuery的集成如何变得更容易MVC.以下是我们如何将JQuery集成到WebForms中:

<script src="Scripts/jquery-1.8.2.min.js"></script>
<script>
$(document).ready(function () {
    $('#DicValue').change(function () {
        $('#ChosenValue').text($('#DicValue option:selected').val());
    });
});
</script>
Run Code Online (Sandbox Code Playgroud)

这几乎是ASP.NET MVC的相同片段:

@section scripts{
<script src="~/Scripts/jquery-1.8.2.min.js"></script>
<script>
$(document).ready(function () {
    $('#DictionaryEntryId').change(function () {
        $('#ChosenValue').text($('#DictionaryEntryId option:selected').val());
    });
});
</script>
}
Run Code Online (Sandbox Code Playgroud)

关于JQuery还有另外一点要提到:由于ASP.NET MVC是非常有意见的框架,因此对于大量的JS使用它会变得有些限制.它最初是为基于Scaffold Templates的开发而设计的,它最适合它.JQuery适用于ajax请求和ASP.NET MVC中的一些次要逻辑,但是当你开始广泛使用它时,每个视图最终会有两个控制器:一个是C#,一个是JS.您好,单元测试!此外,JQuery(UI)具有丰富的UI控件.

ASP.NET在设计时考虑了Postbacks,它们决定了基本的应用程序模型.但是,ASP.NET也有不同的UI工具包,使应用程序更具动态性,JQuery仍有一些地方.

哇,这是一个很长的答案.希望它会有所帮助.


Nip*_*tha 1

好的。

我正在 Webforms 和 MVC 这两个框架中开发应用程序,将根据我的经验进行解释。

纪律是您正在开发的任何架构中需要遵循的最重要的事情。

如果您正确遵循 MVC 并按照标准,生活将会非常简单。

让我们一点一点地讲。

关注点分离(SoC): MVC 在各个级别提供干净、有组织和细粒度的解决方案,例如,有多个辅助类可以在后期绑定中进行挂钩和帮助,您可以使用各种插件来模拟控制器。易于开发 Helper 类。

启用对渲染的 HTML 的完全控制 基本上,在 MVC 中,我们拥有原生格式的 HTML,因此您可以对其进行更多控制,重要的是当页面上有大量控件和数据时,它可以加快页面加载速度。当我们采用 Web 表单架构时,这一点很重要。

启用测试驱动开发 (TDD): 只要遵守纪律,您就可以在两种架构中做到这一点

没有 ViewState 和 PostBack 事件: Viewstate 会给页面和 Web 表单带来额外的负载,当您看到具有大量控件、网格等的页面源时,您将看到巨大的 viewstate。如果没有视图状态,生活就会很简单。ViewData 位于客户端,而其他视图位于服务器端。

与 Jquery 轻松集成: 确实,MVC3、4 对 JQuery 的支持超级好。模板中已经引入了许多预定义的 JQuery。

除了上述几点之外,还有一些其他要点 捆绑 更新和现代化的默认项目模板 更好地支持移动应用程序 快速开发 代码可重用性 层内耦合最少 对 Ajax 的良好支持

看看几个链接

http://www.codeproject.com/Articles/683730/New-Features-in-ASP-NET-MVC http://www.asp.net/mvc/tutorials/hands-on-labs/whats-new-in -aspnet-mvc-4

ASP.NET MVC 3 和 4 之间的区别?