網站建設中的cookies
中國信息港 QQ800015119域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設Cookies 為 Web 應用程序提供了存儲特定用戶信息的方法。例如,當一個
中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設
Cookies 為 Web 應用程序提供了存儲特定用戶信息的方法。例如,當一個用戶訪問網站的時候,你能夠使用 Cookies 來存儲該用戶的偏好或其他信息。在用戶下一次訪問網站的時候,應用程序能夠獲取這些較早前被存儲的信息。 在中國信息港同事們的陪伴下,我的進步也算明顯。!
什么是 Cookies ?
Cookies 是隨著請求連同頁面一起在 Web 服務器和瀏覽器之間來回流動的小塊文本。Web 應用程序能夠隨時在用戶訪問網站的時候讀取 Cookies 中所包含的信息。
例如,如果用戶在網站中請求頁面的時候,應用程序除了返回一個頁面之外,還返回了一個包含日期和時間的 Cookie ,在用戶的瀏覽器獲得這個頁面的時候,瀏覽器就會獲得這個 Cookie ,并把它存儲到用戶硬盤的特定目錄中。
然后,如果用戶想要再次從網站中請求該頁面,當用戶在瀏覽器中輸入 URL 的時候瀏覽器就會在本地硬盤中查找與該 URL 相關聯的 Cookie 。如果 Cookie 存在,瀏覽器就會把它連同頁面請求一起發(fā)送到網站中。這時候應用程序就能夠檢測到用戶最后一次訪問網站的日期和時間。你可能還會使用這個信息來為用戶顯示消息或者檢查日期是否過期。
Cookies 是與網站相關聯的,而不是與特定的頁面相關聯的,所以不論用戶請求網站中的哪些頁面,都將會在瀏覽器和服務器之間交換 Cookies 信息。與用戶訪問不同的網站一樣,每個網站都能夠把 Cookie 發(fā)送到用戶的瀏覽器中;而瀏覽器會把所有來自于不同網站的 Cookies 分開進行存儲。
Cookies 能夠幫助網站存儲訪問者的相關信息。通常情況下,Cookies 是在 Web 應用程序中維護連續(xù)性的一種方式,也就是說,關于狀態(tài)管理。除了在它們實際交換信息之外,瀏覽器和 Web 服務器之間連接通常都是斷開的。用戶訪問 Web 服務器時所產生的每一個請求都被視為獨立的。多數時候,只要用戶在請求頁面,它都能夠幫助 Web 服務器對用戶進行識別。例如,購物網站的 Web 服務器會始終保持對每個購物者的追蹤,從而能夠管理購物車和其他特定的用戶信息。Cookie 因此扮演了名片的角色,呈現相關的鑒定信息來輔助應用程序的運行。
Cookies 能夠用于多種用途,這些用途全部都涉及到幫助網站對于用戶的記憶。例如,某個投票管理網站可能把 Cookie 簡單地當成一個布爾值來指明用戶的瀏覽器是否已經參與投票,從而禁止該用戶的重復性投票;又如某個要求用戶登入的網站會使用 Cookie 來記錄用戶是否已經登入,從而使得該用戶不再需要重復輸入驗證信息。
Cookies 的局限性
大部分瀏覽器所支持的 Cookies 長度最多不能超過 4096 字節(jié)。因為這個限制,Cookies 最適合被用來存儲小巧的數據,最好是標識符(如用戶 ID )。用戶 ID 這時候能夠被用來識別當前用戶并從數據庫或其他數據存儲中讀取用戶信息。(請參考本文中關于存儲用戶信息的安全含意信息的[Cookies 和安全]部分。)
瀏覽器同樣限制了網站能夠存儲到用戶瀏覽器中的 Cookies 數量。大部分瀏覽器只允許每網站最多只能存儲 20 個 Cookies ;如果你嘗試存儲更多,那么最舊的 Cookies 將被廢棄。有些瀏覽器同樣提出了一個絕對限制,它們所能接受的 Cookies 數量總和不能夠超過 300(來自于所有網站的 Cookies 的總和)。
你可能遇到的另一個 Cookies 限制就是用戶能夠設置他們的瀏覽器來拒絕 Cookie 。如果你定義了一個 P3P 機密策略并把它存放在網站的根目錄,大部分瀏覽會都將接受來自網站中的 Cookies 。但是,你可能已經完全避免了 Cookies 的使用,從而使用了另一個不同的機制
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設
來存儲特定的用戶信息。存儲用戶信息的一種通用的方式就是使用會話狀態(tài),但是會話狀態(tài)又依賴于 Cookies ,與本文中的[Cookies 和會話狀態(tài)]部分所說明的一樣。
提示:更多關于在 Web 應用程序中保存用戶信息的狀態(tài)管理和狀態(tài)選項的信息,請參考:[ASP.NET 狀態(tài)管理概覽]和[ASP.NET 狀態(tài)管理的建議]。
盡管 Cookies 在應用程序中是比較實用的,但是應用程序不應該對 Cookies 的使用而產生依賴。請不要使用 Cookies 來支持關鍵特征。如果你的應用程序必須依賴于 Cookies ,你可以對瀏覽器進行測試并了解其是否接受 Cookies 的使用。請參考本文中的[檢查瀏覽器是否接受 Cookies ]部分。
寫入 Cookies
瀏覽器負責在用戶系統(tǒng)中管理 Cookies 。發(fā)送到瀏覽器的 Cookies 經過 HttpResponse 對象暴露了一個名為 Cookies 的集合。你能夠像訪問 Page 類的 Response 屬性一樣來訪問 HttpResponse 對象。任何你需要發(fā)送到瀏覽器的 Cookies 都必須被添加到這個集合中。在創(chuàng)建 Cookie 之后,你就需要為其指定 Name 和 Value 屬性。每個 Cookie 必須擁有唯一的名稱才能夠在瀏覽器中被讀取的時候被識別。因為 Cookies 是通過名稱來存儲的,兩個使用相同名稱的 Cookies 中將會有一個會被覆蓋。
你同樣可以設置 Cookie 的過期日期和時間。已過期的 Cookies 會在用戶訪問網站并且重新寫入 Cookies 的時候被瀏覽器所刪除。Cookie 的過期可以根據應用程序所決定的 Cookie 有效期來進行設置。要使 Cookie 能夠長期有效,你可以把過期日期設置成從現在所開始的后續(xù) 50 年時間。
提示:用戶能夠在任何時候清除計算機中的 Cookies 。即使你已經存儲了一個長期有效的 Cookie ,用戶還是能夠自行決定來刪除所有的 Cookies ,這樣一來,所有被存儲在 Cookies 中的設置都將被消毀。
如果你沒有設置 Cookie 的有效期,Cookie 仍然能夠被創(chuàng)建,但是并不會被存儲到用戶的硬盤中。相反,這種 Cookie 是作為用戶會話信息的一部分而被維護的。當用戶關閉瀏覽器,Cookie 也隨之被廢棄。類似于這種非持續(xù)保持的 Cookie 在只需要短暫存儲信息或者出于安全原因而不應該寫入到客戶端計算機的硬盤中的時候是比較有用的。例如,非持續(xù)保持的 Cookies 適用于用戶在公共計算機上使用,或者你不想把 Cookie 寫入到硬盤的情況下使用。
你能夠使用多種方法把 Cookies 寫入到 Cookies 集合中。如下實例說明了兩個寫入 Cookies 的方式: Response.Cookies["userName"].Value = "patrick";
Response.Cookies["userName"].Expires = DateTime.Now.AddDays(1);
HttpCookie aCookie = new HttpCookie("lastVisit");
aCookie.Value = DateTime.Now.ToString();
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 aCookie.Expires = DateTime.Now.AddDays(1);
Response.Cookies.Add(aCookie);
該實例在 Cookies 集合中添加了兩個 Cookies ,一個被命名為 userName 而另一個被命名為 lastVisit 。至于第一個 Cookie ,直接設置了 Cookies 集合的值。你可以使用這個方法來在集合中添加值,因為 Cookies 是繼承自 NameObjectCollectionBase 類型的一個專用集合。 至于第二個 Cookie ,代碼創(chuàng)建了 HttpCookie 類型的一個對象實例,并設置它的屬性,然后通過 Add 方法把它添加到 Cookies 集合中。當你實例化一個 HttpCookie 對象的時候,你必須把 Cookie 的名稱作為構造器的一個部分進行傳遞。
這兩個實例都完成了把 Cookie 寫入到瀏覽器的相同任務。在這兩個方法中,有效期屬性值的類型必須是 DateTime 。但是,lastVisited 中的值同樣也是一個表示時間日期的值。因為所有 Cookie 的值都應該被存儲成字符串格式,所以日期時間值會被自動轉換成字符串。 擁有多個值的 Cookies
你能夠在 Cookie 中存儲單獨的值,如用戶名稱或最后訪問的時間。你同樣可以在單獨的 Cookie 中存儲多個 Name/Value 數據對。Name/Value 數據對被引用成子鍵。(子鍵展開之后的格式與 URL 中的查詢字符串相似。)例如,作為創(chuàng)建名為 userName 和 lastVisit 的兩個分開的 Cookies 的替代,你可以創(chuàng)建名為 userInfo 的單獨 Cookie 來包含子鍵 userName 和 lastVisit 。
你可能出于幾個原因而使用子鍵。首先,它對于把相關信息或類似信息放進單獨的 Cookie 中是比較方便的。另外,因為所有信息都在單獨的 Cookie 中,Cookie 的參數(如有效期)會被應用到所有信息。(相反,如果你需要為不同類型的信息指定不同的有效期,那么你就應該把這些信息存儲到單獨的 Cookies 中。)
使用子鍵的 Cookie 同樣有助于你突破 Cookie 文件尺寸的限制。與先前在[Cookie 的局限性]部分中所描述的一樣,Cookies 的尺寸上限通常是 4096 個字節(jié),并且你不能為單個網站存儲超過 20 個以上的 Cookies 。通過使用包含子鍵的單獨 Cookie ,你可以減少 Cookies 的使用數量。另外,單獨的 Cookie 中最多只能出現 50 個字符(有效期信息,等等),加上保存在其中的值的長度,全部總和相加后接近 4096 個字節(jié)。如果你使用 5 個子鍵來取代 5 個分離的 Cookies ,那么你能夠在每個 Cookies 中保存接近 200 個字節(jié)的數據。
要創(chuàng)建包含子鍵的 Cookie ,你就要使用不同的語法來寫入單獨的 Cookie 。下列實例說明了寫入相同 Cookie (分別包含了兩個子鍵)的兩個方式: Response.Cookies["userInfo"]["userName"] = "patrick";
Response.Cookies["userInfo"]["lastVisit"] = DateTime.Now.ToString();
Response.Cookies["userInfo"].Expires = DateTime.Now.AddDays(1);
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 HttpCookie aCookie = new HttpCookie("userInfo");
aCookie.Values["userName"] = "patrick";
aCookie.Values["lastVisit"] = DateTime.Now.ToString();
aCookie.Expires = DateTime.Now.AddDays(1);
Response.Cookies.Add(aCookie);
控制 Cookie 的作用范圍
默認時,網站的所有 Cookies 都一起被存儲在客戶端,并且所有 Cookies 連同網站的任何請求一起被發(fā)送到服務器。換句話說,網站中的每個頁面都能夠為網站獲取所有的 Cookies 。但是,你能夠通過兩個方式來設置 Cookies 的作用范圍:
把 Cookies 的作用范圍限制到服務器的目錄,從而允許你把 Cookies 限制到網站的某個應用程序。
設置域的作用范圍,能夠允許你指定域中的哪些子域能夠訪問 Cookie 。
把 Cookies 限制到目錄或應用程序
要把 Cookies 限制到服務器的目錄,請設置 Cookie 的 Path 屬性,如下實例所示: HttpCookie appCookie = new HttpCookie("AppCookie");
appCookie.Value = "written " DateTime.Now.ToString();
appCookie.Expires = DateTime.Now.AddDays(1);
appCookie.Path = "/Application1";
Response.Cookies.Add(appCookie);
提示:你同樣可以通過直接添加到 Cookies 集合的方式來寫入 Cookies ,如前面的實例所示。 路徑既能夠位于網站的物理根目錄中也能夠位于虛擬根目錄中。結果將會是 Cookie 只對于目錄或者虛擬根 Application1 中的頁面可用。例如,如果你的網址是www.cncnc.com.cn ,在前面的實例中所創(chuàng)建的 Cookie 將只對于路徑 http:// www.cncnc.com.cn/Application1/ 以及其下所有子目錄中的頁面可用。但是,該 Cookie 對于其他應用程序(如 http:// www.cncnc.com.cn/Application2/ 或者 /)中的頁面則是不可用的。 提示:部分瀏覽器中的路徑對大小寫字母是敏感的。你無法控制用戶如何在他們的瀏覽器中輸入 URL ,但是如果你的應用程序依賴于 Cookies 來約束特定的路徑,請確保你所創(chuàng)建的
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 任何超級鏈接中的 URL 能夠與 Path 屬性值中的大小寫相匹配。
限制 Cookie 的域范圍
默認時,Cookies 是與特定的域相關聯的。例如,如果你的網站是 www.contoso.com ,你寫入的 Cookies 會在用戶從網站中請求任何頁面的時候被發(fā)送到服務器。(可能不包括有特定的路徑值的 Cookies 。)如果你的網站中還擁有子域(例如,contoso.com 、sales.contoso.com 、以及 support.contoso.com ),那么你可以把特定的子域與 Cookies 相關聯。要這樣做,請設置 Cookie 的 Domain 屬性,如實例所示: Response.Cookies["domain"].Value = DateTime.Now.ToString();
Response.Cookies["domain"].Expires = DateTime.Now.AddDays(1);
Response.Cookies["domain"].Domain = "support.contoso.com";
當按照這樣設置域之后,Cookie 將只對于特定域中的頁面可用。你同樣能夠使用 Domain 屬性來創(chuàng)建一個能夠在多個子域之間被共享的 Cookie ,如下實例所示: Response.Cookies["domain"].Value = DateTime.Now.ToString();
Response.Cookies["domain"].Expires = DateTime.Now.AddDays(1);
Response.Cookies["domain"].Domain = "contoso.com";
Cookie 這時候將與 sales.contoso.com 和 support.contoso.com 域一樣對于主域是可用的。 讀取 Cookies
在瀏覽器向服務器發(fā)送請求的時候,它會把 Cookies 連同請求一起發(fā)送到服務器。在你的 ASP.NET 應用程序中,你能夠使用 HttpRequest 對象來讀取 Cookies ,該對象是作為 Page 類的 Request 屬性出現的。HttpRequest 對象的結構實質上與 HttpResponse 對象一樣,所以你能夠使用把 Cookies 寫入到 HttpResponse 對象類似的方式從 HttpRequest 對象中讀出 Cookies 。如下代碼實例說明了獲取 Cookie (名為 userName )的值并顯示到一個 Label 控件中的兩種方式: if(Request.Cookies["userName"] != null)
Label1.Text = Server.HtmlEncode(Request.Cookies["userName"].Value);
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 if(Request.Cookies["userName"] != null)
{
HttpCookie aCookie = Request.Cookies["userName"];
Label1.Text = Server.HtmlEncode(aCookie.Value);
}
在嘗試獲取 Cookie 的值之前,你應該先確定該 Cookie 已經存在;如果該 Cookie 并不存在,你將會得到一個 NullReferenceException 異常。注意到在顯示 Cookie 的內容之前已經調用了 HtmlEncode 方法進行編碼。這使得惡意用戶無法在 Cookie 中添加可執(zhí)行腳本。關于 Cookie 安全性的更多信息,請參考:[Cookies 和安全]。
提示:因為不同的瀏覽器存儲 Cookies 的方式都各不相同,相同計算機中的瀏覽器無法讀取其他類型瀏覽器所設置的 Cookies 。例如,如果你使用 Internet Explorer 來測試頁面,然后又使用另一個不同的瀏覽器再次進行測試,第二個瀏覽器將無法找到由 Internet Explorer 所保存的 Cookies 。
從 Cookie 中讀取子鍵的值與設置的時候相似。如下代碼實例說明了獲取子鍵的值的一種方式: if(Request.Cookies["userInfo"] != null)
{
Label1.Text =
Server.HtmlEncode(Request.Cookies["userInfo"]["userName"]);
Label2.Text =
Server.HtmlEncode(Request.Cookies["userInfo"]["lastVisit"]);
}
在前面的實例中,代碼讀取子鍵 lastVisit 中的值,該值在前面的實例中被設置成一個被呈現成字符串的 DateTime 值。Cookies 把值存儲成為字符串,所以如果你需要把 lastVisit 的值當成日期對象來使用,你就應該把它轉換成適當的類型,如下實例所示:
DateTime dt;
dt = DateTime.Parse(Request.Cookies["userInfo"]["lastVisit"]);
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設
Cookie 中的子鍵被類型化成為 NameValueCollection 類型的一個集合。因此,獲取單獨子鍵的另一種方式就是先獲取子鍵集合然后通過名稱來提取子鍵的值,如下實例所示: if(Request.Cookies["userInfo"] != null)
{
System.Collections.Specialized.NameValueCollection
UserInfoCookieCollection;
UserInfoCookieCollection = Request.Cookies["userInfo"].Values;
Label1.Text =
Server.HtmlEncode(UserInfoCookieCollection["userName"]);
Label2.Text =
Server.HtmlEncode(UserInfoCookieCollection["lastVisit"]);
}
改變 Cookie 的過期時間
瀏覽器負責管理 Cookies ,并且 Cookie 的過期時間和日期有助于瀏覽器對所存儲的 Cookies 進行管理。因此,雖然你能夠讀取 Cookie 的名稱和值,但是你無法讀取 Cookie 的過期日期和時間。在瀏覽器把 Cookie 信息發(fā)送到服務器的時候,瀏覽器中并不包括有效期信息。(Cookie 的 Expires 屬性始終返回為零的日期值。)如果你關心 Cookie 的過期時間,你就應該把它重置,具體操作被包含在本文的[更改并刪除 Cookies ]部分。
提示:在 Cookie 被發(fā)送到瀏覽器之前,你能夠讀取 Cookie 的 Expires 屬性(該屬性在 HttpResponse 對象中被設置)。但是,你不能從 HttpRequest 對象中反向獲取過期時間。
讀取 Cookie 集合
第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
,中國信息港 QQ800015119
域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設
你偶爾可能需要讀取所有的 Cookies 并為頁面可用。要把所有 Cookies 的名稱和值讀取到頁面中,你可以如下代碼對 Cookies 集合進行循環(huán)。 System.Text.StringBuilder output = new System.Text.StringBuilder();
HttpCookie aCookie;
for(int i=0; i { aCookie = Request.Cookies[i]; output.Append("Cookie name = " Server.HtmlEncode(aCookie.Name) " output.Append("Cookie value = " Server.HtmlEncode(aCookie.Value) " } Label1.Text = output.ToString(); 提示:當你運行這段代碼的時候,你可能會看到一個名為 ASP.NET_SessionId 的 Cookie 。也就是 ASP.NET 用來為你的會話而存儲唯一標識符的 Cookie 。這個會話 Cookie 不會被保持到你的硬盤中。更多關于會話 Cookies 的信息,請參考本文中的[Cookies 和會話狀態(tài)]部分。 前面實例的一個局限性就是如果 Cookie 擁有子鍵,執(zhí)行結果會把子鍵顯示成一個 Name/Value 字符串。你能夠讀取 Cookie 的 HasKeys 屬性來檢測 Cookie 中是否含有子鍵。如果是,你就能夠讀取子鍵的集合并獲取單獨的子鍵名稱和值。你能夠從 Values 集合中直接使用索引值來讀取子鍵的值。相應的子鍵名稱在 Values 集合的 AllKeys 成員中是可用的,從而返回一個字符串數組。你同樣可以使用 Values 集合中的 Keys 成員。但是,AllKeys 屬性在第一次被訪問的時候就會被緩存起來。恰好相反,Keys 屬性則在每次被訪問的時候都建立一個新的數組。正是因為這個原因,AllKeys 屬性在相同頁面請求環(huán)境的后繼訪問中是非常高效的。 第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥ 中國信息港 QQ800015119 域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 如下實例說明了對前面實例的修正。它使用 HasKeys 屬性對子鍵進行測試,如果子鍵被檢測到,那么該實例就從 Values 集合中獲取子鍵: for(int i=0; i { aCookie = Request.Cookies[i]; output.Append("Name = " aCookie.Name " if(aCookie.HasKeys) { for(int j=0; j { subkeyName = Server.HtmlEncode(aCookie.Values.AllKeys[j]); subkeyValue = Server.HtmlEncode(aCookie.Values[j]); output.Append("Subkey name = " subkeyName " output.Append("Subkey value = " subkeyValue " } } else { output.Append("Value = " Server.HtmlEncode(aCookie.Value) " } } Label1.Text = output.ToString(); 第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥ 中國信息港 QQ800015119 域名注冊 服務器托管 VPS主機 服務器租用 海外空間 數據庫 網站建設 或者,你也可以像如下實例一樣把子鍵當成 NameValueCollection 對象來提?。? System.Text.StringBuilder output = new System.Text.StringBuilder(); HttpCookie aCookie; string subkeyName; string subkeyValue; for (int i = 0; i < Request.Cookies.Count; i ) { aCookie = Request.Cookies[i]; output.Append("Name = " aCookie.Name " if (aCookie.HasKeys) { System.Collections.Specialized.NameValueCollection CookieValues = aCookie.Values; string[] CookieValueNames = CookieValues.AllKeys; for (int j = 0; j < CookieValues.Count; j ) { subkeyName = Server.HtmlEncode(CookieValueNames[j]); subkeyValue = Server.HtmlEncode(CookieValues[j]); 第一萬維網【www.01www.com 】域名優(yōu)惠活動:com net org 新注冊49¥,續(xù)費59¥
");
");
");
");
");
");
");