前幾天偶爾在網上看到thrift的信息,其內容和做用極大的引發了個人興趣,由於我也是作iOS開發的,經過在網上的查詢發現信息雖然不少實用的不多,容易誤導他人,通過本身的成功實踐,作了筆錄,爲了方便朋友瞭解和閱讀,就也囉裏囉嗦的整理一下繁瑣的東西,但願對個人朋友和他人能有所幫助。php
我是在Mac上經過終端先安裝brew,再在終端輸入brew命令行來安裝thrift的,固然還有其餘的方式,你們能夠去網上了解一下,而我用brew是對其偏心,是由於brew做爲Mac OSX上的軟件包管理工具,能在Mac中方便的安裝軟件或者卸載軟件, 只須要一個命令, 而不用麻煩的終端命令,很是方便,另外brew 又叫Homebrew。具體安裝步驟很是簡單以下:html
1,打開終端,輸入ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"。固然也能夠直接複製這個命令行粘貼到終端,按回車鍵java
2,而後一會會跳出這個語句:Press RETURN to continue or any other key to abort,其意思就是按回車鍵繼續,或者其餘鍵跳出,固然咱們按回車鍵,而後就開始安裝了。node
3,注意,有時候過程可能稍慢,請耐心等候,其以上過程可能須要輸入你的本機帳號密碼,直接輸入而後按回車鍵便可,python
第一次我還不肯定是否真的安裝成功,就有操做一次結果提醒我已經安裝過,再次安裝會覆蓋之前的,因此你們不用擔憂再次輸入操做,如圖:jquery
/usr/local/bin不在PATH中
找到解決方式。其實解決這個問題真的很簡單。以下:
sudo vim .bash_profile
添加:
保存,source .bash_profile使配置修改生效。
從新啓動終端 再次使用brew 命令就ok了。
使用brew安裝軟件,經過在終端一行命令便可(brew的命令都是在終端輸入的),如:sudo brew install git,就會安裝git,咱們也能夠sudo brew update更新brew,經常使用命令列示以下:ios
1,sudo brew uninstall wget 卸載軟件wgetgit
2, sudo brew search /wge*/ 查詢軟件wgetgithub
3, sudo brew list 列出已安裝的軟件apache
4, sudo brew home 用瀏覽器打開brew的官方網站
5, sudo brew info 顯示軟件信息
6, sudo brew deps 顯示包依賴
好比:輸入3,和4
固然經過以上就知道如何安裝thrift了,只須要在終端輸入brew命令行sudo brew install thrift,過程如圖:
注意過程很慢,可從圖最下3.9%,最後安裝成功可從下圖比較:
一直到出現你的本機名的時候纔算成功
不過我在安裝輸入sudo brew install thrift 的時候提示:Running Homebrew as root is extremely dangerous and no longer supported
參考:mac下面經過brew安裝東西的時候報Error: Running Homebrew as root is extremely dangerous and no longer supported的解決
其實就是把 sudo 去掉, 直接輸入 brew install thrift
安裝成功你們就可使用thrift了,若是不瞭解thrift的朋友能夠在網上查查,這裏也作一些瞭解:
thrift最初由Facebook研發,主要用於各個服務之間的RPC通訊,支持跨語言,經常使用的語言ActionScript3,glibc,cocoa(開發ios用的),C++,C#,delphi,erlang,go,haskell,html,java,javame(山寨機開發),jquery,node.js,Ocaml,perl,php,python,ruby,smalltalk,xsd,簡單的說,就是可讓人快速的寫Socket Server(服務器)和Client(客戶端)。其實不用thrift開發socket也不難,那麼爲何要用thrift開發呢?主要有兩個緣由,一個是由於thrift自己幫你封裝了不少基本的東西,你不須要本身去寫socket裏面的bind,accept之類的,以及他們的邏輯。能夠很快速的開發基於進程的,線程的,SSL的socket。第二個理由是標準化,跨語言和跨平臺,windows不算在其中。主要是在各類Posix兼容的操做系統中均可以不須要改造基本直接可用,支持的語言種類也不少,基本你會寫的,他都支持。你不會寫的,他也支持。相似的項目還有ICE和Avro,可是感受都沒有thrift作的易用性好。並且這是facebook開源的諸多項目中,爲數很少的能正常編譯的軟件,
使用thrift須要先定義接口文件,在thrift裏簡稱叫IDL,全稱叫Interface Description Language,接口描述語言。接口描述語言裏面須要定義接口中所使用的數據類型,方法等等
數據類型包括:
基本類型:
bool: 布爾類型(true或者false)
byte: 有符號8位整型
i16: 有符號16位整型
i32: 有符號32位整型
i64: 有符號64位整型
double: 64位浮點數
string: UTF8編碼的字符串
特殊類型:
binary: 未編碼的二進制字節流
struct:結構體類型
container:
list:列表,能夠理解爲數組,其中的元素能夠是任意類型的。
exceptions:
用來拋出你本身定義的異常狀況
service:
這個是最重要的定義,有些地方說是虛函數,可是理解成你程序中所使用的方法更容易明白一些。他須要你定義返回類型,這有點相似於C或者java的函數定義。但你要明白,這個返回是給socket的。若是你定義錯了,將不只僅是你得不到返回值這麼簡單的事情。而是程序會報錯
如今,再按照上面的步驟進行下去,就能夠正確安裝thrift了.
1,建立一個服務Hello,建立文件Hello.thrift,代碼以下:
namespace java service.demo service Hello{ string helloString(1:string para) }
這裏定義了一個名爲helloString的方法,入參和返回值都是一個string類型的參數.
2,終端進入Hello.thrift所在目錄,執行命令:
thrift -r -gen java Hello.thrift
發如今當前目錄下多了一個gen-java的目錄,裏面的有一個Hello.java的文件.這個java文件包含Hello服務的接口定義Hello.Iface,以及服務調用的底層通訊細節,包括客戶端的調用邏輯Hello.Client以及服務端的處理邏輯Hello.Processor,
3,建立一個Maven管理的Java項目,pom.xml中添加相關的依賴,並將Hello.java文件複製到項目中:
<dependency> <groupId>org.apache.thrift</groupId> <artifactId>libthrift</artifactId> <version>0.10.0</version> </dependency> <dependency> <groupId>org.slf4j</groupId> <artifactId>slf4j-log4j12</artifactId> <version>1.7.5</version> </dependency>
此處須要注意,若是你的pom.xml中原來就有的話,難麼,你須要先新建標籤dependencies;
好比個人:
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>thrift_test</groupId> <artifactId>thrift_test</artifactId> <version>1.0-SNAPSHOT</version> <dependencies> <dependency> <groupId>org.apache.thrift</groupId> <artifactId>libthrift</artifactId> <version>0.10.0</version> </dependency> <dependency> <groupId>org.slf4j</groupId> <artifactId>slf4j-log4j12</artifactId> <version>1.7.5</version> </dependency> </dependencies> </project>
注意到了嗎,新建了<dependencies>標籤;
4,建立HelloServiceImpl實現Hello.Iface接口:
package service.demo; import org.apache.thrift.TException; /** * @author yogo.wang * @date 2017/02/21-下午2:13. */ public class HelloServiceImpl implements Hello.Iface { public String helloString(String para) throws TException { return "result:"+para; } }
5,建立服務端實現代碼HelloServiceServer,把HelloServiceImpl做爲一個具體的處理器傳遞給Thrift服務器:
package service.demo; import org.apache.thrift.TProcessor; import org.apache.thrift.protocol.TBinaryProtocol; import org.apache.thrift.server.TServer; import org.apache.thrift.server.TSimpleServer; import org.apache.thrift.transport.TServerSocket; import org.apache.thrift.transport.TTransportException; /** * @author yogo.wang * @date 2017/02/21-下午2:15. */ public class HelloServiceServer { /** * 啓動thrift服務器 * @param args */ public static void main(String[] args) { try { System.out.println("服務端開啓...."); TProcessor tprocessor = new Hello.Processor<Hello.Iface>(new HelloServiceImpl()); // 簡單的單線程服務模型 TServerSocket serverTransport = new TServerSocket(9898); TServer.Args tArgs = new TServer.Args(serverTransport); tArgs.processor(tprocessor); tArgs.protocolFactory(new TBinaryProtocol.Factory()); TServer server = new TSimpleServer(tArgs); server.serve(); }catch (TTransportException e) { e.printStackTrace(); } } }
6,建立客戶端實現代碼HelloServiceClient,調用Hello.client訪問服務端的邏輯實現:
package service.demo; import org.apache.thrift.TException; import org.apache.thrift.protocol.TBinaryProtocol; import org.apache.thrift.protocol.TProtocol; import org.apache.thrift.transport.TSocket; import org.apache.thrift.transport.TTransport; import org.apache.thrift.transport.TTransportException; /** * @author yogo.wang * @date 2017/02/21-下午2:35. */ public class HelloServiceClient { public static void main(String[] args) { System.out.println("客戶端啓動...."); TTransport transport = null; try { transport = new TSocket("localhost", 9898, 30000); // 協議要和服務端一致 TProtocol protocol = new TBinaryProtocol(transport); Hello.Client client = new Hello.Client(protocol); transport.open(); String result = client.helloString("哈哈"); System.out.println(result); } catch (TTransportException e) { e.printStackTrace(); } catch (TException e) { e.printStackTrace(); } finally { if (null != transport) { transport.close(); } } } }
所有工做完成後,下面來測試一下,先執行服務端main方法,在執行客戶端main方法,會在客戶端控制檯打印出:result:哈哈.
這裏注意幾點:
(1)先執行服務端的main方法,而後執行客戶端的main方法;
(2)當把Hello.java文件放到項目中的時候,個人老是報錯,說thrift生成的Hello.java文件 中的override 不能重寫,我直接把關鍵字override註銷了;錯誤消失;
在terminal 中執行 mvn clean; 成功
執行mvn clean install 成功
執行 mvn clean install -Dmaven.test.skip=true 成功;
例子下載地址:thrift 架構的Java的小例子 demo