使用 Action.async 有什么影响,因为 Play 使用的是非阻塞的 Netty [英] What effect does using Action.async have, since Play uses Netty which is non-blocking

查看:20
本文介绍了使用 Action.async 有什么影响,因为 Play 使用的是非阻塞的 Netty的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

既然 Netty 是一个非阻塞服务器,那么改变一个动作到使用 .async 有什么影响?

def index = Action { ... }

对比

def index = Action.async { ... }

我知道使用 .async 你会得到一个 Future[SimpleResult].但是由于 Netty 是非阻塞的,Play 会在幕后做类似的事情吗?

这会对吞吐量/可扩展性产生什么影响?这是一个很难回答的问题,它取决于其他因素吗?

我问的原因是,我有自己的自定义 Action,我想为每个页面请求重置 cookie 超时,所以我这样做是一个 async 调用:

object MyAction 扩展 ActionBuilder[abc123] {def invokeBlock[A](request: Request[A], block: (abc123[A]) => Future[SimpleResult]) = {...val 结果:Future[SimpleResult] = block(new abc123(..., result))结果.map(_.withCookies(...))}}

从上面的代码片段中得出的结论是我正在使用 Future[SimpleResult],这与调用 Action.async 类似,但这是在我的 Action 内部?

我想了解这会对我的应用程序设计产生什么影响.似乎只是为了能够在每个请求的基础上设置我的 cookie,我已经从阻塞更改为非阻塞.但是我很困惑,因为 Netty 是非阻塞的,也许我实际上并没有真正改变任何东西,因为它已经是异步的了?

或者我只是创建了另一个嵌入在另一个异步调用中的异步调用?

希望有人能用一些细节来澄清这一点,以及这将对性能/吞吐量产生什么影响.

解决方案

def index = Action { ... } is non-blocking you are right.

Action.async 的目的只是为了让您更轻松地在操作中使用 Futures.

例如:

def index = Action.async {val allOptionsFuture: Future[List[UserOption]] = optionService.findAll()allOptionFuture 映射 {选项 =>好的(views.html.main(选项))}}

这里我的服务返回一个 Future,为了避免提取结果,我只是将它映射到 Future[SimpleResult]Action.async 负责其余的工作.

如果我的服务直接返回 List[UserOption] 我可以只使用 Action.apply,但在引擎盖下它仍然是非阻塞的.

如果您查看Action 源代码,您甚至可以看到apply 最终调用了async:https://github.com/playframework/playframework/blob/2.3.x/framework/src/play/src/main/scala/play/api/mvc/Action.scala#L432>

Since Netty is a non-blocking server, what effect does changing an action to using .async?

def index = Action { ... }

versus

def index = Action.async { ... }

I understand that with .async you will get a Future[SimpleResult]. But since Netty is non-blocking, will Play do something similar under the covers anyway?

What effect will this have on throughput/scalability? Is this a hard question to answer where it depends on other factors?

The reason I am asking is, I have my own custom Action and I wanted to reset the cookie timeout for every page request so I am doing this which is a async call:

object MyAction extends ActionBuilder[abc123] {
  def invokeBlock[A](request: Request[A], block: (abc123[A]) => Future[SimpleResult]) = {
    ...
    val result: Future[SimpleResult] = block(new abc123(..., result))
    result.map(_.withCookies(...))
  }
}

The take away from the above snippet is I am using a Future[SimpleResult], is this similar to calling Action.async but this is inside of my Action itself?

I want to understand what effect this will have on my application design. It seems like just for the ability to set my cookie on a per request basis I have changed from blocking to non-blocking. But I am confused since Netty is non-blocking, maybe I haven't really changed anything in reality as it was already async?

Or have I simply created another async call embedded in another one?

Hoping someone can clarify this with some details and how or what effect this will have in performance/throughput.

解决方案

def index = Action { ... } is non-blocking you are right.

The purpose of Action.async is simply to make it easier to work with Futures in your actions.

For example:

def index = Action.async {
  val allOptionsFuture: Future[List[UserOption]] = optionService.findAll()
  allOptionFuture map {
    options =>
      Ok(views.html.main(options))
  }
}

Here my service returns a Future, and to avoid dealing with extracting the result I just map it to a Future[SimpleResult] and Action.async takes care of the rest.

If my service was returning List[UserOption] directly I could just use Action.apply, but under the hood it would still be non-blocking.

If you look at Action source code, you can even see that apply eventually calls async: https://github.com/playframework/playframework/blob/2.3.x/framework/src/play/src/main/scala/play/api/mvc/Action.scala#L432

这篇关于使用 Action.async 有什么影响,因为 Play 使用的是非阻塞的 Netty的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆