编程开源技术交流,分享技术与知识

网站首页 > 开源技术 正文

OKHttp高级用法,看这一篇就够了

wxchong 2024-06-10 17:02:30 开源技术 12 ℃ 0 评论

在现代应用中,实现并发通信是提高性能的关键。OKHttp 是一个强大的 Java 库,可以轻松地实现多个地址的并发调用。本教程将以简洁明了的语言,带您深入了解如何利用 OKHttp 实现并发通信,从基本的并发执行到调度器的灵活使用,助您构建出高效的多线程网络通信策略。让我们一起探索这个并发之旅吧!

直接上干货,拿走用不谢

package com.abclass.utils;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import okhttp3.*;
import org.jetbrains.annotations.NotNull;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.*;

/**
 * @author AbClass
 * @version 1.0.0
 * @since 1.0.0
 */
public class RequestBuilder {
    private OkHttpClient client;
    private List<Request> requests;
    private int maxRetries;

    public RequestBuilder() {
        client = new OkHttpClient();
        requests = new ArrayList<>();
        maxRetries = 3;
    }

    public RequestBuilder client(OkHttpClient client) {
        this.client = client;
        return this;
    }

    public RequestBuilder addRequest(Request request) {
        requests.add(request);
        return this;
    }

    public RequestBuilder maxRetries(int maxRetries) {
        this.maxRetries = maxRetries;
        return this;
    }

    @NotNull
    public Request gen(String url, String tag, String input) {
        JSONObject req = new JSONObject();
        JSONArray jsonArray = new JSONArray();
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("role", "system");
        jsonObject.put("content", input);
        jsonArray.add(jsonObject);
        req.put("messages", jsonArray);
        String json = req.toJSONString();
        MediaType JSON = MediaType.parse("application/json; charset=utf-8");

        RequestBody body = RequestBody.create(JSON, json);
        Request request = new Request.Builder()
                .url(url)
                .post(body)
                .tag(tag)
                .build();

        return request;
    }

    private void printlog(String tag, String input, JSONObject response) {
        try {
            System.out.println("tag=" + tag + " inputText:" + "\n "
                    + input +
                    "\n" + "response:" + "\n"
                    + response.getJSONObject("response"));
        } catch (Exception e) {
            //log error
        }
    }

    public Map<String, JSONObject> execute() {
        Map<String, JSONObject> responses = new HashMap<>();
        ExecutorService executorService = Executors.newFixedThreadPool(requests.size());
        List<Future<String>> futures = new ArrayList<>();

        for (Request request : requests) {
            final int[] retryCount = {0};

            Callable<String> task = () -> {
                String response = null;
                boolean shouldRetry = true;

                while (shouldRetry && retryCount[0] <= maxRetries) {
                    try (Response httpResponse = client.newCall(request).execute()) {
                        response = httpResponse.body().string();
                        shouldRetry = false;
                    } catch (IOException e) {
                        e.printStackTrace();
                        retryCount[0]++;
                    }

                    if (shouldRetry) {
                        System.out.println("Retry " + retryCount[0] + " for " + request.tag());
                        Thread.sleep(1000);
                    }
                }

                return response != null ? response : "";
            };

            futures.add(executorService.submit(task));
        }

        for (int i = 0; i < futures.size(); i++) {
            final int index = i;
            Future<String> future = futures.get(index);
            String tag = requests.get(index).tag().toString();
            String input = requests.get(index).body().toString();
            JSONObject defaultObj = new JSONObject();
            defaultObj.put("content", "");
            try {
                String response = future.get();
                if (response == null || "".equals(response)) {
                    System.out.println("Timeout for " + tag);
                    responses.put(tag, defaultObj);
                    continue;
                }

                JSONObject jsonObject = JSONObject.parseObject(response);
                printlog(tag, input, jsonObject);
                responses.put(tag, jsonObject.getJSONObject("response"));
            } catch (InterruptedException | ExecutionException e) {
                e.printStackTrace();
                responses.put(tag, defaultObj);
            }
        }

        executorService.shutdown();
        return responses;
    }


    public static void main(String[] args) {
        RequestBuilder builder = new RequestBuilder();
        Map<String, JSONObject> responses = builder
                .client(new OkHttpClient())
                .addRequest(builder.gen("http://", "", ""))
                .addRequest(builder.gen("http://", "", ""))
                .addRequest(builder.gen("http://", "", ""))
                .maxRetries(5)
                .execute();
    }

}

解读一下这个代码

  • 核心方法execute,多线程并发访问,结果汇总
  • RequestBuilder用于构造请求内容,使用起来非常简洁
RequestBuilder builder = new RequestBuilder();
        Map<String, JSONObject> responses = builder
                .client(new OkHttpClient())
                .addRequest(builder.gen("http://", "tag1", "内容"))//多个地址,每个请求设置一个标签
                .addRequest(builder.gen("http://", "tag2", "内容"))
                .addRequest(builder.gen("http://", "tag3", "内容"))
                .maxRetries(5)//异常重试次数
                .execute();

通过本教程的学习,您已经深入了解了 OKHttp 在并发通信中的应用和优化技巧。从并发执行到任务调度,再到性能优化和监控,您已经为自己的 Java 应用构建了高效可靠的多线程网络通信方案。将这些知识应用到实际项目中,创造出高性能的并发通信策略

Tags:

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表