當(dāng)前位置:首頁 > 公眾號精選 > 架構(gòu)師社區(qū)
[導(dǎo)讀]今天給大家分享幾個Java的開源類庫,親測非常好用!有了它們之后,你就可以和很多重復(fù)勞動說再見了。1.MapStructMapStruct是干什么的?MapStruct是個代碼產(chǎn)生器,它能直接根據(jù)注解生成Java對象對應(yīng)的轉(zhuǎn)換器。比如,直接把一個A類型的Java對象,給轉(zhuǎn)成B類型...

今天給大家分享幾個 Java 的開源類庫,親測非常好用!

有了它們之后,你就可以和很多重復(fù)勞動說再見了。

1. MapStruct

推薦幾個開源類庫,超好用,遠(yuǎn)離996!
MapStruct是干什么的?

MapStruct是個代碼產(chǎn)生器,它能直接根據(jù)注解生成 Java 對象對應(yīng)的轉(zhuǎn)換器。

比如,直接把一個 A 類型的 Java 對象,給轉(zhuǎn)成 B 類型的 Java 對象,只需要在他們之間配置上字段之間的映射關(guān)系即可。

為什么在項目里用它?

現(xiàn)在隨便一個項目都是多層的,尤其是 Web 項目,經(jīng)常需要在多層之間做對象模型轉(zhuǎn)換,比如 DTO 轉(zhuǎn)換成 BO。

DTO(Data Transfer Object):數(shù)據(jù)傳輸對象,Service 向外傳輸?shù)膶ο蟆?br>BO(Business Object):業(yè)務(wù)對象,由 Service 層輸出的封裝業(yè)務(wù)邏輯的對象。

但是這種轉(zhuǎn)換工作就像是小時候,老師罰我們抄寫名人名言 100 遍一樣,十分枯燥,還容易出錯。

像這樣:

public?class?CarMapper?{
????CarDto?carDoToCarDto(Car?car)?{
????????CarDto?carDto?=?new?CarDto();
????????carDto.setCarId(car.getCarId());
????????carDto.setWheel(car.getWheel());
????????carDto.setCarType(car.getCarType());
????????carDto.setCarColor(car.getCarColor());
????????......
????}

}
要是 Car 有幾十個字段,像 Car 一樣的又有幾十個類,你可以想一下,這種繁瑣程度。

在 MapStruct 之前,我們都是通過 Apache 或者 Spring 的 BeanUtils 工具,去自動做這種事情。

但是這類工具有兩個問題:

1.性能比較差

性能差主要是 Apache 的 BeanUtils 這套東西,它每次都要針對字段,做是否可讀寫的檢查,還要根據(jù)字段生成對應(yīng)的 PropertyDescriptor。

這些嚴(yán)重影響了它的性能,所以,在阿里 Java 手冊里,也不推薦用它。

Spring 的 BeanUtils,雖然精簡了很多 Apache 的 BeanUtils 的讀寫檢查以及對應(yīng)的屬性信息記錄,但是它依然是通過反射調(diào)用,而且是大量反射調(diào)用。這種性能也不能令人滿意。

2.運(yùn)行期做轉(zhuǎn)換,出錯就代表損失

BeanUtils 這類工具,有個統(tǒng)一的名稱,叫做 Java 對象映射框架。

它們大部分的實現(xiàn)都是在運(yùn)行期去執(zhí)行代碼,然后在 Java 對象之間去拷貝對應(yīng)的值。

運(yùn)行期間做這種事兒,有個最大的問題——整個項目啟動運(yùn)行后,才能發(fā)現(xiàn)錯誤。比如,轉(zhuǎn)換的時候,類型不一致導(dǎo)致報錯。

對于此種情況,咱們大家都知道,這事兒就像開業(yè)酬賓沒搞好,變成了開業(yè)仇賓……

如果能寫完代碼,編譯的時候就發(fā)現(xiàn)問題,這種損失就可以避免了。

MapStruct 的引入就是為了解決以上這兩個問題。

MapStruct 首先是個代碼產(chǎn)生器,它是根據(jù)注解,去產(chǎn)生一個專門用來轉(zhuǎn)換的工具類,這個工具類,就像我們自己寫的 Java 類一樣,可以直接被使用,這樣就避免了反射。

同時,它產(chǎn)生的轉(zhuǎn)換類也特別簡單,就是默認(rèn)會在兩個類型的 Java 對象之間,拷貝同名屬性的值。

如果有了配置,屬性不同名也可以拷貝。所以它的性能很好。

示例代碼如下:

@Mapper
public?interface?CarMapper?{

????CarMapper?INSTANCE?=?Mappers.getMapper(?CarMapper.class?);

????@Mapping(target?=?"seatCount",?source?=?"numberOfSeats")
????CarDto?carBoToCarDto(Car?car);
}
MapStruct由于是個代碼產(chǎn)生器,就帶來了個巨大的好處,就是這家伙是在編譯階段就會生成對應(yīng)的類,所以,如果有了類似類型轉(zhuǎn)換不過去的問題,直接就編譯報錯了,根本等不到運(yùn)行才發(fā)現(xiàn)。這樣的話,就不會造成什么損失,這真是件十分 Nice 的事情。

代碼庫地址

https://github.com/mapstruct/mapstruct

2. Retrofit

推薦幾個開源類庫,超好用,遠(yuǎn)離996!
Retrofit 是干什么的?

Retrofit 就是一套 Http 客戶端,可以用來訪問第三方的 Http 服務(wù)。

比如,咱們代碼里想調(diào)用一個 Http 協(xié)議的 URL,就可以用它來訪問這個 URL,獲取響應(yīng)結(jié)果。

為什么在項目里用它?

在公司里,我們有些項目有如下的特點:

  1. 不是基于 Spring 的項目
  2. 需要經(jīng)常訪問大量的第三方 Http 服務(wù)
  3. 訪問 Http 服務(wù)的模型通常是異步回調(diào)
以前的時候,我們訪問 Http 服務(wù),都是直接用的 HttpClient。

可是吧,HttpClient 用起來實在夠麻煩的。主要也存在兩個問題:

1.請求參數(shù)和 URL 拼接實在繁瑣

請求參數(shù)和 URL 拼接實在是太煩人了。你想想,每調(diào)用一個接口,就需要自己去拼接參數(shù),有的 URL,甚至十幾二十個參數(shù)需要拼接。

拼接這事兒簡單、枯燥、重復(fù),還沒有技術(shù)含量,但是工作量卻不小,時間真的算浪費(fèi)了。

URIBuilder?uriBuilder?=?new?URIBuilder(uriBase);
uriBuilder.setParameter("a",?"valuea");
uriBuilder.setParameter("b",?"valueb");
uriBuilder.setParameter("c",?"valuec");
uriBuilder.setParameter("d",?"valued");
uriBuilder.setParameter("e",?"valuee");
uriBuilder.setParameter("f",?"valuef");
uriBuilder.setParameter("g",?"valueg");
uriBuilder.setParameter("h",?"valueh");
uriBuilder.setParameter("i",?"valuei");
...
2.異步回調(diào)需要自己搞

異步回調(diào)這種模型不好處理,主要就是需要自己去搞線程池,還要對線程池管理,還要考慮出錯的重試之類的容錯問題,實在麻煩。

所以,我們就需要一套能用法簡單,不用我們一直搞拼接參數(shù),自己搞線程管理就能完成對第三方 Http 服務(wù)訪問的庫。

其實我們也想過用 Feign 這套框架的。但是,這套東西和 Spring 綁定的太緊了。如果離開 Spring,它的一些功能就沒法簡單的通過注解直接使用,必須自己寫代碼調(diào)用。

而且,F(xiàn)eign 要實現(xiàn)異步回調(diào)方式使用,尤其在協(xié)程方面,還是需要自己開發(fā)。

這時候,Retrofit 就跳進(jìn)了我們的選型里。

Retrofit 的模型里,異步回調(diào)模型它支持的很好,我們只需要實現(xiàn)一個 Callable 就夠了。

并且最清爽的是,它和 Spring 沒什么關(guān)系。

Retrofit?retrofit?=?new?Retrofit.Builder()
????????.baseUrl("http://xxx.example.com/")
????????.build();

public?interface?BlogService?{
????@GET("blog/{id}")
????Call?getBlog(@Path("id")?int?id);
}

BlogService?service?=?retrofit.create(BlogService.class);

Call?call?=?service.getBlog(2);
//?用法和OkHttp的call如出一轍,
//?回調(diào)
call.enqueue(new?Callback()?{
????@Override
????public?void?onResponse(Call?call,?Response?response)?{
????????try?{
????????????System.out.println(response.body().string());
????????}?catch?(IOException?e)?{
????????????e.printStackTrace();
????????}
????}

????@Override
????public?void?onFailure(Call?call,?Throwable?t)?{
????????t.printStackTrace();
????}
});
你看,只需要寫上這些代碼,我們就不需要操心惱人的 Url 拼接和異步回調(diào)的管理問題了。全交給了 Retrofit,著實推薦。

代碼庫地址

https://github.com/square/retrofit

3. Faker

推薦幾個開源類庫,超好用,遠(yuǎn)離996!
Faker 是干什么的?

Faker 是專門用來產(chǎn)生各種假數(shù)據(jù)的輔助工具庫。

比如,你想產(chǎn)生個和真實數(shù)據(jù)一樣的有姓名、有地址的用戶。

為什么在項目里用它?

我們經(jīng)常需要造數(shù)據(jù)去測試,但是,如果沒有工具輔助,我們自己造數(shù)據(jù),存在一些問題。

1.數(shù)據(jù)是需要格式的

很多關(guān)于項目,都需要一些格式上盡量能模仿真實世界的數(shù)據(jù)。

比如,國內(nèi)用戶的姓名,大部分都是兩字、三字的姓名,叫王大,就不能叫 王da 這種。

又比如,國內(nèi)的地址是 xx市xx區(qū)xx街道xx號 這種的,就不能胡寫一個幾個沒意義的漢字來當(dāng)?shù)刂贰?/p>用貼近真實格式的數(shù)據(jù),一來可以測出我們對用戶的數(shù)據(jù)解析是否存在問題,二來可以測出數(shù)據(jù)庫內(nèi)的字段長度是否沒問題。

所以,格式對產(chǎn)生出可靠地測試結(jié)果,是很重要的。

2.數(shù)據(jù)的量大

有的測試數(shù)據(jù)量都是上十萬、百萬的,這些量級的數(shù)據(jù)并不是只會產(chǎn)生一次。

甚至幾乎每個項目,每個項目的每次測試,可能都會需要新的數(shù)據(jù),需要能源源不斷地產(chǎn)生出來。

更甚至的是,有時候還想要根據(jù)我們的要求,在恰當(dāng)?shù)臅r候,產(chǎn)生某種關(guān)系的數(shù)據(jù),或者以某些特定頻率產(chǎn)生。比如,兩秒后產(chǎn)生一次數(shù)據(jù);比如,產(chǎn)生一批姓王的數(shù)據(jù)。

以上這三種要求綜合起來,要是我們自己造數(shù)據(jù),那真是要了命了。

與其自己開發(fā),不如用現(xiàn)成的——Faker 庫被我們找到了。

Faker庫可以創(chuàng)造三百多種數(shù)據(jù),而且還很容易對它進(jìn)行擴(kuò)展改造,去產(chǎn)生更多的貼合我們需求的數(shù)據(jù)。

Faker?faker?=?new?Faker();

String?name?=?faker.name().fullName();?//?Miss?Samanta?Schmidt
String?firstName?=?faker.name().firstName();?//?Emory
String?lastName?=?faker.name().lastName();?//?Barton

String?streetAddress?=?faker.address().streetAddress();?//?60018?Sawayn?Brooks?Suite?449
幾行代碼,我們需要的一個用戶就有了。

用上 Faker 后,小伙伴們紛紛表示“有更多的時間摸魚了”。

代碼庫地址

https://github.com/DiUS/java-faker

4. Wiremock

推薦幾個開源類庫,超好用,遠(yuǎn)離996!
Wiremock 是干什么的?

Wiremock 是一個可以模擬服務(wù)的測試框架。

比如,你想測試訪問阿里的支付相關(guān)接口的代碼邏輯,就可以用它來做測試。

為什么在項目里用它?

比如,我們需要調(diào)用銀行接口去做資金業(yè)務(wù),調(diào)用微信接口去做微信登錄……這些調(diào)用第三方服務(wù)的測試存在一個問題:

即太過依賴對方的平臺。假如對方平臺限制了一些 IP,或者限制了訪問頻率,又或者就是服務(wù)出現(xiàn)了維護(hù),都會影響我們自身的功能測試。

為了解決上述問題,在之前,我們需要自己寫代碼模仿第三方的接口,等我們自己全部測試沒問題了,再去和第三方聯(lián)調(diào)。對于這種模擬出來的接口,我們稱作擋板。

可是,這種方式是個苦活,沒人愿意干。因為每接入一個第三方,可能都需要做擋板。辛苦做個擋板,就是單純?yōu)榱藴y試。如果第三方的接口做了改造,你這邊還得跟著改。

大家可以想想,換成你自己,你愿意做這么件事兒嗎?

這時候,Wiremock 的價值就體現(xiàn)出來了。有了 Wiremock,擋板這種東西就再也不存在了,直接在單元測試?yán)锬M測試即可,像這樣:

WireMock.stubFor(get(urlPathMatching("/aliyun/.*"))
????????????????.willReturn(aResponse()
????????????????????????.withStatus(200)
????????????????????????.withHeader("Content-Type",?APPLICATION_JSON)
????????????????????????.withBody("\"testing-library\":?\"WireMock\"")));

CloseableHttpClient?httpClient?=?HttpClients.createDefault();
HttpGet?request?=?new?HttpGet(String.format("http://localhost:%s/aliyun/wiremock",?port));
HttpResponse?httpResponse?=?httpClient.execute(request);
String?stringResponse?=?convertHttpResponseToString(httpResponse);

verify(getRequestedFor(urlEqualTo(ALIYUN_WIREMOCK_PATH)));
assertEquals(200,?httpResponse.getStatusLine().getStatusCode());
assertEquals(APPLICATION_JSON,?httpResponse.getFirstHeader("Content-Type").getValue());
assertEquals("\"testing-library\":?\"WireMock\"",?stringResponse);
代碼庫地址

https://github.com/wiremock/wiremock

結(jié)語

雖然 Java 有很多遭人詬病的地方,但是 Java 最重要的優(yōu)點之一,就是它的生態(tài),有其琳瑯滿目的各種工具類庫。

希望大家都“懶”一點,不要埋頭去做無效的苦干,不要自己造輪子,你要相信:

你遇到的問題,基本已經(jīng)有很多人遇到過了,而且已經(jīng)被牛人給解決了,把輪子都給你造好了。

本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點,本站亦不保證或承諾內(nèi)容真實性等。需要轉(zhuǎn)載請聯(lián)系該專欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請及時聯(lián)系本站刪除。
換一批
延伸閱讀

9月2日消息,不造車的華為或?qū)⒋呱龈蟮莫毥谦F公司,隨著阿維塔和賽力斯的入局,華為引望愈發(fā)顯得引人矚目。

關(guān)鍵字: 阿維塔 塞力斯 華為

加利福尼亞州圣克拉拉縣2024年8月30日 /美通社/ -- 數(shù)字化轉(zhuǎn)型技術(shù)解決方案公司Trianz今天宣布,該公司與Amazon Web Services (AWS)簽訂了...

關(guān)鍵字: AWS AN BSP 數(shù)字化

倫敦2024年8月29日 /美通社/ -- 英國汽車技術(shù)公司SODA.Auto推出其旗艦產(chǎn)品SODA V,這是全球首款涵蓋汽車工程師從創(chuàng)意到認(rèn)證的所有需求的工具,可用于創(chuàng)建軟件定義汽車。 SODA V工具的開發(fā)耗時1.5...

關(guān)鍵字: 汽車 人工智能 智能驅(qū)動 BSP

北京2024年8月28日 /美通社/ -- 越來越多用戶希望企業(yè)業(yè)務(wù)能7×24不間斷運(yùn)行,同時企業(yè)卻面臨越來越多業(yè)務(wù)中斷的風(fēng)險,如企業(yè)系統(tǒng)復(fù)雜性的增加,頻繁的功能更新和發(fā)布等。如何確保業(yè)務(wù)連續(xù)性,提升韌性,成...

關(guān)鍵字: 亞馬遜 解密 控制平面 BSP

8月30日消息,據(jù)媒體報道,騰訊和網(wǎng)易近期正在縮減他們對日本游戲市場的投資。

關(guān)鍵字: 騰訊 編碼器 CPU

8月28日消息,今天上午,2024中國國際大數(shù)據(jù)產(chǎn)業(yè)博覽會開幕式在貴陽舉行,華為董事、質(zhì)量流程IT總裁陶景文發(fā)表了演講。

關(guān)鍵字: 華為 12nm EDA 半導(dǎo)體

8月28日消息,在2024中國國際大數(shù)據(jù)產(chǎn)業(yè)博覽會上,華為常務(wù)董事、華為云CEO張平安發(fā)表演講稱,數(shù)字世界的話語權(quán)最終是由生態(tài)的繁榮決定的。

關(guān)鍵字: 華為 12nm 手機(jī) 衛(wèi)星通信

要點: 有效應(yīng)對環(huán)境變化,經(jīng)營業(yè)績穩(wěn)中有升 落實提質(zhì)增效舉措,毛利潤率延續(xù)升勢 戰(zhàn)略布局成效顯著,戰(zhàn)新業(yè)務(wù)引領(lǐng)增長 以科技創(chuàng)新為引領(lǐng),提升企業(yè)核心競爭力 堅持高質(zhì)量發(fā)展策略,塑強(qiáng)核心競爭優(yōu)勢...

關(guān)鍵字: 通信 BSP 電信運(yùn)營商 數(shù)字經(jīng)濟(jì)

北京2024年8月27日 /美通社/ -- 8月21日,由中央廣播電視總臺與中國電影電視技術(shù)學(xué)會聯(lián)合牽頭組建的NVI技術(shù)創(chuàng)新聯(lián)盟在BIRTV2024超高清全產(chǎn)業(yè)鏈發(fā)展研討會上宣布正式成立。 活動現(xiàn)場 NVI技術(shù)創(chuàng)新聯(lián)...

關(guān)鍵字: VI 傳輸協(xié)議 音頻 BSP

北京2024年8月27日 /美通社/ -- 在8月23日舉辦的2024年長三角生態(tài)綠色一體化發(fā)展示范區(qū)聯(lián)合招商會上,軟通動力信息技術(shù)(集團(tuán))股份有限公司(以下簡稱"軟通動力")與長三角投資(上海)有限...

關(guān)鍵字: BSP 信息技術(shù)
關(guān)閉
關(guān)閉