VS2022中RestAPI Specflow+RestSharp:如何复用首个API返回ID调用其他服务
解决方案步骤
1. 存储生成的用户ID到Specflow上下文
在创建用户的步骤定义中,将获取到的ID存入ScenarioContext,实现跨步骤的数据共享:
[When(@"I create user throught the API \(x\)")] public void WhenICreateUserThroughtTheAPIX(Table table) { // 从场景表格中读取请求参数 var userInfo = new { Firstname = table.Rows[0]["Value"], Lastname = table.Rows[1]["Value"] }; // 初始化第一个API的RestClient并发送请求 var client = new RestClient("https://第一个API的基础地址"); var request = new RestRequest("/users", Method.Post); request.AddJsonBody(userInfo); var response = client.ExecutePostAsync<dynamic>(request).Result; var userId = response.Data.id; // 根据实际响应结构提取ID // 将ID存入场景上下文,供后续步骤调用 ScenarioContext.Current.Add("CreatedUserId", userId); }
2. 实现第二个服务的API调用步骤
从上下文取出存储的ID,作为参数构造第二个服务的请求:
[When(@"I make a get call for another service with ID generated from API\(x\)")] public void WhenIMakeAGetCallForAnotherServiceWithIDGeneratedFromAPIX() { // 从上下文获取用户ID if (!ScenarioContext.Current.TryGetValue("CreatedUserId", out string userId)) { throw new InvalidOperationException("未获取到用户ID,请先执行创建用户步骤"); } // 初始化第二个服务的RestClient var anotherClient = new RestClient("https://第二个服务的基础地址"); // 根据API要求构造请求(示例为路径参数,若为查询参数则用AddQueryParameter) var anotherRequest = new RestRequest($"/target-resource/{userId}", Method.Get); // 发送请求并存储响应,供后续断言使用 var anotherResponse = anotherClient.ExecuteGetAsync<dynamic>(anotherRequest).Result; ScenarioContext.Current.Add("AnotherServiceResponse", anotherResponse); }
3. 实现响应断言步骤
取出第二个服务的响应,验证是否返回成功:
[Then(@"the API should returns a ""success"" response")] public void ThenTheAPIShouldReturnsASuccessResponse() { ScenarioContext.Current.TryGetValue("AnotherServiceResponse", out IRestResponse<dynamic> response); Assert.NotNull(response); // 根据实际响应结构断言(示例为验证status字段和HTTP状态码) Assert.AreEqual("success", response.Data.status); Assert.AreEqual(HttpStatusCode.OK, response.StatusCode); }
关键注意事项
- Specflow 3.x+ 推荐注入方式:避免使用静态
ScenarioContext.Current,改为在步骤类构造函数注入ScenarioContext:
后续用private readonly ScenarioContext _scenarioContext; public YourStepDefinitions(ScenarioContext scenarioContext) { _scenarioContext = scenarioContext; }_scenarioContext.Add(...)和_scenarioContext.TryGetValue(...)操作数据。 - 异步优化:建议用
await替代.Result,避免线程阻塞,例如:var response = await client.ExecutePostAsync<dynamic>(request); - 参数传递适配:根据第二个API的参数要求调整请求构造方式(路径参数、查询参数、请求体等)。
内容的提问来源于stack exchange,提问作者Dee
相关产品推荐
相关产品推荐

