Citrus Framework - 可以从响应中分配变量吗?
Citrus Framework - Can a variable be assigned from a response?
我正在尝试测试以下两个 REST 调用:
请求 1
GET getLatestVersion
Response: {"version": 10}
请求 2
POST getVersionData (body={"version": 10})
Response: {"version": 10, data: [...]}
是否可以将请求 1 中的 "version" 分配给一个变量,以便在同一测试中的请求 2 中使用?
@CitrusTest(name = "SimpleIT.getVersionTest")
public void getVersionTest() {
// Request 1
http()
.client("restClient")
.send()
.get("/getLatestVersion")
.accept("application/json");
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
// Can the version be assigned to a variable here?
.payload("{\"version\":10}");
// Request 2
http()
.client("restClient")
.send()
.post("/getVersionData")
// Idealy this would be a Citrus variable from the previous response
.payload("{\"version\":10}")
.accept("application/json");
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("\"version\": 10, data: [...]");
}
一种可行的方法是从 TestContext 中提取值并将其分配为变量
@CitrusTest(name = "SimpleIT.getVersionTest")
@Test
public void getVersionTest(@CitrusResource TestContext context) {
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.send()
.get("/getLatestVersion")
.name("request1")
.accept("application/json")
);
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("{\"version\":\"@greaterThan(0)@\"}")
);
// This extracts the version and assigns it as a variable
groovy(action -> action.script(new ClassPathResource("addVariable.groovy")));
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.send()
.post("/getVersionData")
.payload("{\"version\":${versionId}}")
.accept("application/json")
);
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
);
}
addVariable.groovy
这将从响应中提取变量并将其添加到 TestContext。
import com.consol.citrus.message.Message
import groovy.json.JsonSlurper
Message message = context.getMessageStore().getMessage("receive(restClient)");
def jsonSlurper = new JsonSlurper();
def payload = jsonSlurper.parseText((String) message.getPayload())
// Set the version as a variable in the TestContext
context.getVariables().put("versionId", payload.version)
问题
- 有没有更简洁的方法来做到这一点?
- 有没有办法命名 MessageStore 中的消息?
您可以使用 JsonPath 表达式:
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.extractFromPayload("$.version", "apiVersion")
.payload("{\"version\":\"@ignore@\"}");
或者您可以在负载中使用创建变量匹配器:
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("{\"version\":\"@variable('apiVersion')@\"}");
这两个选项都会创建一个新的测试变量 apiVersion
,您可以在进一步的测试操作中使用 ${apiVersion}
引用它。
我正在尝试测试以下两个 REST 调用:
请求 1
GET getLatestVersion
Response: {"version": 10}
请求 2
POST getVersionData (body={"version": 10})
Response: {"version": 10, data: [...]}
是否可以将请求 1 中的 "version" 分配给一个变量,以便在同一测试中的请求 2 中使用?
@CitrusTest(name = "SimpleIT.getVersionTest")
public void getVersionTest() {
// Request 1
http()
.client("restClient")
.send()
.get("/getLatestVersion")
.accept("application/json");
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
// Can the version be assigned to a variable here?
.payload("{\"version\":10}");
// Request 2
http()
.client("restClient")
.send()
.post("/getVersionData")
// Idealy this would be a Citrus variable from the previous response
.payload("{\"version\":10}")
.accept("application/json");
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("\"version\": 10, data: [...]");
}
一种可行的方法是从 TestContext 中提取值并将其分配为变量
@CitrusTest(name = "SimpleIT.getVersionTest")
@Test
public void getVersionTest(@CitrusResource TestContext context) {
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.send()
.get("/getLatestVersion")
.name("request1")
.accept("application/json")
);
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("{\"version\":\"@greaterThan(0)@\"}")
);
// This extracts the version and assigns it as a variable
groovy(action -> action.script(new ClassPathResource("addVariable.groovy")));
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.send()
.post("/getVersionData")
.payload("{\"version\":${versionId}}")
.accept("application/json")
);
http(httpActionBuilder -> httpActionBuilder
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
);
}
addVariable.groovy
这将从响应中提取变量并将其添加到 TestContext。
import com.consol.citrus.message.Message
import groovy.json.JsonSlurper
Message message = context.getMessageStore().getMessage("receive(restClient)");
def jsonSlurper = new JsonSlurper();
def payload = jsonSlurper.parseText((String) message.getPayload())
// Set the version as a variable in the TestContext
context.getVariables().put("versionId", payload.version)
问题
- 有没有更简洁的方法来做到这一点?
- 有没有办法命名 MessageStore 中的消息?
您可以使用 JsonPath 表达式:
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.extractFromPayload("$.version", "apiVersion")
.payload("{\"version\":\"@ignore@\"}");
或者您可以在负载中使用创建变量匹配器:
http()
.client("restClient")
.receive()
.response(HttpStatus.OK)
.messageType(MessageType.JSON)
.payload("{\"version\":\"@variable('apiVersion')@\"}");
这两个选项都会创建一个新的测试变量 apiVersion
,您可以在进一步的测试操作中使用 ${apiVersion}
引用它。