使用 gRPC 访问 Gatling feeder 中的变量

Access variables in Gatling feeder with gRPC

我正在尝试通过从 csv 文件(它有 guestID 和类别作为列)读取数据来创建我的 gRPC 负载。 我按照这里的示例 https://github.com/phiSgr/gatling-grpc/blob/244ab372da6773102d79c65a7e4086f409d3fe94/src/test/scala/com/github/phisgr/example/GrpcExample.scala 但是当我尝试相同时我看到类型不匹配错误。 (它期望 Seq[ContextKey] 但在这里我能够形成 Seq[Expression[ContextKey]])

val scn2: ScenarioBuilder = scenario("gRPC call - 50 users repeated 100 times")
  .feed(csv("testtext.csv"))
  .exec(
    grpc("gRPC request with test message")
      .rpc(RecommenderGrpc.METHOD_GET_RECOMMENDATIONS)
      .payload(RequestContext.of(Map("test" -> "test"),
        Seq(ContextKey.defaultInstance.updateExpr(
          _.id :~ $("guestID"),
          _.`type` :~ Type.GUEST
        ), ContextKey.defaultInstance.updateExpr(
          _.id :~ $("category"),
          _.`type` :~ Type.CATEGORY
        )),
        Seq())
      )
  )

(有效负载是一个 RequestContext 对象,它接收元数据、键和项目。元数据是一个映射,键是 ContextKey 的 Seq,项目是空 Seq。ContextKey 包含字符串 guestID 或类别和类型)。

这里如何使用feeder中的变量?

跳到底部查看解决方案。


Expression[T]Session => Validation[T] 的别名。用简单的英语来说,这是一个从会话中构造有效载荷的函数,可能会失败。

你可以抽象地考虑一个Expression[T],"contains"一个T


就像 Promise 在 JavaScript "contains" 中的未来值。您不能将 TPromise 赋给需要 T 的函数。如果要转换或组合 Promises,则必须将该代码从里到外翻转,并作为参数提供给 .then.1

aPromise + 1 // wrong
aPromise.then(a => a + 1)

这与您的代码示例无法编译的原因相同。


Gatling 的用户不一定熟悉 Scala 或一般的函数式编程。让他们理解这个"wrapping"东西会适得其反。2所以有代码可以帮助你组合Expressions。

对于 HTTP 和其他未类型化的内容,EL string 在后台被解析并转换为 Expression

Protobuf 消息是强类型的,无法使用字符串插值轻松构造有效负载。所以镜头上的 :~ 运算符用于处理管道,这样您就不必手动处理 Expression 包装。


但是现在您有一个函数 RequestContext.of 可以构造有效载荷。如果您需要该功能,镜头魔术将无济于事。您必须自己编写 Expression lambda。3

.payload { session =>
  for {
    guestId <- session("guestId").validate[String]
    category <- session("category").validate[String]
  } yield RequestContext.of(
    Map("test" -> "test"),
    Seq(
      ContextKey(id = guestID, `type` = Type.GUEST),
      ContextKey(id = category, `type` = Type.CATEGORY)
    ),
    Seq()
  )
}

  1. 不用说这个很麻烦,现在的人用async-await用Promises.

  2. 一个Expression就是Either单子和Reader单子叠加在一起,有什么问题?

  3. 如果我知道RequestContext.of的作用,我也许可以写一个带镜头的版本。