大家好,我是小寧
這半個(gè)月鼓搗了不少工具類,搞著搞著發(fā)現(xiàn),這些工具類雖然功能不一樣,但是封裝的思路和組織的方式很像,可以提煉出一些共同點(diǎn)出來, 這是很值得分享的事.
所謂授人以魚,不如授人以漁,可能看我的文章,代碼沒學(xué)會幾行,但相信我,收獲的絕不止是代碼
工具類案例
先看下我這段時(shí)間的成果(安裝包還沒在網(wǎng)上發(fā)布,可以找我拿安裝包)
工具類源碼示例
我選取了幾個(gè)工具包展示出來,可以看到,一個(gè)工具的組成,大致由三種類組成: 1. xxxConfig. 2. xxxTools. 3.model包,存放工具的請求/返回實(shí)體
我們以釘釘?shù)墓ぞ甙鼮槔M(jìn)行剖析:
DingConfig.java
public class DingConfig {
// 釘釘添加機(jī)器人時(shí)獲得的url
private String url;
// 釘釘添加機(jī)器人時(shí)獲取的secret
private String secret;
// 在原有的URL之上添加一些參數(shù)
public String getUrl() {
Long timestamp = System.currentTimeMillis();
String sign = getSign(timestamp);
returnurl+"×tamp="+timestamp+"&sign="+sign;
}
/**
* 通過時(shí)間戳和sercet進(jìn)行加密.
*/
public String getSign(Long timestamp) {
try {
String stringToSign = timestamp +"\n"+ secret;
Mac mac = Mac.getInstance("HmacSHA256");
mac.init(new SecretKeySpec(secret.getBytes("UTF-8"),"HmacSHA256"));
byte[] signData = mac.doFinal(stringToSign.getBytes("UTF-8"));
returnURLEncoder.encode(Base64.getEncoder().encodeToString(signData),"UTF-8");
}catch (Exception e){
returnnull;
}
}
}
如上所示,我們可以看到,這個(gè)配置類不僅僅是存一些值, 一些常用的和配置相關(guān)的功能也都在這里,這里有點(diǎn)像領(lǐng)域驅(qū)動的充血實(shí)體類的感覺了.
DingMessage.java 已精簡掉相關(guān)的get/set方法
public class DingMessage {
// 定義釘釘消息的類型,純文字類型
public static final String TYPE_TEXT="text";
// 定義釘釘消息的類型,帶按鈕可跳轉(zhuǎn)的類型
public static final String TYPE_ACTION_CARD ="actionCard";
privateString? msgtype;
privateTextMessage text;
privateActionCardMessage actionCard;
// 采用靜態(tài)內(nèi)部類的形式來組織嵌套的實(shí)體類
static class TextMessage{
privateString content;
public String getContent() {
return content;
}
}
// 采用靜態(tài)內(nèi)部類的形式來組織嵌套的實(shí)體類
static class ActionCardMessage{
privateString title;
privateString text;
privateString hideAvatar;
privateString btnOrientation;
privateList btns;
}
// 采用靜態(tài)內(nèi)部類的形式來組織嵌套的實(shí)體類
static class DButton{
privateString title;
privateString actionURL;
}
// 對外提供的初始化函數(shù),對外部看來,只需要傳一個(gè)content就可以了
// 拼實(shí)體類的操作,放到了實(shí)體類里面
public static DingMessage initTextMessage(String content){
TextMessage textMessage = new TextMessage();
textMessage.content = content;
DingMessage dingMessage = new DingMessage();
dingMessage.text = textMessage;
dingMessage.msgtype = TYPE_TEXT;
return dingMessage;
}
}
通過我們和第三方都是通過json的方式進(jìn)行交互. 要么就是map轉(zhuǎn)json,要么就是實(shí)體類轉(zhuǎn)json, 這里我都是使用的實(shí)體類轉(zhuǎn)json, 也沒有拆分很多的實(shí)體類,直接通過靜態(tài)內(nèi)部類就可以完成實(shí)體的組織
DingTools.java
// 提供給外部使用的工具類
public static void sendText(String content,DingConfig config){
? ? ? ? // 構(gòu)造請求實(shí)體類
? ? ? ? DingMessage message = DingMessage.initTextMessage(content);
? ? ? ? // 轉(zhuǎn)成json
? ? ? ? String s = JSON.toJSONString(message);
? ? ? ? // 請求第三方
? ? ? ? HttpResponse<String> response = HttpTools.doPost(config.getUrl(),s , HttpRequest.JSON_HEADER, String.class);
? ? ? ? // 處理返回值
? ? ? ? System.out.println(response.getBody());
? ? }
如上源碼所示,真得到工具類里面大致分為四步, 構(gòu)造請求實(shí)體類,轉(zhuǎn)成json,請求, 然后處理返回值,同樣的去請求微信/redis,也大致都是這個(gè)結(jié)構(gòu)
調(diào)用方
public static void main(String[] args) {
// 配置config
DingConfigconfig= new DingConfig();
config.setUrl("https://oapi.dingtalk.com/robot/send?access_token=xx");
config.setSecret("xxxx");
// 調(diào)工具類
DingTools.sendActionCard("測試審核","這是一條測試審核的信息",config);
}
對調(diào)用方來說, 就兩個(gè)事, 拼Config , 然后調(diào)用工具類. 通過傳入的Config不一樣, 工具類可以操作不同主體的第三方, 這個(gè)跟所謂的無狀態(tài)就很像了
總結(jié)
思路思路, 本篇文章只要強(qiáng)調(diào)的是思路, 大家以后在封裝自己的工具類時(shí),也可以考慮使用這樣的結(jié)構(gòu), 一個(gè)Config , 一個(gè)實(shí)體包, 一個(gè)Tools. 這樣對調(diào)用方和對自己來說,都很簡單.