在Web Forms專案上整合新技術,打造現代化網站
作者:陳傳興 (Bruce, 微軟最有價值專家)
早期,當我們談論ASP.NET時,絕大部分的開發者都很清楚且明白我們是在討論使用「伺服器控制項」的WebForms網頁開發技術。2013年開始,ASP.NET開發團隊喊出OneASP.NET架構與實作,在One ASP.NET架構下,ASP.NET不再是網站開發技術?,而是一種通用的底層運作核心,在此核心上提供各種開發技術,提供的網站開發技術有Web Forms、Web Pages、Single Page Apps與MVC(下一代的 MVC 6 = Web Pages + MVC + Web API),提供的服務開發技術有Web API與SignalR。
在 One ASP.NET 架構下應該正確稱呼使用「伺服器控制項」的網頁開發技術為 Web Forms。ASP.NET 開發團隊由 One ASP.NET 與 .NET Framework 4.5 開始,為了讓 Web Forms 也能擁有開發現代化網站的能力,開始專注提供下一代的開發技術與開發平台。
►關閉萬惡的 ViewState
我們都知道,HTTP 是一種無狀態(stateless)的協定,而過去,Web Forms使用了一種特別的機制來保存網頁的狀態,這種機制稱ViewState。ViewState就像神奇魔法讓頁面在與伺服器往返之間(Post Back)能保有頁面狀態。當然,ViewState有優點,也有缺點。
優點是: ViewState 是存在於 <form> 元素裡的隱藏欄位,並無cookie之類儲存方式的限制。可以將資料庫取出的資料放入ViewState裡,如此一來PostBack時便不需要重讀資料庫。
缺點是:加密的資料存儲在隱藏欄位會使網頁變大,若開發人員因為沒有注意,而在ViewState放入大量的資料,將會造成載入速度變慢。
✧註:圖表 3在ViewState儲存Northwind的Products資料表。
來源 |
資料量 |
圖表3 |
25.06 KB |
圖表4 |
9.91 KB |
頁面大小減少60%。雖然已經不使用ViewState儲存資料,但預設ViewState依然在運作當中。
Web Forms從.NET Framework 4.5開始,有越來越多的伺服器控制項不需要使用(或依賴) ViewState。我們可以很容易的關閉ViewState的使用,在頁面宣告加入EnableViewState="false"
:
<%@ Page EnableViewState="false" %>
頁面由9.91 KB又縮小至6.15 KB,也縮減37%的大小。
如果要整個專案停用ViewState,可以到web.config進行調整:
<system.web>
<pages enableViewState="false">
</system.web>
大小是其次,重點在於,現在沒有了ViewState,我們的Web Forms網站依然正常運作且反應更快。
►還在用 Data Source Controls?
過去在使用伺服器控制項(GridView、FormView、ListView…等)時大多會配合著使用Data-Source-Controls(SqlDataSource、ObjectDataSouce…等),但使用Data Source controls會有幾個問題:
- 難以測試。
- 難以驗證。
- 在ASPX檔案中含有大量的T-SQL語法與描述。
<asp:SqlDataSource ID="gridDS" runat="server"
ConnectionString="<%$ ConnectionStrings:Northwind %>"
DeleteCommand="DELETE FROM [Products] WHERE [ProductID] = @ProductID"
InsertCommand="INSERT INTO [Products] ([ProductName], [SupplierID], [CategoryID], [QuantityPerUnit], [UnitPrice], [UnitsInStock], [UnitsOnOrder], [ReorderLevel], [Discontinued]) VALUES (@ProductName, @SupplierID, @CategoryID, @QuantityPerUnit, @UnitPrice, @UnitsInStock, @UnitsOnOrder, @ReorderLevel,
@Discontinued)"
SelectCommand="SELECT * FROM [Products]"
UpdateCommand="UPDATE [Products] SET [ProductName] = @ProductName,
[SupplierID] = @SupplierID, [CategoryID] = @CategoryID, [QuantityPerUnit] =
@QuantityPerUnit, [UnitPrice] = @UnitPrice, [UnitsInStock] = @UnitsInStock,
[UnitsOnOrder] = @UnitsOnOrder, [ReorderLevel] = @ReorderLevel, [Discontinued]
= @Discontinued WHERE [ProductID] = @ProductID">
<DeleteParameters>
<asp:Parameter Name="ProductID" Type="Int32" />
</DeleteParameters>
<InsertParameters>
<asp:Parameter Name="ProductName" Type="String" />
<asp:Parameter Name="SupplierID" Type="Int32" />
<asp:Parameter Name="CategoryID" Type="Int32" />
<asp:Parameter Name="QuantityPerUnit" Type="String" />
<asp:Parameter Name="UnitPrice" Type="Decimal" />
<asp:Parameter Name="UnitsInStock" Type="Int16" />
<asp:Parameter Name="UnitsOnOrder" Type="Int16" />
<asp:Parameter Name="ReorderLevel" Type="Int16" />
<asp:Parameter Name="Discontinued" Type="Boolean" />
</InsertParameters>
<UpdateParameters>
<asp:Parameter Name="ProductName" Type="String" />
<asp:Parameter Name="SupplierID" Type="Int32" />
<asp:Parameter Name="CategoryID" Type="Int32" />
<asp:Parameter Name="QuantityPerUnit" Type="String" />
<asp:Parameter Name="UnitPrice" Type="Decimal" />
<asp:Parameter Name="UnitsInStock" Type="Int16" />
<asp:Parameter Name="UnitsOnOrder" Type="Int16" />
<asp:Parameter Name="ReorderLevel" Type="Int16" />
<asp:Parameter Name="Discontinued" Type="Boolean" />
<asp:Parameter Name="ProductID" Type="Int32" />
</UpdateParameters>
</asp:SqlDataSource>
這是Northwind資料庫Products資料表經由SqlDataSource所產生的程式碼,一般簡單需求,控制項與Data Source都是很不錯的解決方案。但需求慢慢趨向複雜,舉例來說,當我們有大量客製化T-SQL需求,例如Join Table,以前的便利就會變成現在的不便。
開發現代化網站有個重要的觀念:關注點分離(Separation_of_concerns,SoC)。舉例來說,Web_Forms的頁面基本上都是由二支程式組成,Default.aspx與Default.aspx.cs(CodeBehind),那麼我們應盡量讓每一支程式只負責一種工作,Default.aspx負責頁面的呈現,Dafault.aspx.cs負責DAL(Data Access Layer)或BLL(Business Logic Layer)的工作。但使用Data Source Controls會使得這樣的分工難以實作。
Web Forms在.NET_Framework_4.5由ASP.NET MVC框架學習一個非常好用的機制稱為「Model Binding」,Web Forms經由Model Binding可以將原本依賴Data Source Controls的功能,轉而直接呼叫開發好的DAL或BLL的程式模組。
在以下範例中,使用Visual-Studio-2013-Update-2與Entity-Framework-6.1經由Code-First產生Northwind的POCO類別,並且撰寫以下Repository類別:
public class ProductRepository
{
private Northwind db;
public ProductRepository()
{
this.db = new Northwind();
}
public IQueryable Get()
{
return db.Products;
}
public void Insert(Product newProduct)
{
db.Products.Add(newProduct);
}
public void Update(Product product)
{
db.Products.Attach(product);
}
public void Remove(int id)
{
db.Products.Remove(db.Products.Find(id));
}
public void Save()
{
db.SaveChanges();
}
}
在伺服器控制項,如GridView,DetailsView,ListView與FormView等為Model Binding提供的新屬性:
- ☛SelectMethod
- ☛UpdateMethod
- ☛DeleteMethod
- ☛InsertMethod
Default.aspx
<asp:GridView ID="grid" runat="server"
DataKeyNames="ProductID"
SelectMethod="Get"
OnCallingDataMethods="grid_OnCallingDataMethods">
</asp:GridView>
Defualt.aspx.cs
protected void
grid_OnCallingDataMethods(object sender, CallingDataMethodsEventArgs e)
{
e.DataMethodsObject = new Models.ProductRepository();
}
就這樣。有了Model Binding之後,Default.aspx專心在呈現工作,不再需要含有大量後端程式的Data Source Controls,原先Data-Source-Controls的後端程式碼可轉為模組化的DAL或BLL,除了可重覆使用之外,維護也方便。
►Bootstrap 3
在視覺設計這部分,一直是程式設計師的一大挑戰,而且近年行動設備的流行,對於Web-Forms程式設計師更是一大難關,各種伺服器控制項本身並不容易進行UI設計。Visual-Studio-2013開發範本中全面導入Bootstrap-3框架(https://getbootstrap.com/),讓開發人員用最少的力氣也能讓控制項產出的UI擁有專業美工的效果。
圖表7是GridView預設輸出樣式,GridView之類的控制項可以透過CssClass 屬性指定CSS類別來套用即有的CSS類別,例如套用Bootstrap
Css Table類別(https://getbootstrap.com/css/#tables):
▲圖表 8 CssClass=”table” Bootstrap效果
▲圖表 9 CssClass=” table table-striped” Bootstrap效果
引用Bootstrap的另一個好處是12欄網格的設計與RWD(Responsive Web Design)效果取得的立即性。例如,使用行動設備瀏覽預設Web Forms範本根目錄的Defualt.aspx。
▲圖表 10 Nokia 920瀏覽效果
頁面會隨著瀏覽設備的大小自動變更介面的配置。
►肥大的前端框架
前端技術近年來大爆發,各種優秀前端框架孕育而生:jQuery、jQuery UI、KendoUI、Modernizr、Bootstrap、Responsive、Knockout、AngularJS、RequireJS等等。但不管是CSS Framework或JavaScript Framework,雖然帶來強大的功能也不斷加大網頁的大小。大量使用各種前端框架頁面,還有一個問題,那就是不斷增加HTTP要求(HTTP Request)數量。
當FriendlyUrls偵測到要求是來自行動設備時,會自動採用同一支程式的Mobile版本。如圖12,Site.Master是正常版本,當有個要求來自行動設備,就會採用Site.Mobile.Master;ASPX應用程式也是相同原理,例如Default.aspx,我們可以設計Default.Mobile.aspx提供給行動設備使用。
一般:Site.Master
行動:Site.Mobile.Master
一般:Default.aspx
行動:Default.Mobile.aspx
►上吧,HTML5隊長
HTML5協定已經是未來網站發展確定的方向,Visual Studio 2013對於HTML5的支援度相當完整,Web Forms也以此為基礎進行改良,TextBox控制項提供TextMode屬性讓Web Forms開發者非常簡單就能選用各種HTML5表單屬性:
<div>
Color:
<asp:TextBox runat="server" TextMode="Color"></asp:TextBox>
<br />
Date:
<asp:TextBox runat="server" TextMode="Date"></asp:TextBox>
<br />
DateTime:
<asp:TextBox runat="server" TextMode="DateTime"></asp:TextBox>
<br />
DateTimeLocal:
<asp:TextBox runat="server" TextMode="DateTimeLocal"></asp:TextBox>
<br />
Email:
<asp:TextBox runat="server" TextMode="Email"></asp:TextBox>
<br />
Month:
<asp:TextBox runat="server" TextMode="Month"></asp:TextBox>
<br />
Multiline:
<asp:TextBox runat="server" TextMode="MultiLine"></asp:TextBox>
<br />
Number:
<asp:TextBox runat="server" TextMode="Number"></asp:TextBox>
<br />
Password:
<asp:TextBox runat="server" TextMode="Password"></asp:TextBox>
<br />
Phone:
<asp:TextBox runat="server" TextMode="Phone"></asp:TextBox>
<br />
Range:
<asp:TextBox runat="server" TextMode="Range"></asp:TextBox>
<br />
Search:
<asp:TextBox runat="server" TextMode="Search"></asp:TextBox>
<br />
SingleLine:
<asp:TextBox runat="server" TextMode="SingleLine"></asp:TextBox>
<br />
Time:
<asp:TextBox runat="server" TextMode="Time"></asp:TextBox>
<br />
Url:
<asp:TextBox runat="server" TextMode="Url"></asp:TextBox>
<br />
Week:
<asp:TextBox runat="server" TextMode="Week"></asp:TextBox>
<br />
</div>
註:呈現與各種效果依瀏覽器與瀏覽器版本有所不同。
另外強烈推薦安裝Visual Studio 2013的Web Essentials擴充套件,它可以讓我們在開發各種HTML5、CSS3、JavaScript時可以如虎添翼。
註:Web Essentials 2013 RTM now available
►結語
Web Forms經過十多年的淬煉已經有非常良好的基礎,但也有”歷史包袱”,但ASP.NET開發團隊並不以此為藉口,反而努力找出方法為了讓Web Forms開發技術也能具備現代化網站開發能力,其中像是不再依賴ViewState的控制項更是一大突破。
另一方面,ASP.NET MVC框架在網站開發技術上獲得的成功,讓ASP.NET開發團隊思考向ASP.NET MVC借用其成功經驗與技術,將ASP.NET MVC優良的技術導入Web Forms開發技術之內,整合Model Binding、Bundling and Minification、ASP.NET Routing等技術的Web Forms,開發現代化網站,No problem!:D
----------------------------------------------------------------------------------------------------------------------------
如何訂閱MSDN電子報?
請登入您的LiveID之後,勾選 台灣微軟 MSDN 程式開發人員電子報
登入請由此:https://aka.ms/newsletter-signup
---------------------------------------------------------------------------------------------
Comments
Anonymous
November 08, 2015
先進您好: 請教您關於使用ASP.Net Web form開發的.ASPX頁面,是否可以嵌入MVC的頁面中? 也就是把.ASPX(包含有test.aspx、test.aspx.cs、test.aspx.designer.cs,其中連結資料庫來源皆在test.aspx)作為一個View,來取代_layout.cshtml 裡面的@RenderBody 區塊? 如果可以,不知要如何實作?還望請指點,感謝您。Anonymous
November 09, 2015
先進您好: 請教您關於使用ASP.Net Web form開發的.ASPX頁面,是否可以嵌入MVC的頁面中? 也就是把.ASPX(包含有test.aspx、test.aspx.cs、test.aspx.designer.cs,其中連結資料庫來源皆在test.aspx)作為一個View,來取代_layout.cshtml 裡面的@RenderBody 區塊? 不知要如何實作?還望請指點,感謝您。