4

我正在尝试了解 gevent 获得的性能优势,并希望对其进行定量测量。基于这个 SO answer,我创建了一个简单的 django 应用程序,它在一个简单的视图中休眠了 3 秒。

当我使用 1 个同步工作者运行 gunicorn 时,当我使用 firefox 检查时,我每秒收到约 3 秒的可预测请求。当我再打开一个浏览器时,我可以看到它需要更长的时间(~ 3 * 我打开的浏览器数量)。前端服务器是 nginx。

我的观点:

def home(request,epoch):
    sleeptime = 3
    time.sleep(sleeptime);
    html = "<html><body>%s </body></html>" % str(float(time.time()) - float(epoch) / 1000)
    return HttpResponse(html)

但是,当我运行以下ab命令 ab -r -n 100 -c 100 http://ec2-compute-1.amazonaws.com/

使用以下 gunicorn 命令,

gunicorn --pythonpath=/home/ubuntu/webapps/testt -c /home/ubuntu/webapps/testt/gunicorn.conf.py testt.wsgi

我得到以下结果:

Concurrency Level:      100
Time taken for tests:   7.012 seconds
Complete requests:      100
Requests per second:    14.26 [#/sec] (mean)
Time per request:       7011.750 [ms] (mean)
Time per request:       70.118 [ms] (mean, across all concurrent requests)
Transfer rate:          40.53 [Kbytes/sec] received

Connection Times (ms)
              min  mean[+/-sd] median   max
Connect:       37  837 1487.4     98    3869
Processing:     0 3475 913.2   3777    3890
Waiting:        0 3467 911.2   3777    3889
Total:       3141 4312 1150.1   3870    7011

我应该如何从上述结果中理解 (3 * browser connections) 的行为?

因此,如果只有一名工作人员和 100 个客户端正在连接,那么第 100 个连接实际上应该需要大约 100 * 3 = 300 秒(因为第 100 个连接必须等待所有其他连接完成)顺便说一句,如果我打开 3 个浏览器并连接,我需要大约 9 秒最坏的情况,我认为这是有道理的 :)。所以,我的第一个问题是,在上面的结果中,为什么每次请求的 Time 大约为 7 秒ab?我希望它会更多,因为只有前 2 个连接需要大约 6 秒,所有第 n 个并发连接都需要 n*3 秒才能返回。

当我不更改程序时,只需执行以下操作:

gunicorn -k gevent --pythonpath=/home/ubuntu/webapps/testt -c /home/ubuntu/webapps/testt/gunicorn.conf.py testt.wsgi

并运行相同的ab命令,我得到以下(!):

Concurrency Level:      100
Time taken for tests:   0.558 seconds
Complete requests:      100
Failed requests:        0
Write errors:           0
Total transferred:      255300 bytes
HTML transferred:       241600 bytes
Requests per second:    179.32 [#/sec] (mean)
Time per request:       557.675 [ms] (mean)
Time per request:       5.577 [ms] (mean, across all concurrent requests)
Transfer rate:          447.06 [Kbytes/sec] received

Connection Times (ms)
              min  mean[+/-sd] median   max
Connect:       33   44   6.2     47      58
Processing:    47  133  74.0    122     506
Waiting:       46  132  74.2    122     506
Total:         80  177  76.2    162     555

所以你完成一个请求的最短时间是 3 秒,但是上面的结果表明它不到 1 秒,这是没有意义的。

我错过了什么?

我已经附加了正在 ping 视图的客户端(它与上面链接的 SO 问题中列出的类似,但不完全相同:

<html>
<head>
    <title>BargePoller</title>
    <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.2.6/jquery.min.js" type="text/javascript" charset="utf-8"></script>

    <style type="text/css" media="screen">
      body{ background:#000;color:#fff;font-size:.9em; }
      .msg{ background:#aaa;padding:.2em; border-bottom:1px #000 solid}
      .old{ background-color:#246499;}
      .new{ background-color:#3B9957;}
    .error{ background-color:#992E36;}
    </style>

    <script type="text/javascript" charset="utf-8">
    function addmsg(type, msg){
        /* Simple helper to add a div.
        type is the name of a CSS class (old/new/error).
        msg is the contents of the div */
        $("#messages").append(
            "<div class='msg "+ type +"'>"+ msg +"</div>"
        );
    }

    function waitForMsg(){
        /* This requests the url "msgsrv.php"
        When it complete (or errors)*/
       var currentdate = new Date();
        $.ajax({


            type: "GET",
            url: "server/" + currentdate.getTime() + "/",

            async: true, /* If set to non-async, browser shows page as "Loading.."*/
            cache: false,
            timeout:50000, /* Timeout in ms */

            success: function(data){ /* called when request to barge.php completes */
                addmsg("new", data); /* Add response to a .msg div (with the "new" class)*/
                setTimeout(
                    waitForMsg, /* Request next message */
                    1000 /* ..after 1 seconds */
                );
            },
            error: function(XMLHttpRequest, textStatus, errorThrown){
                var currentdate = new Date();
                addmsg("error", currentdate.getTime() + textStatus + " (" + errorThrown + " " + currentdate.getTime() + ")");
                setTimeout(
                    waitForMsg, /* Try again after.. */
                    1000); /* milliseconds (15seconds) */
            },
         beforeSend: function(){
               var currentdate = new Date();
                addmsg("body", currentdate + " <-  sent request");
            }
        });
    };

    $(document).ready(function(){
        waitForMsg(); /* Start the inital request */
    });
    </script>
</head>
<body>
    <div id="messages">
        <div class="msg old">
            BargePoll message requester!
        </div>
    </div>
</body>
</html>
4

0 回答 0