Zope中Cookie的使用 - Zope编程 - 李迎辉

(这条文章已经被阅读了 52 次) 时间:2001-12-07 09:40:17 来源:李迎辉 (limodou) 原创-IT

笔者在前面做过一个翻译与评论的网站,其中允许用户输入自已的一些信息,如:姓名、邮件和主页。并且可以保存以来,以便下次使用。但是也发现一个问题:当关闭浏览器时,再打开时,以前可以保留的信息统统没有了。笔者明明用了Cookie技术的,为什么会这样。经过对RFC2109(HTTP State Management Mechanism)的分析,原来当使用Cookie时,没有指明失效期时,缺省地,当用户退出时,Cookie自动失效。难怪只要不关闭浏览器,Cookie的设置都是有效的。只要一关闭浏览器,Cookie保存的值全都不见了。如果想让用户信息长期有效,那么我们只能通过设置Cookie的失效期了。

Cookie如何设置呢?很简单,Zope提供的RESPONSE中提供了setCookie方法,调用它必须提供两个参数:变量名和变量值。其它Cookie的附加属性,只要通过关键字参数传入即可。如:

    <dtml-call expr="RESPONSE.setCookie('test', 'hello')">

这是一个在DTML标记中的调用。如果你只是想在不关闭浏览器时有效,这样就可以了。但如果想长期有效,还应该提供expires参数才可以(本来Cookie中还有Max-Age参数,感到它应该挺方便的,但是在Python中,它会将Max-Age看成一个表达式,就是因为’-‘号造成的,因此会失败。我想,可能可以通过设置头信息来解决,但没有再试验了。如果你有兴趣,可以试一试。)。那么expires的值应该是一个符合RFC822的日期格式。下面我们先看一看,如何生成这么一个日期格式。

在Zope中提供了DateTime对象,通过看DateTime的帮助,我们可以看到,它提供了一个rfc822()的函数,那么用它就可以了。如显示当前时间,用DTML标记来写,可以为:

    <dtml-var expr="_.DateTime().rfc822()">

结果可能是:

    Thu, 06 Dec 2001 19:20:36 GMT+8

这里,’_’表示DTML的名字空间。我们不可以直接使用DateTime对象。因为它不是一个可以获取(acquisition)的对象,它存在于DTML名字空间中。你可以使用’_’来使用DTML名字空间。再看上面的结果,最后有一个’+8’,它表明我们与格林威治时间相差8个小时。而且它并不是Cookie所要求的时间写法。不应该有后面的’+8’。于是我们直接使用格林威治时间(GMT)。使用:

    <dtml-var expr="_.DateTime().toZone('GMT').rfc822()">

这样结果可能是:

    Thu, 06 Dec 2001 11:20:36 GMT

的确是没有了’+8’,但时间并不是当地时间。不过没有关系,一样可以用。但当前时间并不是我们想要的,我们要的是当前时间的未来某个时间,怎么办?DateTime对象是可以直接做加法的,做加法后仍返回一个DateTime对象。如:

    <dtml-var expr="(_.DateTime()+1).toZone('GMT').rfc822()">

那么结果可能是:

    Fri, 07 Dec 2001 11:20:36 GMT

如果你仔细观察,你会发现,时间增加了一天。为什么?于是笔者查看了DateTime.py源程序,发现,原来它的确是以天来计算的。因此+1就是加一天。如果加0.1,就是加0.1天。如果想加一秒呢?那就应该是加1/86400天。其中86400为一天的秒数。当然这样并不精确,我们可以使用另一种方法。DateTime对象还提供了timeTime()方法,它可以返回以秒计算的时间。同时DateTime对象的构造函数可以支持传入一个秒的参数。因此,如果想要表示当前时间的后一秒,我们可以:

    <dtml-var expr="_.DateTime(_.DateTime().timeTime()+1).toZone('GMT').rfc822()">

不过,如果你的确想以天来计,那么使用DateTime的加法就可以了。

好了,时间会表示了,设置Cookie就容易了:

    <dtml-call expr="RESPONSE.setCookie('test', 'hello', expires="_.DateTime(_.DateTime().timeTime()+1).toZone('GMT').rfc822()">

这句话表示,设置一个Cookie变量test=hello,失效期是一天。

当然对于Cookie还有其它的一些参数,如Path,Domain,Comment,Max-Age(前面说了可能有问题),secure,Version等,因为用的不多,就不再说了。

上面所举的例子,都是以DTML标记来实现的,那么在Python Script中实现,该如何做呢?下面举一个例子,大家一看就应该知道了:

    request = container.REQUEST
    RESPONSE =  request.RESPONSE
    etime=(DateTime()+365).toZone('GMT').rfc822()
    RESPONSE.setCookie("username", 'limodou', expires=etime)

上面的例子,表示设置一个Cookie变量username=limodou,失效期为一年以后。要注意,如果没有将RESPONSE作为参数传入Script中,那么就要从container中得到。

希望看过这篇文章对大家有所帮助。

版权所有limodou([email protected]) 如要转载请保留此信息!