1.概述
magic-api
是一個基於Java的接口快速開發框架,編寫接口將通過magic-api
提供的UI界面完成,自動映射為HTTP接口,無需定義Controller、Service、Dao、Mapper、XML、VO等Java對象。
只不過這種方式雖然簡單,但無法處理復制的業務邏輯。對於復雜的業務邏輯,還是使用java代碼進行實現。注意要保證二者的接口路徑不重復。
2.實戰演練
源碼:https://github.com/zhongyushi-git/springboot-magic-demo。數據庫的備份在項目根目錄下打包db2020.nb3。
2.1項目准備
1)新建一個SpringBoot的項目,導入數據庫需要的依賴:
<dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <scope>runtime</scope> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid</artifactId> <version>1.1.9</version> </dependency>
2)新建數據庫和表
CREATE TABLE `user` ( `id` int(11) NOT NULL AUTO_INCREMENT, `username` varchar(255) COLLATE utf8_bin DEFAULT NULL, `password` varchar(255) COLLATE utf8_bin DEFAULT NULL, `addr` varchar(500) COLLATE utf8_bin DEFAULT NULL, PRIMARY KEY (`id`) ) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
3)在配置文件配置數據源
spring: datasource: type: com.alibaba.druid.pool.DruidDataSource url: jdbc:mysql://localhost:3306/db2020?useUnicode=true&characterEncoding=utf-8&serverTimezone=Asia/Shanghai username: root password: zys123456
2.2 加入magic-api
1)在pom.xml
中添加magic-api
相關依賴:
<dependency>
<groupId>org.ssssssss</groupId>
<artifactId>magic-api-spring-boot-starter</artifactId>
<version>1.2.1</version>
</dependency>
2)在配置文件配置magic-api相關信息
magic-api: # 配置api管理頁面入口 web: /magic/web # 配置存儲方式 resource: # 配置接口資源存儲位置,可選file、database、redis type: database # 存儲表名 tableName: magic_api_file # 使用database、redis存儲時的key前綴 prefix: /db2020 # 是否是只讀模式 readonly: false # 啟用駝峰命名轉換 sql-column-case: camel # 分頁配置 page-config: # 頁大小的請求參數名稱 size: size # 頁碼的請求參數名稱 page: page # 未傳頁碼時的默認頁碼 default-page: 1 # 未傳頁大小時的默認頁大小 default-size: 10
3)創建表magic_api_file,用來存儲接口的配置信息
CREATE TABLE `magic_api_file` ( `id` bigint(255) NOT NULL AUTO_INCREMENT, `file_path` varchar(255) DEFAULT NULL, `file_content` text, PRIMARY KEY (`id`) )
4)啟動項目,訪問http://localhost:8080/magic/web,即可進入magic的管理頁面,如下圖:
默認是白色,可點擊皮膚設置黑色。
4.基本用法
4.1添加操作
1)在接口列表中添加添加按鈕,添加一個分組並設置分組前綴
2)在創建的分組中選擇右鍵,新建一個接口,填寫接口的相關信息和執行腳本,如下圖:
右側區域是編輯框,里面主要編寫magic的執行腳本,添加如下腳本:
return db.table('user').insert(body);
在底部的接口信息
中進行如下配置,POST
請求,請求路徑為/create
,請求參數放在請求body
中,是json字符串:
{ "username":"zhangsan", "password":"123", "addr":"湖北武漢" }
點擊右上角的執行按鈕,在執行結果中看到返回了success,說明添加成功。在數據庫中查詢,數據已經添加進來。
在瀏覽器中查看請求的路徑:此路徑的組成:http://localhost:8080+"分組前綴"+接口路徑。后續可直接根據此路徑執行用戶的添加操作,其他類同。
4.2修改操作
1)添加修改的接口,輸入執行腳本
return db.table('user').primary('id',body.id).update(body);
2)在接口信息
中進行如下配置,POST
請求,請求路徑為/update
,請求參數放在請求body
中:
修改id等於3的用戶的密碼和地址。
4.3刪除操作
1)添加刪除的接口,輸入執行腳本
return db.update('delete from user where id=#{id}');
2)在接口信息
中進行如下配置,POST
請求,請求路徑為/del/{id}
,請求參數放在路徑變量
中:
3)點擊執行按鈕,會把數據刪除,返回執行的結果。
4.4查詢操作
4.4.1根據id查詢
1)新建一個接口,添加執行腳本:
// 路徑變量從path對象中獲取 return db.table('user') .where() .eq('id',path.id) .selectOne();
2)在接口信息
中進行如下配置,GET
請求,請求路徑為/one/{id}
,請求參數放在路徑變量
中:
3)點擊執行按鈕,若有數據,則會返回數據,沒有數據則data的值是null
4.4.2 分頁查詢
由於已在配置文件中配置了分頁的參數信息,故這里直接使用。
1)新建一個接口,添加執行腳本:
return db.table('user').page();
2)在接口信息
中進行如下配置,GET
請求,請求路徑為/page
,請求參數放在請求參數
中:
3)點擊執行按鈕,若有數據,則會返回數據,沒有數據則data的值是null。
5.magic語法詳解
5.1db模塊
(1)db是默認引入的模塊,使用此模塊操作數據庫,需要使用return把結果返回。
(2)db.table()就指定了表名,可以使用期自帶的方法進行查詢等操作,但其只能對單表進行操作,多表無法使用。
(3)除了使用自帶的方法外,還可以自定義sql進行操作。具體見后面的章節
5.2自定義查詢
1)select()
根據sql查詢結果,返回的是list集合。
return db.select('select * from user')
若需要攜帶參數,可以使用#{}進行占位,其他查詢類似:
return db.select('select * from user where id = #{id} ')
2)selectInt()
根據sql查詢結果,返回的是int值。
return db.selectInt('select count(*) from user')
3)selectOne()
查詢單個對象,其返回值必須是小於等於一條數據,不能超過一條。
return db.selectOne('select * from user where id = #{id} ')
使用db.tableI()方式進行對比:
return db.table('user') .where() .eq('id',path.id) .selectOne();
兩種方式的效果一樣,只不過使用的模式不一樣。
4)selectValue()
查詢單個列的值。若查詢結果是多條,則只會返回第一條數據的對應字段信息。
return db.selectValue('select username from user where id = #{id}');
5)page()
分頁查詢。要傳遞分頁的條件(當前頁碼page,每頁條數size),會返回數據總條數和數據集合。
return db.page('select * from user')
使用db.tableI()方式進行對比:
return db.table('user').page()
兩種方式的效果是一樣的,可自由選擇。
6)update()
對於增刪改操作,都可以使用此方法,不過一般刪除會使用此方法,添加和修改均使用db.table()方式。原因是此方法必須使用get請求傳遞參數,不安全。
return db.update('delete from user where id=#{id}');
如根據id進行修改:使用post請求,把需要修改的字段和值使用json字符串方式傳遞即可,可參考4.2小節的說明。
return db.table('user').primary('id',body.id).update(body);
6.集成Swagger
當接口很多時,想查詢接口及路徑,Swagger是一個不錯的選擇。而magic也可以和Swagger進行無縫整合。
1)導入Swagger相關依賴
<dependency> <groupId>io.springfox</groupId> <artifactId>springfox-swagger2</artifactId> <version>2.9.2</version> </dependency> <dependency> <groupId>io.springfox</groupId> <artifactId>springfox-swagger-ui</artifactId> <version>2.9.2</version> </dependency>
2)在配置文件application.yml
中添加Swagger相關配置。
magic-api: # 集成Swagger配置 swagger-config: # 文檔名稱 name: MagicAPI # 文檔標題 title: MagicAPI Swagger Docs # 文檔描述 description: MagicAPI # 文檔版本號 version: 1.0 # 文檔資源位置 location: /v2/api-docs/magic-api/swagger2.json
3)重啟項目,訪問Swagger界面http://localhost:8080/swagger-ui.html,即可查看我們在magic-api
中寫的接口
7.攔截器配置
在開發環境,可以使用magic進行接口的開發,但是在正式環境中,其頁面是不能暴露出來的,同時swagger在正式環境也不能暴露。故需要攔截器進行攔截,同時其自帶SQL的攔截器,可以打印SQL的日志信息。
新建一個類,進行配置,具體見源碼:
/** * 攔截器配置 */ @Component public class MyInterceptor implements SQLInterceptor, HandlerInterceptor { Logger logger = LoggerFactory.getLogger(this.getClass()); @Value("${isAllowed}") private Boolean isAllowed; /*** * 自定義SQL攔截器,打印sql及參數 * @param boundSql * @param requestEntity */ @Override public void preHandle(BoundSql boundSql, RequestEntity requestEntity) { logger.warn("執行的SQL===> " + boundSql.getSql()); logger.warn("執行的SQL參數===> " + Arrays.toString(boundSql.getParameters())); } /** * 配置資源攔截器,開發頁面只能在開發中使用,在正式環境攔截 * * @param request * @param response * @param handler * @return */ @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws IOException { if (!isAllowed) { Map<String, Object> result = new HashMap<>(); result.put("msg", "抱歉,未找到可訪問資源!"); result.put("status", false); response.setCharacterEncoding("utf-8"); response.setHeader("Content-type", "text/html;charset=UTF-8"); response.getWriter().write(JSON.toJSONString(result)); return false; } return true; } }
另外還需要一個MVC的配置其注入攔截器和要攔截的資源:
/** * mvc配置,注入攔截器 */ @Configuration public class MyWebMvcConfigurer implements WebMvcConfigurer { @Autowired private MyInterceptor myInterceptor; @Override public void addInterceptors(InterceptorRegistry registry) { //addPathPatterns表示攔截所有請求,excludePathPatterns表示不攔截的請求 registry.addInterceptor(myInterceptor).addPathPatterns("/swagger-ui.html").addPathPatterns("/magic/**"); } }
這樣一來,就可以通過修改isAllowed的值選擇是否可訪問。到這里,基本的接口開發已經完成,只需前端進行整合即可。