衆所周知,Thrift
是一個RPC的框架,其可用於不一樣語言之間的服務相互調用。好比最近接觸到的一個運用環境: *前端使用Node.Js重構了部分咱們的老舊代碼(先後端未分離的SpringBoot項目),咱們後端使用zookeeper+Thrift爲新的Node.Js前端項目提供基本的DAO層服務支持*
因此基於這個項目,我大概瞭解了一下Thrift,該文章則均以Java
爲基礎語言。前端
由於後端已經有一套服務註冊和暴露機制,因此服務已是RPC的形式,因此咱們僅須要使用Thrift IDL
來重寫一遍咱們須要暴露的方法便可,Thrift IDL
有兩個比較好的參考選擇:java
thrift
基本支持全部的Java基本類型以及引用類型:bool(boolean)、byte(byte)、i16(short)、i32(int)、i64(long)、double(double)、string(String)、binary(byte[])以及一些經常使用容器和自建類型(Struct);services
和struct
放在一個.thrift
文件中,這種方式將service
和其所需的struct
綁定在一塊兒,會致使個別struct
重複出如今多個.thrift
文件中,致使大量的代碼重複。因此,應該與Java的編碼風格保持一致,採用POJO類(struct)
+接口(services)
的方案,利用include
關鍵字,將struct引進services中使用。Java基本類型
,可是注意是基本類型,相似於Java中的Integer、Boolean、Long、Double等基本類型包裝類是不支持的,或許你可使用struct
實現一個相似的包裝類結構進行數據承載。enum
枚舉類型,可是若是沒有description
的枚舉類型也能夠直接使用string
來承接。struct
結構體的數據的,因此struct
中的數據順序必定要和java
文件中的一致,不然可能會出現數據對應關係錯亂或者數據丟失。struct
體時,要注意java對象
的父級,若是父級中含有變量,不要忘記其變量的書寫,且順序必定在前面。java對象
中的常量能夠不出如今thrift idl
的struct
結構體中。Date
咱們固定使用timestamp
時間戳的形式傳遞,即long
型。咱們如今有一個Account
對象,須要將其變爲thrift
文件,Account
的結構以下:node
public class Account extends BaseEntity implements SecurityUser{
private static final long serialVersionUID = 1L;
public static final String PASSWORD_TIME = "passwordTime";
private String password; // 密碼
private Date createTime; // 建立時間
private Date lastLoginTime; // 最後登陸時間
private int loginCount = 0; // 登陸次數
private boolean enabled = true;
private Date passwordTime; //密碼修改時間
private boolean freeze; //帳戶是否被凍結
//該帳戶的綁定信息,非持久化字段
@Transient
private Set<Binding> bindings = new HashSet();
@Transient
private String name;//保存登陸時用的用戶名,非持久化字段
//省略getter和setter
}
複製代碼
根據上述結構咱們能夠書寫以下的Account.thrift
:apache
/**
* 帳戶信息
*/
struct Account{
1: string password, //密碼
2: i64 createTime, //建立時間
3: i64 lastLoginTime, //最後登陸時間
4: i32 loginCount, //登錄次數
5: bool enabled=true,
6: i64 passwordTime, //密碼修改時間
7: bool freeze, //帳戶是否被凍結
}
複製代碼
可是通過測試前端調用接口獲取到的Account
信息,要麼數據錯位,要麼數據丟失,問題出在哪裏呢?這時,咱們發現Account
對象繼承了BaseEntity
,實現了SecurityUser
,咱們去查看一下繼承的BaseEntity
對象:後端
public abstract class BaseEntity extends IdEntity implements Cacheable, TypeAliases{
private static final long serialVersionUID = 1L;
private static final String CACHE_NAMESPACE = "entity" ;
public BaseEntity() {
super();
}
public BaseEntity(Long id) {
super(id);
}
//省略下方代碼
}
複製代碼
咱們發現其中並無很是量變量,可是BaseEntity
又繼承了IdEntity
,因此咱們得再去看一看IdEntity
:框架
public abstract class IdEntity implements Serializable{
private static final long serialVersionUID = -1L;
/**
* Hibernate JPA環境中使用@GenericGenerator註解生成主鍵
*/
@Id
@GeneratedValue(generator = "longIdGenerator")
@GenericGenerator(name = "longIdGenerator", strategy = "net.qiyuesuo.framework.id.LongIdGenerator")
protected Long id;
public IdEntity() {
super();
}
public IdEntity(Long id) {
super();
this.id = id;
}
//省略getter和setter
}
複製代碼
這時咱們發現IdEntity
中含有一個Id
的變量,因此咱們須要重構一下剛剛書寫的Account.thrift
:ide
/**
* 帳戶信息
*/
struct Account{
1: i64 id, //帳戶Id
2: string password, //密碼
3: i64 createTime, //建立時間
4: i64 lastLoginTime, //最後登陸時間
5: i32 loginCount, //登錄次數
6: bool enabled,
7: i64 passwordTime, //密碼修改時間
8: bool freeze, //帳戶是否被凍結
}
複製代碼
書寫完Account.thrift
後,咱們須要寫其相應的接口即service
,查看Interface AccountService
:學習
public interface AccountService {
/**
* 建立帳戶
* @param account
* @return 返回建立後的Account對象
*/
Account create(Account account);
/**
* 更新帳戶信息
* @param account
* @return
*/
boolean update(Account account);
/**
* 修改開放平臺密碼 傳入的 密碼是未加密的
* @param username
* @param newPassword
* @return
*/
boolean updatePasswd(String username, String newPassword);
/**
* 重置密碼
* @param username 用戶名
* @param newPassword 新密碼
*/
void resetPasswd(String username, String newPassword);
/**
* 驗證用戶名和密碼是否匹配
* @param username
* @param password
*/
boolean matches(String username,String password);
}
複製代碼
有不少方法,可是若是前端只須要用到校驗用戶名和密碼的方法,那麼我就只須要暴露建立帳戶的方法,即:測試
include "Account.thrift"
service AccountService{
/*
* 校驗用戶名和密碼
*/
bool matches(1: string username,2: string password),
}
複製代碼
這樣咱們就完成了一個關於用戶名和密碼的校驗方法的thrift idl
文檔的書寫,前端須要執行thrift
的一條語句對文件進行編譯,以node.js
爲例(具體可參考:Apache Thrift Tutorial)ui
thrift --gen <language> <Thrift filename>
thrift -r --gen js:node Account.thrift
thrift -r --gen js:node AccountService.thrift複製代碼