推荐几个开源类库,超好用,远离996!

今天给大家分享几个 Java 的开源类库,亲测非常好用!

有了它们之后,你就可以和很多重复劳动说再见了。

1. MapStruct

295b14eb8d45e85969fddcfacf0e0391.png

MapStruct是干什么的?

MapStruct是个代码产生器,它能直接根据注解生成 Java 对象对应的转换器。

比如,直接把一个 A 类型的 Java 对象,给转成 B 类型的 Java 对象,只需要在他们之间配置上字段之间的映射关系即可。

为什么在项目里用它?

现在随便一个项目都是多层的,尤其是 Web 项目,经常需要在多层之间做对象模型转换,比如 DTO 转换成 BO。

DTO(Data Transfer Object):数据传输对象,Service 向外传输的对象。
BO(Business Object):业务对象,由 Service 层输出的封装业务逻辑的对象。

但是这种转换工作就像是小时候,老师罚我们抄写名人名言 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 这套东西,它每次都要针对字段,做是否可读写的检查,还要根据字段生成对应的 PropertyDescriptor。

这些严重影响了它的性能,所以,在阿里 Java 手册里,也不推荐用它。

Spring 的 BeanUtils,虽然精简了很多 Apache 的 BeanUtils 的读写检查以及对应的属性信息记录,但是它依然是通过反射调用,而且是大量反射调用。这种性能也不能令人满意。

2.运行期做转换,出错就代表损失

BeanUtils 这类工具,有个统一的名称,叫做 Java 对象映射框架。

它们大部分的实现都是在运行期去执行代码,然后在 Java 对象之间去拷贝对应的值。

运行期间做这种事儿,有个最大的问题——整个项目启动运行后,才能发现错误。比如,转换的时候,类型不一致导致报错。

对于此种情况,咱们大家都知道,这事儿就像开业酬宾没搞好,变成了开业仇宾……

如果能写完代码,编译的时候就发现问题,这种损失就可以避免了。

MapStruct 的引入就是为了解决以上这两个问题。

MapStruct 首先是个代码产生器,它是根据注解,去产生一个专门用来转换的工具类,这个工具类,就像我们自己写的 Java 类一样,可以直接被使用,这样就避免了反射。

同时,它产生的转换类也特别简单,就是默认会在两个类型的 Java 对象之间,拷贝同名属性的值。

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

示例代码如下:

@Mapper
public interface CarMapper {

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

    @Mapping(target = "seatCount", source = "numberOfSeats")
    CarDto carBoToCarDto(Car car);
}

MapStruct由于是个代码产生器,就带来了个巨大的好处,就是这家伙是在编译阶段就会生成对应的类,所以,如果有了类似类型转换不过去的问题,直接就编译报错了,根本等不到运行才发现。这样的话,就不会造成什么损失,这真是件十分 Nice 的事情。

代码库地址

https://github.com/mapstruct/mapstruct

2. Retrofit

71d136345762b90e64c09e3601e78a5a.png

Retrofit 是干什么的?

Retrofit 就是一套 Http 客户端,可以用来访问第三方的 Http 服务。

比如,咱们代码里想调用一个 Http 协议的 URL,就可以用它来访问这个 URL,获取响应结果。

为什么在项目里用它?

在公司里,我们有些项目有如下的特点:

  1. 不是基于 Spring 的项目

  2. 需要经常访问大量的第三方 Http 服务

  3. 访问 Http 服务的模型通常是异步回调

以前的时候,我们访问 Http 服务,都是直接用的 HttpClient。

可是吧,HttpClient 用起来实在够麻烦的。主要也存在两个问题:

1.请求参数和 URL 拼接实在繁琐

请求参数和 URL 拼接实在是太烦人了。你想想,每调用一个接口,就需要自己去拼接参数,有的 URL,甚至十几二十个参数需要拼接。

拼接这事儿简单、枯燥、重复,还没有技术含量,但是工作量却不小,时间真的算浪费了。

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.异步回调需要自己搞

异步回调这种模型不好处理,主要就是需要自己去搞线程池,还要对线程池管理,还要考虑出错的重试之类的容错问题,实在麻烦。

所以,我们就需要一套能用法简单,不用我们一直搞拼接参数,自己搞线程管理就能完成对第三方 Http 服务访问的库。

其实我们也想过用 Feign 这套框架的。但是,这套东西和 Spring 绑定的太紧了。如果离开 Spring,它的一些功能就没法简单的通过注解直接使用,必须自己写代码调用。

而且,Feign 要实现异步回调方式使用,尤其在协程方面,还是需要自己开发。

这时候,Retrofit 就跳进了我们的选型里。

Retrofit 的模型里,异步回调模型它支持的很好,我们只需要实现一个 Callable 就够了。

并且最清爽的是,它和 Spring 没什么关系。

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

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

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

Call<ResponseBody> call = service.getBlog(2);
// 用法和OkHttp的call如出一辙,
// 回调
call.enqueue(new Callback<ResponseBody>() {
    @Override
    public void onResponse(Call<ResponseBody> call, Response<ResponseBody> response) {
        try {
            System.out.println(response.body().string());
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onFailure(Call<ResponseBody> call, Throwable t) {
        t.printStackTrace();
    }
});

你看,只需要写上这些代码,我们就不需要操心恼人的 Url 拼接和异步回调的管理问题了。全交给了 Retrofit,着实推荐。

代码库地址

https://github.com/square/retrofit

3. Faker

1853ce1612c9263605d373d9e3a3d78c.png

Faker 是干什么的?

Faker 是专门用来产生各种假数据的辅助工具库。

比如,你想产生个和真实数据一样的有姓名、有地址的用户。

为什么在项目里用它?

我们经常需要造数据去测试,但是,如果没有工具辅助,我们自己造数据,存在一些问题。

1.数据是需要格式的

很多关于项目,都需要一些格式上尽量能模仿真实世界的数据。

比如,国内用户的姓名,大部分都是两字、三字的姓名,叫王大,就不能叫 王da 这种。

又比如,国内的地址是 xx市xx区xx街道xx号 这种的,就不能胡写一个几个没意义的汉字来当地址。

用贴近真实格式的数据,一来可以测出我们对用户的数据解析是否存在问题,二来可以测出数据库内的字段长度是否没问题。

所以,格式对产生出可靠地测试结果,是很重要的。

2.数据的量大

有的测试数据量都是上十万、百万的,这些量级的数据并不是只会产生一次。

甚至几乎每个项目,每个项目的每次测试,可能都会需要新的数据,需要能源源不断地产生出来。

更甚至的是,有时候还想要根据我们的要求,在恰当的时候,产生某种关系的数据,或者以某些特定频率产生。比如,两秒后产生一次数据;比如,产生一批姓王的数据。

以上这三种要求综合起来,要是我们自己造数据,那真是要了命了。

与其自己开发,不如用现成的——Faker 库被我们找到了。

Faker库可以创造三百多种数据,而且还很容易对它进行扩展改造,去产生更多的贴合我们需求的数据。

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

09572a2f3c531079bfd4b91f80fbcc8d.png

Wiremock 是干什么的?

Wiremock 是一个可以模拟服务的测试框架。

比如,你想测试访问阿里的支付相关接口的代码逻辑,就可以用它来做测试。

为什么在项目里用它?

比如,我们需要调用银行接口去做资金业务,调用微信接口去做微信登录……这些调用第三方服务的测试存在一个问题:

即太过依赖对方的平台。假如对方平台限制了一些 IP,或者限制了访问频率,又或者就是服务出现了维护,都会影响我们自身的功能测试。

为了解决上述问题,在之前,我们需要自己写代码模仿第三方的接口,等我们自己全部测试没问题了,再去和第三方联调。对于这种模拟出来的接口,我们称作挡板。

可是,这种方式是个苦活,没人愿意干。因为每接入一个第三方,可能都需要做挡板。辛苦做个挡板,就是单纯为了测试。如果第三方的接口做了改造,你这边还得跟着改。

大家可以想想,换成你自己,你愿意做这么件事儿吗?

这时候,Wiremock 的价值就体现出来了。有了 Wiremock,挡板这种东西就再也不存在了,直接在单元测试里模拟测试即可,像这样:

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

结语

虽然 Java 有很多遭人诟病的地方,但是 Java 最重要的优点之一,就是它的生态,有其琳琅满目的各种工具类库。

希望大家都“懒”一点,不要埋头去做无效的苦干,不要自己造轮子,你要相信:

你遇到的问题,基本已经有很多人遇到过了,而且已经被牛人给解决了,把轮子都给你造好了。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Spring4GWT GWT Spring 使得在 Spring 框架下构造 GWT 应用变得很简单,提供一个易于理解的依赖注入和RPC机制。 Java扫雷游戏 JVMine JVMine用Applets开发的扫雷游戏,可在线玩。 public class JVMine extends java.applet.Applet 简单实现!~ 网页表格组件 GWT Advanced Table GWT Advanced Table 是一个基于 GWT 框架的网页表格组件,可实现分页数据显示、数据排序和过滤等功能! Google Tag Library 该标记库和 Google 有关。使用该标记库,利用 Google 为你的网站提供网站查询,并且可以直接在你的网页里面显示搜查的结果。 github-java-api github-java-api 是 Github 网站 API 的 Java 语言版本。 java缓存工具 SimpleCache SimpleCache 是一个简单易用的java缓存工具,用来简化缓存代码的编写,让你摆脱单调乏味的重复工作!1. 完全透明的缓存支持,对业务代码零侵入 2. 支持使用Redis和Memcached作为后端缓存。3. 支持缓存数据分区规则的定义 4. 使用redis作缓存时,支持list类型的高级数据结构,更适合论坛帖子列表这种类型的数据 5. 支持混合使用redis缓存和memcached缓存。可以将列表数据缓存到redis中,其他kv结构数据继续缓存到memcached 6. 支持redis的主从集群,可以做读写分离。缓存读取自redis的slave节点,写入到redis的master节点。 Java对象的SQL接口 JoSQL JoSQL(SQLforJavaObjects)为Java开发者提供运用SQL语句来操作Java对象集的能力.利用JoSQL可以像操作数据库中的数据一样对任何Java对象集进行查询,排序,分组。 搜索自动提示 Autotips AutoTips是为解决应用系统对于【自动提示】的需要(如:Google搜索), 而开发的架构无关的公共控件, 以满足该类需求可以通过快速配置来开发。AutoTips基于搜索引擎Apache Lucene实现。AutoTips提供统一UI。 WAP浏览器 j2wap j2wap 是一个基于Java的WAP浏览器,目前处于BETA测试阶段。它支持WAP 1.2规范,除了WTLS 和WBMP。 Java注册表操作类 jared jared是一个用来操作Windows注册表的 Java 类库,你可以用来对注册表信息进行读写。 GIF动画制作工具 GiftedMotion GiftedMotion是一个很小的,免费而且易于使用图像互换格式动画是能够设计一个有趣的动画了一系列的数字图像。使用简便和直截了当,用户只需要加载的图片和调整帧您想要的,如位置,时间显示和处理方法前帧。 Java的PList类库 Blister Blister是一个用于操作苹果二进制PList文件格式的Java开源类库(可用于发送数据给iOS应用程序)。 重复文件检查工具 FindDup.tar FindDup 是一个简单易用的工具,用来检查计算机上重复的文件。 OpenID的Java客户端 JOpenID JOpenID是一个轻量级的OpenID 2.0 Java客户端,仅50KB+(含源代码),允许任何Web网站通过OpenID支持用户直接登录而无需注册,例如Google Account或Yahoo Account。 JActor的文件持久化组件 JFile JFile 是 JActor 的文件持久化组件,以及一个高吞吐量的可靠事务日志组件。 Google地图JSP标签库 利用Google:maps JSP标签库就能够在你的Web站点上实现GoogleMaps的所有功能而且不需要javascript或AJAX编程。它还能够与JSTL相结合生成数据库驱动的动态Maps。 OAuth 实现框架 Agorava Agorava 是一个实现了 OAuth 1.0a 和 OAuth 2.0 的框架,提供了简单的方式通过社交媒体进行身份认证的功能。 Eclipse的JavaScript插件 JSEditor JSEditor 是 Eclipse 下编辑 JavaScript 源码的插件,提供语法高亮以及一些通用的面向对象方法。 Java数据库连接池 BoneCP BoneCP 是一个高性能的开源java数据库连接池实现库。它的设计初衷就是为了提高数据库连接池的性能,根据某些测试数据发现,BoneCP是最快的连接池。BoneCP很小,只有四十几K

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值