Java 高性能网络的 Netty 替代品是什么?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/23839437/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-14 01:31:31  来源:igfitidea点击:

What are the Netty alternatives for high-performance networking?

javanetworkingreal-timenettynio

提问by chrisapotek

I am in the process of choosing a networking library to implement a client/server system that cannot spare any microsecond. It will implement its own protocol to send and receive messages. I am looking for a good NIO framework that will allow me to easily develop the server and the client, without having to worry too much about the low level selector details. Everyone recommends me Netty but I would like to experiment with 2 or 3 other alternatives before committing my team with a framework. One thing I did not like very much about Netty is how it handles ByteBuffers with its own ByteBuf implementation and reference counting. Can anyone share your thoughts and alternatives?

我正在选择一个网络库来实现一个不能节省任何微秒的客户端/服务器系统。它将实现自己的协议来发送和接收消息。我正在寻找一个好的 NIO 框架,它可以让我轻松地开发服务器和客户端,而不必太担心低级选择器的细节。每个人都向我推荐 Netty,但我想在向我的团队提交框架之前尝试 2 或 3 个其他替代方案。我不太喜欢 Netty 的一件事是它如何使用自己的 ByteBuf 实现和引用计数来处理 ByteBuffers。任何人都可以分享您的想法和替代方案吗?

采纳答案by rdalmeida

We have developed a NIO networking librarythat performs under 2 microseconds over loopback without producing any garbage for the GC. As Peter Lawrey mentioned, the native JDK selector produces a lot of garbage but we have fixed all these garbage leaksby implementing our own epoll selector. Busy waiting the selector thread is great for latency but there must be a balance not to burn the chip or consume a lot of energy. Our selector implementation use low-level tricks to implement a kind of energy saving modethat takes care of that balance.

我们开发了一个NIO 网络库,它在环回上的执行时间低于 2 微秒,而不会为 GC 产生任何垃圾。正如 Peter Lawrey 所提到的,原生 JDK 选择器会产生大量垃圾,但我们已经通过实现我们自己的 epoll 选择器修复了所有这些垃圾泄漏。忙于等待选择器线程对于延迟来说是很大的,但必须有一个平衡,不烧芯片或消耗大量能量。我们的选择器实现使用低级技巧来实现一种处理这种平衡的节能模式

Besides CoralReactor, you can also take a look on Grizzlyand Mina, but we haven't played with these frameworks yet.

除了CoralReactor,你还可以看看GrizzlyMina,但我们还没有玩过这些框架。

For some Netty TCP performance benchmarks you can take a look here.

对于一些 Netty TCP 性能基准,您可以查看这里

回答by Peter Lawrey

This is assuming you really want to save every micro-second. Most applications don't have such strict requirements.

这是假设您真的想节省每一微秒。大多数应用程序没有这么严格的要求。

If you want to save micro-seconds, you will want to use busy waiting non-blocking NIO for threads on dedicated cpus. This doesn't scale well as you need to have plenty of CPU but does minimise the latency for handling IO. I suggest you also bind the isolated CPUs to minimise jitter.

如果您想节省微秒,您将需要为专用 CPU 上的线程使用忙等待非阻塞 NIO。这不能很好地扩展,因为您需要有足够的 CPU,但确实最大限度地减少了处理 IO 的延迟。我建议您还绑定隔离的 CPU 以最大程度地减少抖动。

You will want to avoid using Selectors as they block and/or create quite a bit of garbage adding to GC pauses.

您将希望避免使用选择器,因为它们会阻塞和/或创建相当多的垃圾添加到 GC 暂停。

Also to minimise latency you will want to use a low latency, kernel bypass network adapter such as Solarflare.

此外,为了最大限度地减少延迟,您将需要使用低延迟、内核绕过网络适配器,例如 Solarflare。

You will want to use a push parser so long messages can be decoded/parsed as they download. i.e. you won't want to wait until the whole messages is received before starting.

您将需要使用推送解析器,以便可以在下载时解码/解析长消息。即您不会想等到收到全部消息才开始。

Using these tricks in combination can save 10 - 30 micro-seconds off every request or inbound event.

结合使用这些技巧可以在每个请求或入站事件中节省 10 到 30 微秒。

Netty is a better solution for scalability ie, higher net throughput, but at a small cost to latency, as do most frameworks which are based on support web services where milli-seconds delays are tolerable.

Netty 是可扩展性更好的解决方案,即更高的净吞吐量,但延迟成本很小,大多数基于支持 Web 服务的框架也是如此,其中毫秒延迟是可以容忍的。

回答by Rafael Winterhalter

If you are okay with using at least some Scala, Sprayis a great alternative to Netty. On the long run, the Play framework is for example intending to migrate from Netty to Spray. Spray offers different levels of TCP abstractions. Those are:

如果您至少可以使用一些 Scala,Spray是 Netty 的绝佳替代品。从长远来看,例如 Play 框架打算从 Netty 迁移到 Spray。Spray 提供了不同级别的 TCP 抽象。那些是:

  1. Chunk level
  2. Request level (HttpRequest / HttpResponse)
  3. Marshalled object level
  1. 块级
  2. 请求级别(HttpRequest / HttpResponse)
  3. 编组对象级别

The deeper you dig down into the stack, the more raw the delivered information is. In the chunk level API, you come pretty close to original byte buffers. I never used this low abstraction level myself, but I heard good things.

你越深入研究堆栈,传递的信息就越原始。在块级 API 中,您非常接近原始字节缓冲区。我自己从未使用过这种低抽象级别,但我听到了一些好消息。

Spray builds on top of Akka IO which is again built on top of Java NIO. All functionality wraps around Actor abstractions what makes it easy to build parallel applications using Spray. I think a chat server would be a perfect use case. Since Akka offers a Java API, you should be able to use Spray with mostly this API. However, you will probably need to read some Scala sources every now and then. Eventually, Spray will merge completely into Akka.

Spray 建立在 Akka IO 之上,而 Akka IO 又建立在 Java NIO 之上。所有功能都围绕着 Actor 抽象,这使得使用 Spray 构建并行应用程序变得容易。我认为聊天服务器将是一个完美的用例。由于 Akka 提供了 Java API,因此您应该能够在大多数情况下使用 Spray 和这个 API。但是,您可能需要时不时地阅读一些 Scala 源代码。最终,Spray 将完全融入 Akka。



Edit: Quote from the Spray web site: "Spray is no longer maintained and has been superseded by Akka HTTP. Playframework started experimentally supporting Akka HTTP Server backend starting from Play 2.4.X. In Play 2.6.Xversions, play completely migrated to Akka HTTP server backend.

编辑:Spray 网站的引用:“Spray 不再维护并已被Akka HTTP取代。Playframework 从Play 2.4.X开始实验性地支持 Akka HTTP Server 后端。在Play 2.6.X版本中,play 完全迁移到 Akka HTTP 服务器后端。