Okhttp的连接池ConnectionPool(三)

目录

1.get()方法

2.put()


Okhttp3使用及解析:https://mp.csdn.net/postedit/83339916

okhttp系统拦截器:https://mp.csdn.net/postedit/83536609

Okhttp的连接池ConnectionPool:https://mp.csdn.net/postedit/83650740

 

Okhttp将客户端和服务端之间通信的链接抽象成Connection类,而ConnectionPool就是管理这些链接的复用而出现的,作用就是在一定时间内可以复用Connection。

下面分析源码:

1.get()方法

  @Nullable 
RealConnection get(Address address, StreamAllocation streamAllocation, Route route) {
    assert (Thread.holdsLock(this));
    //遍历连接池connections
    for (RealConnection connection : connections) {
        //isEligible判断是否可用
      if (connection.isEligible(address, route)) {
        //acquire获取连接池
        streamAllocation.acquire(connection, true);
        return connection;
      }
    }
    return null;
  }

看看acquire():

 public void acquire(RealConnection connection, boolean reportedAcquired) {
    assert (Thread.holdsLock(connectionPool));
    if (this.connection != null) throw new IllegalStateException();
    //将连接池中获取的RealConnection赋值
    this.connection = connection;
    this.reportedAcquired = reportedAcquired;
    //将弱引用的StreamAllocation存入集合allocations
    connection.allocations.add(new StreamAllocationReference(this, callStackTrace));
  }

 集合allocations存储的多个StreamAllocation,方便后期通过size大小的判断一个网络链接的负载量是否超过最大值。

总结:每次的http请求会在重定向拦截器中创建StreamAllocation,且StreamAllocation的弱引用会被添加至泛型为RealConnection的集合中,后面可通过集合大小判断链接是否超过负载。同时,也提供在一定时间内连接池复用链接。

2.put()

void put(RealConnection connection) {
    assert (Thread.holdsLock(this));
    //线程池异步回收connection
    if (!cleanupRunning) {
      cleanupRunning = true;
      executor.execute(cleanupRunnable);
    }
    //connection存入队列
    connections.add(connection);
  }

题外话:看看cleanupRunnable回收的流程:

private final Runnable cleanupRunnable = new Runnable() {
    @Override public void run() {
      while (true) {
        //计算下一次清理的时间 
        //gc的标记算法,存StreamAllocation弱引用的集合,遍历发现为空,则remove
        long waitNanos = cleanup(System.nanoTime());
        if (waitNanos == -1) return;
        if (waitNanos > 0) {
          long waitMillis = waitNanos / 1000000L;
          waitNanos -= (waitMillis * 1000000L);
          synchronized (ConnectionPool.this) {
            try {
                //等待时间,去执行下次清理
              ConnectionPool.this.wait(waitMillis, (int) waitNanos);
            } catch (InterruptedException ignored) {
            }}}}}};

 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Spring Boot中使用OkHttp连接池可以通过配置`HttpClient` bean来实现。以下是一个示例: ```java import okhttp3.ConnectionPool; import okhttp3.OkHttpClient; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import java.util.concurrent.TimeUnit; @Configuration public class OkHttpConfig { @Bean public OkHttpClient okHttpClient() { int maxIdleConnections = 100; // 最大空闲连接数 long keepAliveDuration = 5; // 连接存活时间(分钟) ConnectionPool connectionPool = new ConnectionPool(maxIdleConnections, keepAliveDuration, TimeUnit.MINUTES); return new OkHttpClient.Builder() .connectionPool(connectionPool) .build(); } } ``` 在上述示例中,我们创建了一个`OkHttpClient`的bean,并通过`ConnectionPool`设置了最大空闲连接数和连接存活时间。你可以根据自己的需求进行调整。 然后,在需要使用OkHttp的地方,你可以通过注入`OkHttpClient`来使用连接池: ```java import okhttp3.OkHttpClient; import okhttp3.Request; import okhttp3.Response; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import java.io.IOException; @Service public class MyService { @Autowired private OkHttpClient okHttpClient; public String makeRequest() throws IOException { Request request = new Request.Builder() .url("https://example.com") .build(); try (Response response = okHttpClient.newCall(request).execute()) { return response.body().string(); } } } ``` 在上述示例中,我们通过`@Autowired`注解将`OkHttpClient`注入到`MyService`中,并在`makeRequest()`方法中使用连接池发送请求。 这样,你就可以在Spring Boot中使用OkHttp连接池了。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值