Cookie 的基本知识.docx
《Cookie 的基本知识.docx》由会员分享,可在线阅读,更多相关《Cookie 的基本知识.docx(17页珍藏版)》请在冰点文库上搜索。
![Cookie 的基本知识.docx](https://file1.bingdoc.com/fileroot1/2023-5/11/2da646dd-140d-48e9-a34f-4fcdb2fac385/2da646dd-140d-48e9-a34f-4fcdb2fac3851.gif)
Cookie的基本知识
ASP.NET中Cookie的基本知识
MikePope
VisualBasicUserEducation
MicrosoftCorporation
2003年1月
摘要:
本文介绍如何使用VisualBasic在ASP.NETWeb应用程序中读写HTTPCookie。
适用于:
∙ASP.NET
∙Microsoft®VisualStudio®.NET
∙Web窗体
读者范围:
初级Web程序员
目录
∙简介
∙什么是Cookie?
∙Cookie的限制
∙编写Cookie
∙多值Cookie(子键)
∙控制Cookie的有效范围
∙读取Cookie
∙修改和删除Cookie
∙Cookie和安全性
∙检查浏览器是否接受Cookie
∙Cookie和会话状态
简介
Cookie为Web应用程序保存用户相关信息提供了一种有用的方法。
例如,当用户访问您的站点时,您可以利用Cookie保存用户首选项或其他信息,这样,当用户下次再访问您的站点时,应用程序就可以检索以前保存的信息。
本文概要介绍Cookie在ASP.NET应用程序中的应用,为您展示在ASP.NET中应用Cookie的技术细节,例如编写Cookie、然后再读取它们。
同时,还将为您介绍Cookie的各种特性和各种特殊情况,以及ASP.NET对Cookie的支持。
什么是Cookie?
Cookie是一小段文本信息,伴随着用户请求和页面在Web服务器和浏览器之间传递。
用户每次访问站点时,Web应用程序都可以读取Cookie包含的信息。
假设在用户请求访问您的网站上的某个页面时,您的应用程序发送给该用户的不仅仅是一个页面,还有一个包含日期和时间的Cookie。
用户的浏览器在获得页面的同时还得到了这个Cookie,并且将它保存在用户硬盘上的某个文件夹中。
以后,如果该用户再次访问您站点上的页面,当该用户输入URL时,浏览器就会在本地硬盘上查找与该URL相关联的Cookie。
如果该Cookie存在,浏览器就将它与页面请求一起发送到您的站点,您的应用程序就能确定该用户上一次访问站点的日期和时间。
您可以根据这些信息向用户发送一条消息,也可以检查过期时间或执行其他有用的功能。
Cookie是与Web站点而不是与具体页面关联的,所以无论用户请求浏览站点中的哪个页面,浏览器和服务器都将交换的Cookie信息。
用户访问其他站点时,每个站点都可能会向用户浏览器发送一个Cookie,而浏览器会将所有这些Cookie分别保存。
以上就是Cookie的基本工作原理。
那么,Cookie有哪些用途呢?
最根本的用途是Cookie能够帮助Web站点保存有关访问者的信息。
更概括地说,Cookie是一种保持Web应用程序连续性(即执行“状态管理”)的方法。
浏览器和Web服务器除了在短暂的实际信息交换阶段以外总是断开的,而用户向Web服务器发送的每个请求都是单独处理的,与其他所有请求无关。
然而在大多数情况下,都有必要让Web服务器在您请求某个页面时对您进行识别。
例如,购物站点上的Web服务器跟踪每个购物者,以便站点能够管理购物车和其他的用户相关信息。
因此Cookie的作用就类似于名片,它提供了相关的标识信息,可以帮助应用程序确定如何继续执行。
使用Cookie能够达到多种目的,所有这些目的都是为了使Web站点记住您。
例如,一个实施民意测验的站点可以简单地利用Cookie作为布尔值,表示您的浏览器是否已经参与了投票,从而避免您重复投票;而那些要求用户登录的站点则可以通过Cookie来确定您是否已经登录过,这样您就不必每次都输入凭据。
有关Cookie的更多背景信息,建议您阅读VerizonWeb站点中的“HowInternetCookiesWork”一文,地址为Cookie以及Cookie是如何在浏览器和服务器之间交换信息的,他还全面总结了Cookie涉及的隐私问题。
顺便问一下,您是否想知道它们为什么被称作“Cookie”?
JargonFile(又称为“TheNewHacker'sDictionary”)版本4.3.3对这一术语的词源给出了准确的定义和合理的解释。
您可以在http:
//www.catb.org/~esr/jargon/jargon.html#cookie(英文)找到相关的条目。
在此后的内容中,本文将假设您已经知道什么是Cookie,并且假设您已经清楚为什么要在ASP.NET应用程序中使用Cookie。
Cookie的限制
在开始讨论Cookie的技术细节之前,我想先介绍一下Cookie应用的几条限制。
大多数浏览器支持最多可达4096字节的Cookie,如果要将为数不多的几个值保存到用户计算机上,这一空间已经足够大,但您不能用一个Cookie来保存数据集或其他大量数据。
在实际应用中,您可能并不希望在Cookie中保存大量的用户信息,而只希望保存用户编号或其他标识符。
之后,当用户再次访问您的站点时,您就可以使用该用户ID在数据库中查找用户的详细信息。
(有关保存用户信息的说明,请参阅Cookie和安全性。
)
浏览器还限制了您的站点可以在用户计算机上保存的Cookie数。
大多数浏览器只允许每个站点保存20个Cookie。
如果试图保存更多的Cookie,则最先保存的Cookie就会被删除。
还有些浏览器会对来自所有站点的Cookie总数作出限制,这个限制通常为300个。
您最可能遇到的Cookie限制是:
用户可以设置自己的浏览器,拒绝接受Cookie。
您很难解决这个问题,除非完全不使用Cookie而是通过其他机制来保存用户相关信息。
保存用户信息的一种常用方法是会话状态,但会话状态又依赖于Cookie。
这一点在后面的Cookie和会话状态中阐述。
注意:
有关状态管理和Web应用程序中用于保存信息的选项的详细信息,请参阅IntroductiontoWebFormsState(英文)和StateManagementRecommendations(英文)。
更一般的经验很可能是,尽管Cookie在应用程序中非常有用,应用程序也不应该依赖于能够保存Cookie。
利用Cookie可以做到锦上添花,但不要利用它们来支持关键功能。
如果您的应用程序必须使用Cookie,则您可以通过测试来确定浏览器是否接受Cookie。
我在本文后面的检查浏览器是否接受Cookie一节中简单介绍了一种测试方法。
编写Cookie
您可以利用页面的Response(英文)属性来编写Cookie,该属性提供的对象使用户可以将信息添加到由页面向浏览器呈现的信息中。
Response对象支持一个名为Cookies(英文)的集合,您可以向其中添加要写入浏览器的Cookie。
注意:
下面要讨论的Response对象和Request对象分别是包含HttpResponse(英文)和HttpRequest(英文)类实例的页面的属性。
要在文档中查找Response和Request的信息,请参阅HttpResponse和HttpRequest下的内容。
在创建Cookie时,您需要指定几个值。
最初,您要指定Cookie的名称和其中保存的值。
您可以创建多个Cookie,每个Cookie都必须具有唯一的名称,以便日后读取时识别。
(Cookie是按名称保存的,所以如果您创建了两个名称相同的Cookie,后保存的那一个将覆盖前一个。
)
您可能还希望指定Cookie的过期日期和时间。
Cookie一般都写入到用户的磁盘,然后可能一直都留在磁盘上。
因此,您可以指定Cookie过期的日期和时间。
当用户再次访问您的站点时,浏览器会先检查您站点的Cookie集合,如果某个Cookie已经过期,浏览器不会把这个Cookie随页面请求一起发送给服务器,而是删除这个已经过期的Cookie。
(您的站点可能已经在用户计算机上写入了多个Cookie,每个Cookie都有各自的过期日期和时间。
)请注意,由浏览器负责管理硬盘上的Cookie,这将影响您在应用程序中对Cookie的使用,我很快会介绍这方面的内容。
一个Cookie的有效期应为多长?
这取决于Cookie的用途,换句话说,取决于您的应用程序需要Cookie值保持有效的时间有多长。
如果利用Cookie统计网站的访问者,您可以把有效期设置为1年,如果某个用户已有一年时间未访问您的站点,则可以把该用户当作新的访问者;如果利用Cookie来保存用户的首选项,则可以把其设置为永远有效(例如50年后到期),因为定期重新设置首选项对用户而言是比较麻烦的。
有时,您可能需要编写在数秒或数分钟内即过期的Cookie。
在本文后面的检查浏览器是否接受Cookie一节中,我列举了一个示例,该示例中创建的Cookie的实际有效期就只有几秒。
注意:
不要忘记用户随时可以删除自己计算机上的Cookie,所以即使您保存了长期有效的Cookie,用户也可以自行决定将其全部删除,同时清除保存在Cookie中的所有设置。
如果没有设置Cookie的有效期,还是可以创建Cookie,但它不会保存到用户的硬盘上,而是会成为用户会话信息的一部分。
如果用户关闭浏览器或会话超时,该Cookie就会被删除。
这种非永久性的Cookie很适合用来保存只需短时间保存的信息,或者保存由于安全原因不应该写入客户计算机磁盘的信息。
例如,如果用户使用的是一台公用计算机,而您不希望把Cookie写入这种计算机的磁盘上,这时就可以使用非永久性的Cookie。
您可以通过多种方法把Cookie添加到Response.Cookies集合中。
以下示例介绍了两种完成此任务的方法:
Response.Cookies("userName").Value="mike"
Response.Cookies("userName").Expires=DateTime.Now.AddDays
(1)
DimaCookieAsNewHttpCookie("lastVisit")
aCookie.Value=DateTime.Now.ToString
aCookie.Expires=DateTime.Now.AddDays
(1)
Response.Cookies.Add(aCookie)
该示例向Cookies集合中添加了两个Cookie,一个称为“userName”,另一个称为“lastVisit”。
对于第一个Cookie,我直接设置了Response.Cookies集合的值。
您可以使用这种方法向集合中添加值,因为Response.Cookies是从NameObjectCollectionBase(英文)类型的特殊集合派生得到的。
对于第二个Cookie,我创建了Cookie对象的一个实例(HttpCookie[英文]类型),并设置了其属性,然后通过Add方法把它添加到Response.Cookies集合。
实例化HttpCookie对象时,您必须把Cookie名称作为构造函数的一部分进行传递。
这两个示例完成了相同的任务,即向浏览器写入一个Cookie。
您要采用哪种方法主要取决于您的个人喜好。
您可能会发现第二种方法在设置Cookie属性方面要稍微容易一些,但同时您也会注意到两者的差别并不是很大。
在这两种方法中,有效期值必须为DateTime类型。
而“lastVisited”值也是日期/时间值。
但在这种情况下,我必须把日期/时间值转换为字符串,因为Cookie中的任何值最终都是以字符串的形式保存的。
查看您的Cookie
您可能会发现,了解创建Cookie的效果会对您很有帮助。
而查看Cookie是比较容易的,因为它们都是文本文件,关键在于您能找到它们。
不同的浏览器保存Cookie的方式也不同。
我将介绍InternetExplorer是如何保存Cookie的。
如果您使用的是其他浏览器,请查看该浏览器的帮助,以了解有关Cookie处理方面的知识。
查看Cookie的一个简便方法是让InternetExplorer为您查找。
在InternetExplorer中,从“工具”菜单中选择“Internet选项”,在“常规”选项卡中单击“设置”,然后单击“查看文件”。
InternetExplorer将打开一个窗口,显示所有的临时文件,包括Cookie。
在窗口中查找以“Cookie:
”开头的文件或查找文本文件。
双击一个Cookie,在默认的文本文件中打开它。
您也可以在硬盘上查找Cookie的文本文件,从而打开Cookie。
InternetExplorer将站点的Cookie保存在文件名格式为@.txt的文件中,其中是您的帐户名。
例如,如果您的名称为mikepope,您访问的站点为,那么该站点的Cookie将保存在名为mikepope@www.contoso.txt的文件中。
(该文件名可能包含一个顺序的编号,如mikepope@www.contoso[1].txt。
)
这个Cookie文本文件是与用户相关的,所以会按照帐户分别保存。
例如,在WindowsXP中,您可以在如下所示的目录中找到Cookie文件:
c:
\DocumentsandSettings\\Cookies
要查找最新创建的Cookie,可以按修改日期对目录内容进行排序,并查找最近修改的文件。
您可以使用文本编辑器打开Cookie。
如果该文件包含多个Cookie,这些Cookie之间将用星号(*)分隔。
每个Cookie的第一行是Cookie的名称,第二行是值,其余各行则包含Cookie的日常处理信息,例如过期日期和时间。
Cookie中还有一个简单的校验和,如果更改Cookie名称或值的长度,浏览器就会检测到修改并删除该Cookie。
多值Cookie(子键)
以上示例为每个要保存的值(用户名、上次访问时间)都使用了一个Cookie。
您也可以在一个Cookie中保存多个名称/值对。
名称/值对也称作“键”或“子键”,具体取决于您读取的内容。
(如果您熟悉URL的结构,就会发现子键与其中的查询字符串非常相象。
)例如,如果不希望创建名为“userName”和“lastVisit”的两个单独的Cookie,可以创建一个名为“userInfo”的Cookie,并使其包含两个子键:
“userName”和“lastVisit”。
有很多原因会让我们用子键来代替单独的Cookie。
最显而易见的是,把相关或类似的信息放在一个Cookie中会比较有条理。
另外,由于所有信息都在一个Cookie中,所以诸如有效期之类的Cookie属性就适用于所有信息。
(当然,如果要为不同类型的信息指定不同的过期日期,就应该把信息保存在单独的Cookie中。
)
带有子键的Cookie还可以帮助您减小Cookie的大小。
如前面的Cookie的限制一节所述,Cookie的总大小限制在4096字节以内,而且不能为一个网站保存超过20个Cookie。
利用带子键的单个Cookie,站点的Cookie数量就不会超过20个的限制。
此外,一个Cookie会占用大约50个字符的基本空间开销(用于保存有效期信息等),再加上其中保存的值的长度,其总和接近4K的限制。
如果使用五个子键而不是五个单独的Cookie,您可以省去四个Cookie的基本空间开销,总共能节省大约200个字节。
要创建带子键的Cookie,您可以使用用于编写单个Cookie的各种语法。
以下示例显示了编写同一Cookie的两种不同方法,其中的每个Cookie都带有两个子键:
Response.Cookies("userInfo")("userName")="mike"
Response.Cookies("userInfo")("lastVisit")=DateTime.Now.ToString
Response.Cookies("userInfo").Expires=DateTime.Now.AddDays
(1)
DimaCookieAsNewHttpCookie("userInfo")
aCookie.Values("userName")="mike"
aCookie.Values("lastVisit")=DateTime.Now.ToString
aCookie.Expires=DateTime.Now.AddDays
(1)
Response.Cookies.Add(aCookie)
控制Cookie有效范围
默认情况下,一个站点的全部Cookie都一起保存在客户机上,而且所有这些Cookie都会随着对该站点发送的请求一起发送到服务器,也就是说,站点的每个页面都能得到该站点的所有Cookie。
但有时候,您可能希望Cookie更具有针对性,这时,您可以通过两种方法设置Cookie的有效范围:
∙把Cookie的有效范围限制在服务器上的一个文件夹中,实际上这样就将Cookie限制到站点上的某个应用程序。
∙把有效范围设置为某个域,从而允许您指定域中的哪些子域可以访问Cookie。
将Cookie限制到某个文件夹或应用程序
要将Cookie限制到服务器上的某个文件夹,请按如下方法设置Cookie的Path属性:
DimappCookieAsNewHttpCookie("AppCookie")
appCookie.Value="written"&Now.ToString
appCookie.Expires=Now.AddDays
(1)
appCookie.Path="/Application1"
Response.Cookies.Add(appCookie)
当然,您也可以通过直接设置Response.Cookies来编写Cookie,如前文所述。
路径可以是站点根目录下的物理路径,也可以是虚拟根目录。
这样一来,Cookie就只能用于Application1文件夹或虚拟根目录中的页面。
例如,如果您的站点名为,则前面示例中生成的Cookie就只能用于路径为的页面以及该文件夹下的所有页面,而不适用于其他应用程序中的页面,如或下的页面。
提示:
通过对InternetExplorer和Mozilla浏览器进行测试发现,此处使用的路径是区分大小写的。
一般而言,Windows服务器上的URL不区分大小写,但这种情况例外。
您无法控制用户如何在浏览器中输入URL,但是,如果您的应用程序依赖于与特定路径相关的Cookie,则请确保您所创建的所有超链接中的URL与Path属性值的大小写相匹配。
将Cookie的有效范围限制到域
默认情况下,Cookie与特定的域相关联。
例如,如果您的站点是,那么当用户向该站点请求页面时,您编写的Cookie就被发送到服务器。
(有特定路径值的Cookie除外,我在上一节刚刚解释过。
)如果您的站点有子域(例如、和),就可以把Cookie同特定的子域相关联。
为此,需要设置Cookie的Domain属性,如下所示:
Response.Cookies("domain").Value=DateTime.Now.ToString
Response.Cookies("domain").Expires=DateTime.Now.AddDays
(1)
Response.Cookies("domain").Domain=""
如果按照这种方式设置域,则Cookie只能用于指定子域中的页面。
您也可以利用Domain属性来创建可在多个子域中共享的Cookie。
例如,对域进行如下设置:
Response.Cookies("domain").Value=DateTime.Now.ToString
Response.Cookies("domain").Expires=DateTime.Now.AddDays
(1)
Response.Cookies("domain").Domain=""
这样,该Cookie就可用于主域、和。
读取Cookie
当浏览器向服务器发送请求时,该服务器的Cookie会与请求一起发送。
在ASP.NET应用程序中,您可以使用Request对象来读取Cookie。
Request对象的结构与Response对象的结构基本相同,所以从Request对象中读取Cookie的方法与向Response对象中写入Cookie的方法非常类似。
以下示例显示了两种方法,目的都是获取名为“username”的Cookie的值并将值显示在Label控件中:
IfNotRequest.Cookies("userName")IsNothingThen
Label1.Text=Server.HtmlEncode(Request.Cookies("userName").Value)
EndIf
IfNotRequest.Cookies("userName")IsNothingThen
DimaCookieAsHttpCookie=Request.Cookies("userName")
Label1.Text=Server.HtmlEncode(aCookie.Value)
EndIf
在获取Cooki