Duang!Duang!Duang!直击痛点的一款 HTTP 客户端框架(Java),墙裂推荐!(1)-阿里云开发者社区

开发者社区> 沉默王二> 正文

Duang!Duang!Duang!直击痛点的一款 HTTP 客户端框架(Java),墙裂推荐!(1)

简介: Duang!Duang!Duang!直击痛点的一款 HTTP 客户端框架(Java),墙裂推荐!
+关注继续查看

大家好,我是二哥呀!


今天来给大家推荐一款直击痛点的 HTTP 客户端框架,可以超高效率地完成和第三方接口的对接。


在介绍本篇的主角之前,我们先来了解下 Java 生态中的 HTTP 组件库,大致可以分为三类:


JDK 自带的 HttpURLConnection 标准库;

Apache HttpComponents HttpClient;

OkHttp。

使用 HttpURLConnection 发起 HTTP 请求最大的优点是不需要引入额外的依赖,但是使用起来非常繁琐,也缺乏连接池管理、域名机械控制等特性支持。


使用标准库的最大好处就是不需要引入额外的依赖,但使用起来比较繁琐,就像直接使用 JDBC 连接数据库那样,需要很多模板代码。来发起一个简单的 HTTP POST 请求吧。


public class HttpUrlConnectionDemo {
    public static void main(String[] args) throws IOException {
        String urlString = "https://httpbin.org/post";
        String bodyString = "password=123";
        URL url = new URL(urlString);
        HttpURLConnection conn = (HttpURLConnection) url.openConnection();
        conn.setRequestMethod("POST");
        conn.setDoOutput(true);
        OutputStream os = conn.getOutputStream();
        os.write(bodyString.getBytes("utf-8"));
        os.flush();
        os.close();
        if (conn.getResponseCode() == HttpURLConnection.HTTP_OK) {
            InputStream is = conn.getInputStream();
            BufferedReader reader = new BufferedReader(new InputStreamReader(is));
            StringBuilder sb = new StringBuilder();
            String line;
            while ((line = reader.readLine()) != null) {
                sb.append(line);
            }
            System.out.println("响应内容:" + sb.toString());
        } else {
            System.out.println("响应码:" + conn.getResponseCode());
        }
    }
}


HttpURLConnection 发起的 HTTP 请求比较原始,基本上算是对网络传输层的一次浅层次的封装;有了 HttpURLConnection 对象后,就可以获取到输出流,然后把要发送的内容发送出去;再通过输入流读取到服务器端响应的内容;最后打印。


不过 HttpURLConnection 不支持 HTTP/2.0,为了解决这个问题,Java 9 的时候官方的标准库增加了一个更高级别的 HttpClient,再发起 POST 请求就显得高大上多了,不仅支持异步,还支持顺滑的链式调用。


public class HttpClientDemo {
    public static void main(String[] args) throws URISyntaxException {
        HttpClient client = HttpClient.newHttpClient();
        HttpRequest request = HttpRequest.newBuilder()
                .uri(new URI("https://postman-echo.com/post"))
                .headers("Content-Type", "text/plain;charset=UTF-8")
                .POST(HttpRequest.BodyPublishers.ofString("二哥牛逼"))
                .build();
        client.sendAsync(request, HttpResponse.BodyHandlers.ofString())
                .thenApply(HttpResponse::body)
                .thenAccept(System.out::println)
                .join();
    }
}



Apache HttpComponents HttpClient 支持的特性也非常丰富:


基于标准、纯净的Java语言,实现了HTTP1.0和HTTP1.1;

以可扩展的面向对象的结构实现了HTTP全部的方法;

支持加密的HTTPS协议(HTTP通过SSL协议);

Request的输出流可以避免流中内容体直接从socket缓冲到服务器;

Response的输入流可以有效的从socket服务器直接读取相应内容。

public class HttpComponentsDemo {
    public static void main(String[] args) throws IOException, IOException, ParseException {
        try (CloseableHttpClient httpclient = HttpClients.createDefault()) {
            HttpPost httpPost = new HttpPost("http://httpbin.org/post");
            List<NameValuePair> nvps = new ArrayList<>();
            nvps.add(new BasicNameValuePair("name", "二哥"));
            httpPost.setEntity(new UrlEncodedFormEntity(nvps, Charset.forName("UTF-8")));
            try (CloseableHttpResponse response2 = httpclient.execute(httpPost)) {
                System.out.println(response2.getCode() + " " + EntityUtils.toString(response2.getEntity()));
            }
        }
    }
}


OkHttp 是一个执行效率比较高的 HTTP 客户端:


支持 HTTP/2.0,当多个请求对应同一个 Host 地址时,可共用同一个 Socket;

连接池可减少请求延迟;

支持 GZIP 压缩,减少网络传输的数据大小;

支持 Response 数据缓存,避免重复网络请求;

public class OkHttpPostDemo {
    public static final MediaType JSON = MediaType.get("application/json; charset=utf-8");
    OkHttpClient client = new OkHttpClient();
    String post(String url, String json) throws IOException {
        RequestBody body = RequestBody.create(json, JSON);
        Request request = new Request.Builder()
                .url(url)
                .post(body)
                .build();
        try (Response response = client.newCall(request).execute()) {
            return response.body().string();
        }
    }
    public static void main(String[] args) throws IOException {
        OkHttpPostDemo example = new OkHttpPostDemo();
        String json = "{'name':'二哥'}";
        String response = example.post("https://httpbin.org/post", json);
        System.out.println(response);
    }
}



那今天介绍的这款轻量级的 HTTP 客户端框架 Forest,正是基于 Httpclient和OkHttp 的,屏蔽了不同细节的 HTTP 组件库所带来的所有差异。


Forest 的字面意思是森林的意思,更内涵点的话,可以拆成For和Rest两个单词,也就是“为了Rest”(Rest为一种基于HTTP的架构风格)。 而合起来就是森林,森林由很多树木花草组成(可以理解为各种不同的服务),它们表面上看独立,实则在地下根茎交错纵横、相互连接依存,这样看就有点现代分布式服务化的味道了。 最后,这两个单词反过来读就像是Resultful。


项目地址:


https://gitee.com/dromara/forest

虽然 star 数还不是很多,但 star 趋势图正在趋于爬坡阶段,大家可以拿来作为一个练手项目,我觉得还是不错的选择。


image.png


Forest 本身是处理前端过程的框架,是对后端 HTTP API 框架的进一步封装。

image.png

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
高校学生在家实践ECS弹性云服务器
简单谈谈我这几周使用ECS弹性云服务器的体验感
8 0
ECS使用感受
阿里云服务器初体验
4 0
ECS初体验
esc简单的初体验
4 0
微服务架构 | *2.3 Spring Cloud 启动及加载配置文件源码分析(以 Nacos 为例)
Spring Cloud 要实现统一配置管理,需要解决两个问题:如何获取远程服务器配置和如何动态更新配置;在这之前,我们先要知道 Spring Cloud 什么时候给我们加载配置文件;
5 0
ECS使用有感
我是一名即将步入社会的大学生,随着网络法等相关专业知识的学习愈发强烈。查询资料时,常常会浏览到制作精美的个人站,因此产生了建设自己个人站的设想,但是由于业余时间少之甚少,同时听闻购买域名与服务器的价格不菲,因此计划一直未能实现
4 0
对于操作系统而言进程、线程以及Goroutine协程的区别
进程、线程、协程实际上都是为并发而生。但是他们的各自的模样是完全不一致的,下面我们来分析一下他们各自的特点和关系。本文不重点介绍什么是进程和线程,而是提炼进程、线程、协程干货。且是基于Linux下的进程、线程解释。
4 0
微服务架构 | *2.4 Nacos 获取配置与事件订阅机制的源码分析
为方便理解与表达,这里把 Nacos 控制台和 Nacos 注册中心称为 Nacos 服务器(就是 web 界面那个),我们编写的业务服务称为 Nacso 客户端; 由于篇幅有限,这里将源码分析分为上下两篇,其中上篇讲获取配置与事件订阅机制,下篇讲长轮询定时机制;
4 0
轻松实现织梦网站数据迁移到新站点
众所周知,织梦已经开始收费了,这对国内版权意识增强应该不算坏事,但想要免费使用又不想惹麻烦的站长们就有点麻烦了。
3 0
冬季实战营第一期学习报告
1月17至22日,我有幸参加了阿里云组织的“冬季实战营第一期:从零到一上手玩转云服务器”抱着期待和学习的心情,我参与其中,经过训练,收益良多、颇有收获
16 0
+关注
沉默王二
微信搜索「沉默王二」,回复关键字「00」获取硬核计算机基础资料。
1084
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
《2021云上架构与运维峰会演讲合集》
立即下载
《零基础CSS入门教程》
立即下载
《零基础HTML入门教程》
立即下载