为什么WSGI必须使用start_response并返回迭代器?

4 投票
1 回答
2239 浏览
提问于 2025-04-18 12:44

非WSGI的方式:

def my_view(request):
    request.start_response('200 OK')
    request.send_header('Content-Type', 'text/plain')
    request.end_headers()
    request.write('Hello World!')
    request.write('Goodbye World!')
    request.end()

WSGI的方式:

def my_view(environ, start_response):
    def generate():
        yield 'Hello World!'
        yield 'Goodbye World!'
    start_response('200 OK', [('Content-Type', 'text/plain')])
    return generate()

这些代码来自于这个博客,不过我不是很理解..

从上面可以看出,非WSGI的方式看起来简单多了。而WSGI的方式则显得有些复杂.. 为什么start_response要传给my_view? 为什么my_view必须返回一个迭代器?WSGI方式中的request对象又在哪里呢?

有没有人对此有想法?

1 个回答

4

简单来说:就是这样做是因为WSGI规定了这样。😉

start_response()在两个例子中都有传入,在第一个例子里,它和request对象“捆绑”在一起,而WSGI则把环境变量和启动响应的可调用对象分开。

返回一个可迭代的对象可以让我们更灵活地生成响应,而且可以在多个中间件之间串联,而不需要一次性把整个内容从一个中间件传递到下一个中间件。顺便说一下,生成器函数并不是最简单的解决方案,因为返回值只需要是可迭代的,不一定非得是迭代器或者生成器。所以,这就是一个最简单的WSGI应用的例子:

def app(environ, start_response):
    start_response('200 OK', [('Content-type', 'text/plain')])
    return ['Hello world!\n']

我觉得这个看起来其实比非WSGI的例子更简单、更容易理解。

撰写回答