首頁 > 軟體

springboot vue測試列表遞迴查詢子節點下的介面功能實現

2022-05-26 18:01:45

基於 springboot+vue 的測試平臺開發

繼續更新

模組樹節點的開發暫告一段落,現在開發右邊介面相關的部分,今天先完成列表的功能。

功能是這樣,當點選樹的某個節點時候,右側列表展示這個節點下的所有介面,帶分頁(最終效果圖)。

需要注意的是,因為節點下還有子節點,所以列表的功能需要使用遞回來查詢。

一、後端

1. 建表

想了一些欄位,可能後續還會有些改動,暫時先這樣:

CREATE TABLE `api_definition` (
  `id` bigint NOT NULL AUTO_INCREMENT COMMENT '主鍵ID',
  `projectId` bigint NOT NULL COMMENT '所屬專案id',
  `name` varchar(255) NOT NULL COMMENT '介面名稱',
  `method` varchar(64) NOT NULL COMMENT '請求方法',
  `path` varchar(1000) DEFAULT NULL COMMENT '介面路徑',
  `description` longtext COMMENT '介面描述',
  `apiHeader` varchar(255) DEFAULT NULL COMMENT '請求頭',
  `request` longtext COMMENT '請求內容 (JSON format)',
  `response` longtext COMMENT '響應內容 (JSON format)',
  `createTime` datetime DEFAULT '1900-01-01 00:00:00' COMMENT '建立時間',
  `updateTime` datetime DEFAULT '1900-01-01 00:00:00' COMMENT '更新時間',
  `createUser` varchar(30) DEFAULT NULL COMMENT '建立人',
  `moduleId` bigint NOT NULL COMMENT '所屬模組id',
  `host` varchar(255) DEFAULT NULL COMMENT '介面域名',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='介面定義表';

2. 列表介面

(1)實體類 ApiDefinition

@Data
@TableName("api_definition")
public class ApiDefinition {
    @TableId(type = IdType.AUTO)
    private Long id;
    private Long projectId;
    private String name;
    private String method;
    private String path;
    private String host;
    private String description;
    private String apiHeader;
    private String request;
    private String response;
    private Long moduleId;
    private String createUser;
    @TableField(fill = FieldFill.INSERT)        // 新增的時候填充資料
    private Date createTime;
    @TableField(fill = FieldFill.INSERT_UPDATE) // 新增或修改的時候填充資料
    private Date updateTime;
}

(2)DAO層

@Repository
public interface ApiDefinitionDAO extends BaseMapper<ApiDefinition> {
}

(3)Controller 層

@RestController
@RequestMapping("apiDefinition")
public class ApiDefinitionController {
    @Autowired
    ApiDefinitionService apiDefinitionService;
    @GetMapping("/list/{projectId}/{moduleId}/{currentPage}/{pageSize}")
    public Result list(@PathVariable Long projectId,
                       @PathVariable Long moduleId,
                       @PathVariable int currentPage,
                       @PathVariable int pageSize) {
        IPage<ApiDefinition> IPageProject = apiDefinitionService.list(projectId, moduleId, currentPage, pageSize);
        return Result.success(IPageProject);
    }
}

這裡路徑有 4 個引數,moduleId 用來查詢模組下的所有介面(包含本節點+子節點),後面2個則是分頁查詢引數。

(4)Service 層

在 service 層實現 list 方法,用來查詢介面。

@Service
public class ApiDefinitionService {
    @Autowired
    ApiDefinitionDAO apiDefinitionDAO;
    @Autowired
    ApiModuleDAO apiModuleDAO;
    public IPage<ApiDefinition> list(Long projectId, Long moduleId, int currentPage, int pageSize) {
        // 查詢專案id下所有模組
        QueryWrapper<ApiModule> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("projectId", projectId);
        List<ApiModule> apiModules = apiModuleDAO.selectList(queryWrapper);
        // 呼叫遞迴查詢,childrenIds存放查詢到的模組 id
        List<Long> childrenIds = new ArrayList<>();
        List<Long> ids = moduleRecursion(childrenIds, apiModules, moduleId);
        // 新增上入參的模組id
        ids.add(moduleId);
        // 查詢模組id下的api
        Page<ApiDefinition> pageApiDefinition = new Page<>(currentPage, pageSize);
        QueryWrapper<ApiDefinition> queryApiWrapper = new QueryWrapper<>();
        queryApiWrapper.in("moduleId", ids)
                       .orderByDesc("id");
        return apiDefinitionDAO.selectPage(pageApiDefinition, queryApiWrapper);
    }
    private List<Long> moduleRecursion(List<Long> children, List<ApiModule> modules, Long pid) {
        for (ApiModule apiModule : modules) {
            //遍歷出父id等於pid,add進子節點集合
            if (apiModule.getParentId().equals(pid)) {
                // 遞迴遍歷下一級
                moduleRecursion(children, modules, apiModule.getId());
                children.add(apiModule.getId());
            }
        }
        return children;
    }
}

list方法中呼叫遞迴查詢方法moduleRecursion,有3個引數:

  • List<Long> children:用來存放子節點的 id,最後返回出來
  • List<ApiModule> modules:專案id下的模組
  • Long pid:就是當前要查詢的模組id

for 迴圈遍歷專案下的所有模組id,每一層裡判斷apiModule.getParentId().equals(pid),相等的話繼續遞迴遍歷,最後把結果返回。

list方法拿到之後,還有一步別忘記了,就是入參的這個模組本身,也需要加進去ids.add(moduleId),最後進行分頁查詢。

在表裡加點測試資料,然後測試下查詢介面沒問題。

二、前端

1. 準備工作

新建apiDefinition.js檔案,存放介面。

import request from '@/utils/request'
export function getApiListByModuleId(projectId, moduleId, current, size) {
  return request({
    url: `/bloomtest/apiDefinition/list/${projectId}/${moduleId}/${current}/${size}`,
    method: 'get'
  })
}

接著,去掉之前寫死的假資料,變成空陣列,從後端介面拿到的陣列就放到這。

2. 請求介面

元件裡有個事件node-click,節點被點選時的回撥。

這裡繫結了一個方法getApi,在這個方法裡會進行介面請求的操作,來實現這個方法:

傳入 data 是可以獲得節點 id 的,可以直接用。

注意,這裡還是需要用到一箇中間欄位currentNode,本來沒有用直接使用 data,後來發現點選分頁的時候有bug。

這是因為 data 是點選左側樹節點的時候才有,所以還是先存起來。

列表中的這些prop的值注意跟介面返回的欄位對應。

分頁的地方,注意下呼叫的方法即可。

3. 測試效果

在表裡新建了個資料,點選這個介面關聯的模組,列表可以呈現資料。

4. 發現問題

問題1

功能實現了,但是發現了個問題。

就是當我點選節點上的 新增、編輯等按鈕的時候,也會觸發這個事件,呼叫了介面列表的方法。

但是看在不影響各自功能的使用,先不去管它。

問題2

剛才我測試是在專案3下進行的,是可以查出來一條資料。但是當我切換專案到還沒資料的專案2下,頁面沒有重新整理,還是呈現的剛才的資料。

修改方法就是當切換專案的時候,查詢出這個專案下的所有介面資料。

找到下來框的元素,之前已經繫結過一個方法queryModuleList,然後現在再加一個方法,用來查詢專案下的介面。

@change="queryModuleList();initProjectApi()",方法加上括號,2個方法用;隔開。

實現這個新的方法initProjectApi

依然是呼叫列表介面,這裡的模組id可以直接傳 0,因為所有專案下的模組,頂級的節點id都是 0 。

測試功能正常。

以上就是springboot vue測試列表遞迴查詢子節點下的介面功能實現的詳細內容,更多關於springboot vue列表遞迴查詢的資料請關注it145.com其它相關文章!


IT145.com E-mail:sddin#qq.com