在处理程序中使用yield时,web.py会话/处理器是否有效?

时间:2013-06-15 11:09:16

标签: python web.py

我有以下两个处理程序用于web.py设置:

class count1:
    def GET(self):
        s.session.count += 1
        return str(s.session.count)

class count2:
    def GET(self):
        s.session.count += 1
        yield str(s.session.count)

该应用程序在web.py上运行cherrypy(app.run())或gevent服务器。

urls = (
    "/count1", "count.count1",
    "/count2", "count.count2",
)

session = web.session.Session(app, web.session.DiskStore('sessions'), initializer={'count': 0})
s.session = session
app = web.application(urls, locals())

print "Main: setting count to 1"    

from gevent.wsgi import WSGIServer
if __name__ == "__main__":
    usecherrypy = False
    if usecherrypy:
        app.run()
    else: # gevent wsgiserver
        wsgifunc = app.wsgifunc()
        server = WSGIServer(('0.0.0.0', 8080), wsgifunc, log=None)
        server.serve_forever()

Session在count1的情况下工作正常,但并不总是在count2中。在第一次加载/ count2的页面时,计数器增加一次,但在此之后刷新不会增加会话中的计数器,即永远不会保存对会话的更新。这会有什么问题?

从pypi安装的Webpy或从github安装的最新版本在这种情况下表现相同。

在深入研究代码之后,实际的原因似乎是,当处理程序使用yield时,它只被调用以返回生成器对象,然后从所有封闭处理器返回(例如调用_save的Session._processor)在最后一块)。 Web.py确保在将数据返回到客户端之前完全展开了生成器,但是展开过程是在所有处理器之后,与正常的函数处理程序相比,这是完全不同的行为。

所以问题是:是否有任何修复或解决方法(除了手动调用Session._save)?

提前感谢您的任何答案!

1 个答案:

答案 0 :(得分:0)

可能会发生因为yield会返回一个生成器,而不是一个值。

参考文献:

http://od-eon.com/blogs/calvin/python-yield-versus-return/

What does the "yield" keyword do in Python?