|
ASP.NET 成功的其中一個(gè)原因在于它降低了 Web 開(kāi)發(fā)人員的門(mén)檻。即便您不是計(jì)算機(jī)科學(xué)博士也可以編寫(xiě) ASP.NET 代碼。我在工作中遇到的許多 ASP.NET 開(kāi)發(fā)人員都是自學(xué)成材的,他們?cè)诰帉?xiě) C# 或 Visual Basic® 之前都在編寫(xiě) Microsoft® Excel® 電子表格。現(xiàn)在,他們?cè)诰帉?xiě) Web 應(yīng)用程序,總的來(lái)說(shuō),他們所做的工作值得表?yè)P(yáng)。 但是與能力隨之而來(lái)的還有責(zé)任,即使是經(jīng)驗(yàn)豐富的 ASP.NET 開(kāi)發(fā)人員也難免會(huì)出錯(cuò)。在多年的 ASP.NET 項(xiàng)目咨詢(xún)工作中,我發(fā)現(xiàn)某些錯(cuò)誤特別容易導(dǎo)致缺陷不斷發(fā)生。其中某些錯(cuò)誤會(huì)影響性能。其他錯(cuò)誤會(huì)抑制可伸縮性。有些錯(cuò)誤還會(huì)使開(kāi)發(fā)團(tuán)隊(duì)耗費(fèi)寶貴的時(shí)間來(lái)跟蹤錯(cuò)誤和意外的行為。 下面是會(huì)導(dǎo)致 ASP.NET 生產(chǎn)應(yīng)用程序的發(fā)布過(guò)程中出現(xiàn)問(wèn)題的 10 個(gè)缺陷以及可避免它們的方法。所有示例均來(lái)自我對(duì)真實(shí)的公司構(gòu)建真實(shí)的 Web 應(yīng)用程序的親身體驗(yàn),在某些情況下,我會(huì)通過(guò)介紹 ASP.NET 開(kāi)發(fā)團(tuán)隊(duì)在開(kāi)發(fā)過(guò)程中遇到的一些問(wèn)題來(lái)提供相關(guān)的背景。 LoadControl 和輸出緩存 用戶(hù)控件可以采用聲明的方式加載,也可以強(qiáng)制加載。強(qiáng)制加載依賴(lài)于 Page.LoadControl,它實(shí)例化用戶(hù)控件并返回控件引用。如果用戶(hù)控件包含自定義類(lèi)型的成員(例如,公共屬性),則您可以轉(zhuǎn)換該引用并從您的代碼訪(fǎng)問(wèn)自定義成員。圖 1 中的用戶(hù)控件實(shí)現(xiàn)名為 BackColor 的屬性。以下代碼加載用戶(hù)控件并向 BackColor 分配一個(gè)值: protected void Page_Load(object sender, EventArgs e){// 加載用戶(hù)控件并將其添加到頁(yè)面中Control control = LoadControl("~/MyUserControl.ascx");PlaceHolder1.Controls.Add(control);// 設(shè)置其背景色((MyUserControl)control).BackColor = Color.Yellow;} 如果您猜到該問(wèn)題與輸出緩存有關(guān),那么您是正確的。正如您所看到的一樣,上述代碼示例編譯和運(yùn)行都正常,但是如果嘗試將以下語(yǔ)句(完全合法)添加到 MyUserControl.ascx 中: <%@ OutputCache Duration="5" VaryByParam="None" %> “無(wú)法將類(lèi)型為‘System.Web.UI.PartialCachingControl’的對(duì)象轉(zhuǎn)換為類(lèi)型‘MyUserControl’。” 問(wèn)題在于為用戶(hù)控件啟用輸出緩存時(shí),LoadControl 不再返回對(duì)控件實(shí)例的引用;相反,它返回對(duì) PartialCachingControl 實(shí)例的引用,而 PartialCachingControl 可能會(huì)也可能不會(huì)包裝控件實(shí)例,具體取決于控件的輸出是否被緩存。因此,如果開(kāi)發(fā)人員調(diào)用 LoadControl 以動(dòng)態(tài)加載用戶(hù)控件并且為了訪(fǎng)問(wèn)控件特定的方法和屬性而轉(zhuǎn)換控件引用,他們必須注意進(jìn)行該操作的方式,以便不管是否具有 OutputCache 指令,代碼都可以運(yùn)行。 圖 2 說(shuō)明動(dòng)態(tài)加載用戶(hù)控件以及轉(zhuǎn)換返回的控件引用的正確方法。以下是其工作原理概要: • 如果 ASCX 文件缺少 OutputCache 指令,則 LoadControl 返回一個(gè) MyUserControl 引用。Page_Load 將該引用轉(zhuǎn)換為 MyUserControl 并設(shè)置控件的 BackColor 屬性。 不管 .ascx 文件中是否具有 OutputCache 指令,圖 2中的代碼都將運(yùn)行。雖然看起來(lái)復(fù)雜一點(diǎn),但它會(huì)避免煩人的錯(cuò)誤。簡(jiǎn)單并不總是代表易于維護(hù)。 返回頁(yè)首 當(dāng)時(shí)的情況是這樣的,某個(gè)網(wǎng)站(我們?cè)诖朔Q(chēng)為 Contoso.com,它在小型 ASP.NET Web 領(lǐng)域中運(yùn)行公共電子商務(wù)應(yīng)用程序)與我的團(tuán)隊(duì)聯(lián)系,抱怨他們遇到了“跨線(xiàn)程”錯(cuò)誤。使用 Contoso.com 網(wǎng)站的客戶(hù)常常突然丟失已經(jīng)輸入的數(shù)據(jù),但卻看到另一用戶(hù)的相關(guān)數(shù)據(jù)。稍做分析即發(fā)現(xiàn),跨線(xiàn)程這個(gè)描述并不準(zhǔn)確;“跨會(huì)話(huà)”錯(cuò)誤更為貼切??雌饋?lái) Contoso.com 是在會(huì)話(huà)狀態(tài)中存儲(chǔ)數(shù)據(jù)的,由于某些原因,用戶(hù)會(huì)偶爾隨機(jī)地連接到其他用戶(hù)的會(huì)話(huà)。 我的一個(gè)團(tuán)隊(duì)成員編寫(xiě)了一個(gè)診斷工具,用來(lái)將每個(gè) HTTP 請(qǐng)求和響應(yīng)的關(guān)鍵要素(包括 Cookie 標(biāo)頭)記錄到日志中。然后,他將該工具安裝在 Contoso.com 的 Web 服務(wù)器上,并讓其運(yùn)行了幾天。結(jié)果非常明顯。大概每 100000 個(gè)請(qǐng)求中會(huì)發(fā)生一次這樣的情況:ASP.NET 正確地為全新會(huì)話(huà)分配一個(gè)會(huì)話(huà) ID 并返回 Set-Cookie 標(biāo)頭中的會(huì)話(huà) ID。然后,它會(huì)在下一個(gè)緊相鄰的請(qǐng)求中返回相同的會(huì)話(huà) ID(即,相同的 Set-Cookie 標(biāo)頭),即使該請(qǐng)求已經(jīng)與一個(gè)有效的會(huì)話(huà)相關(guān)聯(lián)并且正確提交了 Cookie 中的會(huì)話(huà) ID。實(shí)際上,ASP.NET 是隨機(jī)將用戶(hù)從他們自己的會(huì)話(huà)中切換出去并將他們連接到其他會(huì)話(huà)。
|
|
|
來(lái)自: 悟靜 > 《.net和asp.net》