6

我正在尝试使用 gunicorn 及其异步工作者来处理长时间运行的请求,但我找不到任何可以开始工作的示例。我在这里使用了这个例子,但在返回响应之前添加了一个假延迟(睡眠 5 秒):

def app(environ, start_response):
    data = "Hello, World!\n"
    start_response("200 OK", [
        ("Content-Type", "text/plain"),
        ("Content-Length", str(len(data)))
    ])
    time.sleep(5)
    return iter([data])

然后我运行 gunicorn :

gunicorn -w 4 myapp:app -k gevent

当我打开两个浏览器选项卡并输入http://127.0.0.1:8000/它们并几乎同时发送请求时,请求似乎是按顺序处理的——一个在 5 秒后返回,另一个在 5 秒后返回

问:我猜睡眠不友好?但是有 4 个工作人员,所以即使工作人员的类型是“同步”,两个工作人员应该同时处理两个请求?

4

3 回答 3

11

我刚刚遇到了同样的事情,在这里提出了一个问题:Requests not being distributed across gunicorn workers。结果是,浏览器似乎序列化了对同一页面的访问。我猜这可能与可缓存性有关,即浏览器认为页面可能是可缓存的,等到它加载后发现它不是,所以它会发出另一个请求等等。

于 2014-04-13T05:32:52.223 回答
1

试一试gevent.sleep,而不是time.sleep

奇怪的是,这-w 4-k gevent一个异步工作类型,所以 gunicorn 可能会将两个请求都提供给同一个客户端。假设这是正在发生的事情,time.sleep除非您使用gevent.monkey.patch_all().

于 2014-03-18T17:01:38.547 回答
1

当使用具有非阻塞工作类型的 gunicorn 时,例如 gevent,它将只使用一个处理请求的进程,因此您的 5 秒工作顺序执行也就不足为奇了。

当您的工作负载很轻且请求速度很快时,异步工作器很有用,在这种情况下,gunicorn 可以通过切换到另一个来利用浪费在等待 IO 上的时间(例如,等待套接字可写来写入对它的响应)工人工作的另一个要求。通过切换到分配给同一工作人员的另一个请求。

更新

我错了。

当使用具有非阻塞工作者类型的 gunicorn 时,使用 gunicorn 中的工作者设置,每个工作者都是一个进程,它运行一个单独的队列。

So if the time.sleep was ran on different process, it will run simultaneously, but when it's ran in the same worker, it will be carried out sequentially.

The problem is that the gunicorn loadbalancer may not have distributed the two requests into two worker processes. You can check the current process by os.getpid().

于 2014-05-22T11:44:01.297 回答