diff --git a/backend/framework/sdk/src/main/resources/i18n/api.properties b/backend/framework/sdk/src/main/resources/i18n/api.properties index f9a4ff7765..2ced8703be 100644 --- a/backend/framework/sdk/src/main/resources/i18n/api.properties +++ b/backend/framework/sdk/src/main/resources/i18n/api.properties @@ -383,6 +383,7 @@ api_case_report_not_exist=用例报告不存在 api_scenario_report_not_exist=场景报告不存在 permission.api_plugin.name=接口插件 permission.api_step.name=步骤 +api_response_name_code_unique=响应名称 + 响应码需要唯一 #module:ApiScenarioCsv api_scenario_csv.file_id.not_blank=文件ID不能为空 diff --git a/backend/framework/sdk/src/main/resources/i18n/api_en_US.properties b/backend/framework/sdk/src/main/resources/i18n/api_en_US.properties index aa47acac7e..ae63c6b401 100644 --- a/backend/framework/sdk/src/main/resources/i18n/api_en_US.properties +++ b/backend/framework/sdk/src/main/resources/i18n/api_en_US.properties @@ -395,6 +395,7 @@ api_case_report_not_exist=Api report does not exist api_scenario_report_not_exist=Scenario report does not exist permission.api_plugin.name=Api Plugin permission.api_step.name=Step +api_response_name_code_unique=Response name + response code need to be unique #module:ApiScenarioCsv api_scenario_csv.file_id.not_blank=File ID cannot be empty diff --git a/backend/framework/sdk/src/main/resources/i18n/api_zh_CN.properties b/backend/framework/sdk/src/main/resources/i18n/api_zh_CN.properties index 39d9d820da..407c5889bb 100644 --- a/backend/framework/sdk/src/main/resources/i18n/api_zh_CN.properties +++ b/backend/framework/sdk/src/main/resources/i18n/api_zh_CN.properties @@ -363,6 +363,7 @@ api_case_report_not_exist=用例报告不存在 api_scenario_report_not_exist=场景报告不存在 permission.api_plugin.name=接口插件 permission.api_step.name=步骤 +api_response_name_code_unique=响应名称 + 响应码需要唯一 #module:ApiScenarioCsv api_scenario_csv.file_id.not_blank=文件ID不能为空 diff --git a/backend/framework/sdk/src/main/resources/i18n/api_zh_TW.properties b/backend/framework/sdk/src/main/resources/i18n/api_zh_TW.properties index 08175e70f8..226088e7e5 100644 --- a/backend/framework/sdk/src/main/resources/i18n/api_zh_TW.properties +++ b/backend/framework/sdk/src/main/resources/i18n/api_zh_TW.properties @@ -364,6 +364,7 @@ api_case_report_not_exist=用例報告不存在 api_scenario_report_not_exist=場景報告不存在 permission.api_plugin.name=接口插件 permission.api_step.name=步驟 +api_response_name_code_unique=响應名稱 + 响應碼需要唯一 #module:ApiScenarioCsv 繁体 api_scenario_csv.file_id.not_blank=文件ID不能為空 diff --git a/backend/services/api-test/src/main/java/io/metersphere/api/controller/result/ApiResultCode.java b/backend/services/api-test/src/main/java/io/metersphere/api/controller/result/ApiResultCode.java index 94880382f2..96672d6ddd 100644 --- a/backend/services/api-test/src/main/java/io/metersphere/api/controller/result/ApiResultCode.java +++ b/backend/services/api-test/src/main/java/io/metersphere/api/controller/result/ApiResultCode.java @@ -14,7 +14,8 @@ public enum ApiResultCode implements IResultCode { RESOURCE_POOL_EXECUTE_ERROR(104005, "resource_pool_execute_error"), EXECUTE_RESOURCE_POOL_NOT_CONFIG(104006, "execute_resource_pool_not_config_error"), API_DEFINITION_MOCK_EXIST(104007, "api_definition_mock_exist"), - API_SCENARIO_EXIST(104008, "api_scenario_exist"); + API_SCENARIO_EXIST(104008, "api_scenario_exist"), + API_RESPONSE_NAME_CODE_UNIQUE(104009, "api_response_name_code_unique"); private final int code; diff --git a/backend/services/api-test/src/main/java/io/metersphere/api/service/definition/ApiDefinitionService.java b/backend/services/api-test/src/main/java/io/metersphere/api/service/definition/ApiDefinitionService.java index c10e5fcc71..75b3197234 100644 --- a/backend/services/api-test/src/main/java/io/metersphere/api/service/definition/ApiDefinitionService.java +++ b/backend/services/api-test/src/main/java/io/metersphere/api/service/definition/ApiDefinitionService.java @@ -167,6 +167,7 @@ public class ApiDefinitionService { ApiDefinition apiDefinition = new ApiDefinition(); BeanUtils.copyBean(apiDefinition, request); checkAddExist(apiDefinition); + checkResponseNameCode(request.getResponse()); apiDefinition.setId(IDGenerator.nextStr()); apiDefinition.setNum(getNextNum(request.getProjectId())); apiDefinition.setPos(getNextOrder(request.getProjectId())); @@ -230,6 +231,7 @@ public class ApiDefinitionService { ApiDefinition originApiDefinition = checkApiDefinition(request.getId()); ApiDefinition apiDefinition = new ApiDefinition(); BeanUtils.copyBean(apiDefinition, request); + checkResponseNameCode(request.getResponse()); if (request.getProtocol().equals(ModuleConstants.NODE_PROTOCOL_HTTP)) { checkUpdateExist(apiDefinition); //http协议的接口,如果修改了path和method,需要同步把case的path和method修改 @@ -1009,4 +1011,17 @@ public class ApiDefinitionService { extApiTestCaseMapper::getLastPos, apiDefinitionMapper::updateByPrimaryKeySelective); } + + private void checkResponseNameCode(Object response) { + if (!response.toString().isEmpty() && !response.toString().equals("{}")) { + List httpResponses = ApiDataUtils.parseArray(JSON.toJSONString(response), HttpResponse.class); + boolean isUnique = httpResponses.stream() + .map(httpResponse -> httpResponse.getName() + httpResponse.getStatusCode()) + .collect(Collectors.toSet()) + .size() == httpResponses.size(); + if (!isUnique) { + throw new MSException(ApiResultCode.API_RESPONSE_NAME_CODE_UNIQUE); + } + } + } } diff --git a/backend/services/api-test/src/test/java/io/metersphere/api/controller/ApiDefinitionControllerTests.java b/backend/services/api-test/src/test/java/io/metersphere/api/controller/ApiDefinitionControllerTests.java index 515a58819e..694cbaf11d 100644 --- a/backend/services/api-test/src/test/java/io/metersphere/api/controller/ApiDefinitionControllerTests.java +++ b/backend/services/api-test/src/test/java/io/metersphere/api/controller/ApiDefinitionControllerTests.java @@ -212,6 +212,17 @@ public class ApiDefinitionControllerTests extends BaseTest { // @@重名校验异常 assertErrorCode(this.requestPost(ADD, request), ApiResultCode.API_DEFINITION_EXIST); + // @@响应名+响应码唯一校验异常 + request.setName("test123-response"); + request.setMethod("GET"); + request.setPath("/api/halo/posts"); + List mergedList = new ArrayList<>(); + List msHttpResponse1 = MsHTTPElementTest.getMsHttpResponse(); + mergedList.addAll(msHttpResponse); + mergedList.addAll(msHttpResponse1); + request.setResponse(mergedList); + assertErrorCode(this.requestPost(ADD, request), ApiResultCode.API_RESPONSE_NAME_CODE_UNIQUE); + // 校验项目是否存在 request.setProjectId("111"); request.setName("test123"); @@ -388,6 +399,17 @@ public class ApiDefinitionControllerTests extends BaseTest { request.setUnLinkRefIds(null); assertErrorCode(this.requestPost(UPDATE, request), ApiResultCode.API_DEFINITION_EXIST); + // @@响应名+响应码唯一校验异常 + request.setName("test123-response"); + request.setMethod("GET"); + request.setPath("/api/halo/posts"); + List mergedList = new ArrayList<>(); + List msHttpResponse1 = MsHTTPElementTest.getMsHttpResponse(); + mergedList.addAll(msHttpResponse); + mergedList.addAll(msHttpResponse1); + request.setResponse(mergedList); + assertErrorCode(this.requestPost(UPDATE, request), ApiResultCode.API_RESPONSE_NAME_CODE_UNIQUE); + // 校验数据是否存在 request.setId("111"); request.setName("test123");