了解 Cro 请求/响应周期和内存使用

cod*_*ons 12 rakudo cro raku

我对 Cro 如何处理客户端请求感到有点困惑,特别是为什么某些请求似乎会导致 Cro 的内存使用量激增。

\n

一个最小的例子出现在字面上的“Hello world!”中。克罗服务器

\n
use Cro::HTTP::Router;\nuse Cro::HTTP::Server;\n\nmy $application = route {\n    get -> {\n        content \'text/html\', \'Hello Cro!\';\n    }\n}\n\nmy Cro::Service $service = Cro::HTTP::Server.new:\n    :host<localhost>, :port<10000>, :$application;\n\n$service.start;\n\nreact whenever signal(SIGINT) {\n    $service.stop;\n    exit;\n}\n
Run Code Online (Sandbox Code Playgroud)\n

该服务器所做的就是用“Hello Cro!\”\xe2\x80\x93 响应 GET 请求,这当然不应该是繁重的。但是,如果我导航到页面localhost:10000然后快速刷新页面,我会注意到 Cro\'内存使用量开始攀升(然后保持较高水平)。

\n

这种情况似乎只在刷新很快时才会发生,这表明该问题可能与未正确关闭连接或并发问题有关(可能与之前的问题略有相关)。

\n

为了简单起见,这个“Hello world”服务器是否省略了一些性能技术或最佳实践?或者我是否遗漏了有关 Cro 设计工作方式的其他信息?

\n

Jon*_*ton 12

Cro 请求处理管道是supply请求和随后的响应经过的一系列块。有关要创建的最佳处理线程数量的决定留给 RakuThreadPoolScheduler实现。

就连接生命周期而言,连接的关闭程度取决于客户端(即 Web 浏览器);如果浏览器使用保持活动的 HTTP/1.1 连接或保留 HTTP/2.0 连接,Cro 会尊重该请求。

关于内存使用,增长到一定程度并不奇怪;如果最终没有稳定下来,这只是一个问题。原因包括:

  • 调度程序确定需要更多线程来处理负载。每个操作系统线程在虚拟机内部都会产生一些开销,其中大部分是每个线程都有 GC 苗圃,以允许简单的指针碰撞分配。
  • MoarVM 优化器使用内存存储专门的字节码和 JIT 编译的机器代码,这些代码在应用程序运行时在后台生成,并由已执行足够次数的某些代码位驱动。
  • GC 尝试收敛到完整收集阈值。