scala:apache httpclient在多线程环境中

时间:2016-11-11 11:10:22

标签: multithreading scala spark-streaming apache-httpclient-4.x

我正在编写一个单例类(scala中的Object),它使用apache httpclient(4.5.2)发布一些文件内容并将状态返回给调用者。

object HttpUtils{
  protected val retryHandler = new HttpRequestRetryHandler() {
    def retryRequest(exception: IOException, executionCount: Int, context: HttpContext): Boolean = {
      //retry logic
      true
    }
  }
  private val connectionManager = new PoolingHttpClientConnectionManager()

  // Reusing same client for each request that might be coming from different threads . 
  // Is it correct ????
  val httpClient = HttpClients.custom()
    .setConnectionManager(connectionManager)
    .setRetryHandler(retryHandler)
    .build()

  def restApiCall (url : String, rDD: RDD[SomeMessage]) : Boolean = {
    // Creating new context for each request
    val httpContext: HttpClientContext = HttpClientContext.create
    val post = new HttpPost(url)

    // convert RDD to text file using rDD.collect

    // add this file as MultipartEntity to post

    var response = None: Option[CloseableHttpResponse] // Is it correct way of using it ?
    try {
      response = Some(httpClient.execute(post, httpContext))
      val responseCode = response.get.getStatusLine.getStatusCode
      EntityUtils.consume(response.get.getEntity) // Is it require ???
      if (responseCode == 200) true
      else false
    }
    finally {
      if (response.isDefined) response.get.close
      post.releaseConnection() // Is it require ???
    }
  }
  def onShutDown = {
    connectionManager.close()
    httpClient.close()
  }
}

多个线程(更具体地说,来自spark流式上下文)正在调用restApiCall方法。我对scalaapache httpClient相对较新。我必须频繁连接到少数固定服务器(即具有不同请求参数的5-6个固定URL)。

我浏览了多个在线资源,但对此仍然没有信心。

  • 这是在多线程环境中使用http客户端的最佳方式吗?
  • 是否可以保持实时连接并将其用于各种请求?在这种情况下会有益吗?
  • 我有效地使用/释放所有资源吗?如果没有,请建议。
  • 在Scala中使用它还是有更好的库吗?

提前致谢。

1 个答案:

答案 0 :(得分:0)

似乎official docs可以回答您的所有问题:

  

2.3.3。池化连接管理器

     

PoolingHttpClientConnectionManager是一个更复杂的实现   管理客户端连接池并且能够提供服务   来自多个执行线程的连接请求。连接是   按路线汇总。要求获得的路线   manager已经在池中提供了持久连接   通过租用池中的连接而不是创建来提供服务   一个全新的联系。

     

PoolingHttpClientConnectionManager保持最大限制   基于每条路线和总共的连接。默认为此   实现将创建不超过2个并发连接   给定路线,总共不再有20个连接。对于许多现实世界   应用这些限制可能会受到限制,特别是如果   他们使用HTTP作为其服务的传输协议。

  

2.4。多线程请求执行

     

配备池连接管理器时,如   PoolingClientConnectionManager,HttpClient可用于执行   多个请求同时使用多个执行线程。

     

PoolingClientConnectionManager将基于分配连接   它的配置。如果给定路由的所有连接已经存在   被租用,连接请求将阻止,直到连接   被释放回游泳池。可以确保连接管理器   不会在连接请求操作中无限期地阻塞   设置' http.conn-manager.timeout'达到正值。如果   在给定时间段内无法提供连接请求   将抛出ConnectionPoolTimeoutException。