In Gatling, how do you tell a check to extract an Int rather than a String, and why does ofType not compile in a Java, Kotlin or JavaScript simulation?
answer
- Everything extracts String by default
- Scala has one generic method
- The Java family has named methods
- ofInt, ofNode, captureGroups
- bodyStream and ofNode are JVM-only
basics
~20 sofType is the Scala spelling only. The Java API, which Kotlin and the JavaScript/TypeScript SDK also use, exposes a family of named methods instead: ofInt(), ofString(), ofBoolean(), ofLong(), ofDouble(), ofList(), ofMap(), ofObject(), and ofNode() for css.
solid answer
~40 sBy default `jsonPath`, `jmesPath` and `css` extract **Strings** — non-String JSON values get serialised back into JSON text. To get a typed value you add one more step. In **Scala** that step is generic: `jsonPath("$.foo").ofType[Int]`, `css("a", "href").ofType[Node]`, `regex("a(.*)b(.*)c").ofType[(String, String)]`. In the **Java API** — and therefore in Kotlin and the JavaScript/TypeScript SDK — there is no public `ofType`; you call the named method for the type instead: `ofInt()`, `ofString()`, `ofBoolean()`, `ofLong()`, `ofDouble()`, `ofList()`, `ofMap()`, `ofObject()`, `ofNode()` for `css`, and `captureGroups(n)` for a multi-group regex. Two of these have no JS/TS equivalent at all: the JavaScript/TypeScript samples render `css(...).ofNode()` and the whole `bodyStream` check type as `NOT SUPPORTED`.
code
java · 21 linesimport io.gatling.javaapi.core.*;
import io.gatling.javaapi.http.*;
import static io.gatling.javaapi.core.CoreDsl.*;
import static io.gatling.javaapi.http.HttpDsl.*;
public class TypedExtractionSimulation extends Simulation {
ScenarioBuilder scn = scenario("Order")
.exec(http("Fetch order")
.get("/orders/42")
// default extraction is String; ask for a type explicitly
.check(jsonPath("$.quantity").ofInt().gt(0))
.check(jsonPath("$.paid").ofBoolean().is(true))
.check(jsonPath("$.lines").ofList().saveAs("lines"))
// a regex with two capture groups needs captureGroups(2)
.check(regex("order (\\d+) for (\\w+)").captureGroups(2).saveAs("pair")));
{
setUp(scn.injectOpen(atOnceUsers(1)));
}
}go deeper
Be ready to say that path checks extract Strings by default and that asking for another type is an extra step in the chain.
Explain that ofType is Scala-only and that the Java API, Kotlin and the JavaScript SDK use named methods such as ofInt, ofNode and captureGroups.
Point out that the JavaScript and TypeScript SDK lacks bodyStream and css ofNode entirely, so a JVM check cannot always be ported straight across.
Own whether a mixed-language suite is worth the cost, given that the JavaScript SDK is a subset of the JVM check surface.
Every path-style check in Gatling extracts a **String** unless you say otherwise. For `jsonPath` and `jmesPath` the reference is explicit that non-String values are *serialised back into JSON* rather than handed over as numbers or booleans, and that the check will then **fail** if the actual value does not match the type you declare. Declaring the type is a step of its own, and it is spelled differently depending on which SDK you are in. ## Scala: one generic method ```scala .check( jsonPath("$.foo").ofType[Int], jsonPath("$.foo").ofType[Seq[Any]], css("article.more a", "href").ofType[Node], regex("foo(.*)bar(.*)baz").ofType[(String, String)] ) ``` Scala's `ofType[T]` is one method parameterised by the target type. For `regex` it also serves as the multi-capture-group form, taking a tuple of up to eight Strings. ## Java, Kotlin, JavaScript and TypeScript: a family of named methods There is **no public `ofType` in the Java API**. The builder interfaces declare a named method per type: | what you want | Java / Kotlin / JS / TS | Scala | |---|---|---| | String | `ofString()` | `ofType[String]` | | Boolean | `ofBoolean()` | `ofType[Boolean]` | | Int / Long / Double | `ofInt()` / `ofLong()` / `ofDouble()` | `ofType[Int]` etc. | | JSON array | `ofList()` | `ofType[Seq[Any]]` | | JSON object | `ofMap()` | `ofType[Map[String, Any]]` | | any JSON value | `ofObject()` | `ofType[Any]` | | a DOM node from `css` | `ofNode()` | `ofType[Node]` | | several regex capture groups | `captureGroups(n)` | `ofType[(String, String)]` | Because Kotlin and the JavaScript/TypeScript SDK both sit on the Java API rather than on the Scala core, they use the Java column. This is the same split that gives Scala a single `inject` while the other four languages call `injectOpen`/`injectClosed` — the boundary is Java API versus Scala core, not "Java versus everyone else". ## Two gaps that are JVM-only The JavaScript/TypeScript SDK is a subset, and the documentation marks the gaps by rendering the sample region as the literal text `NOT SUPPORTED`. Two of those gaps land squarely on this pipeline: 1. **`css(...).ofNode()`** — the `css-ofType` sample region renders as `NOT SUPPORTED` in the TypeScript sample file. You can select nodes with `css` in JS/TS and read their text or an attribute; you cannot ask for the DOM node object itself. 2. **`bodyStream`** — the whole check type renders as `NOT SUPPORTED` in the same file. The JVM SDKs use it to `transform` the raw `InputStream` before processing — decoding a Base64 body, for example — and JS/TS has no equivalent. Everything else on the typed-extraction step, including `ofInt()` and `captureGroups(n)`, is present in JS/TS. ## Where the step sits in the chain Typed extraction attaches to the **check-type** end of the chain, before or as part of extraction; the rest of the pipeline is unchanged. `jsonPath("$.qty").ofInt().gt(0)` is check type, typed extraction, implicit `find()`, then the `gt` validation. Getting the type wrong does not fail at compile time — it fails at run time, because the check cannot coerce the actual value and reports a failure like any other. ## Two spellings to keep straight * `ofType` in a Java, Kotlin or JS/TS simulation does not compile — the method is `protected` on the default implementations and exists only as the bridge to the Scala core. * The documentation's sample *region* is named `css-ofType` and `jsonPath-ofType` in **all** language tabs, because the region name is shared across the files. The name of the region is not the name of the method in four of the five languages. ## And the Kotlin reserved words Once you have your typed value the validation step follows, and in Kotlin two of its methods collide with language keywords: `is` is written `shouldBe` and `in` is written `within`. So a typed check reads `jsonPath("$.qty").ofInt().shouldBe(3)` in Kotlin against `jsonPath("$.qty").ofInt().is(3)` in Java.
- What does a `jsonPath` check extract if you declare no type at all?A String. Non-String JSON values are serialised back into JSON text, so a number arrives as its textual form and an object arrives as a JSON string. Declaring a type with `ofInt()` or `ofType[Int]` also makes the check fail if the actual value is not of that type.
- Which two parts of the check pipeline are missing from the JavaScript and TypeScript SDK?The `bodyStream` check type and `css(...).ofNode()`. Both render as the literal text `NOT SUPPORTED` in the TypeScript sample files, so a reader of the Java tab alone never learns they are absent. Everything else on the pipeline, including `ofInt()` and `captureGroups(n)`, is present.
- How do you capture two groups from one regular expression?In Java, Kotlin and JS/TS use `regex(pattern).captureGroups(2)`, which yields a list of Strings. In Scala use `regex(pattern).ofType[(String, String)]`, which yields a tuple; the tuple form supports up to eight groups. With no such step a regex extracts zero or one group as a String.
saying these in an interview costs you the question
- Writing ofType in a Java, Kotlin or JavaScript simulation
- Assuming jsonPath hands back a number without a type step
- Believing the JavaScript SDK matches the JVM check surface exactly
- Confusing the doc region name css-ofType with a real Java method