How to implement connection pool in spark

https://github.com/YulinGUO/BigDataTips/blob/master/spark/How%20to%20implement%20connection%20pool%20in%20Spark.md

问题所在

Spark Streaming Guid中,提到:

dstream.foreachRDD { rdd =>
rdd.foreachPartition { partitionOfRecords =>
// ConnectionPool is a static, lazily initialized pool of connections
val connection = ConnectionPool.getConnection()
partitionOfRecords.foreach(record => connection.send(record))
ConnectionPool.returnConnection(connection) // return to the pool for future reuse
}}

可是如何具体实现呢?

Scala + Mongodb实现连接池

一个通常意义上的连接池,能够请求获取资源,也能释放资源。不过MongoDB java driver已经帮我们实现了这一套逻辑。

Note: The Mongo object instance actually represents a pool of connections to the database; you will only need one object of class Mongo even with multiple threads. See the concurrency doc page for more information.

The Mongo class is designed to be thread safe and shared among threads. Typically you create only 1 instance for a given DB cluster and use it across your app. If for some reason you decide to create many mongo intances, note that:

all resource usage limits (max connections, etc) apply per mongo instance to dispose of an instance, make sure you call mongo.close() to clean up resources

也就是说,我们的pool,只要能获得Mongo就可以了。也就是说每次请求,在executor端,能get已经创建好了MongoClient就可以了。

object MongoPool {

  var  instances = Map[String, MongoClient]()

  //node1:port1,node2:port2 -> node
def nodes2ServerList(nodes : String):java.util.List[ServerAddress] = {
val serverList = new java.util.ArrayList[ServerAddress]()
nodes.split(",")
.map(portNode => portNode.split(":"))
.flatMap{ar =>{
if (ar.length==2){
Some(ar(0),ar(1).toInt)
}else{
None
}
}}
.foreach{case (node,port) => serverList.add(new ServerAddress(node, port))} serverList
} def apply(nodes : String) : MongoClient = {
instances.getOrElse(nodes,{
val servers = nodes2ServerList(nodes)
val client = new MongoClient(servers)
instances += nodes -> client
println("new client added")
client
})
}
}

这样,一个static 的MongoPool的Object已经创建,scala Ojbect类,在每个JVM中会初始化一次。

rdd.foreachPartition(partitionOfRecords => {

   val nodes = "node:port,node2:port2"
lazy val client = MongoPool(nodes)
lazy val coll2 = client.getDatabase("dm").getCollection("profiletags") partitionOfRecords.grouped(500).foreach()
})

注意,此处client用lazy修饰,等到executor使用client的时候,才会执行。否则的话,会出现client not serializable.

优点分析

1.不重复创建,销毁跟数据库的连接,效率高。 Spark 每个executor 申请一个JVM进程,task是多线程模型,运行在executor当中。task==partition数目。Object只在每个JVM初始化一次。
2.代码design pattern

参考资料

Spark Streaming Guid

在Spark中通过Scala + Mongodb实现连接池的更多相关文章

  1. java操作mongodb(连接池)(转)

    原文链接: java操作mongodb(连接池) Mongo的实例其实就是一个数据库连接池,这个连接池里默认有10个链接.我们没有必要重新实现这个链接池,但是我们可以更改这个连接池的配置.因为Mong ...

  2. 如何在 Swoole 中优雅的实现 MySQL 连接池

    如何在 Swoole 中优雅的实现 MySQL 连接池 一.为什么需要连接池 ? 数据库连接池指的是程序和数据库之间保持一定数量的连接不断开, 并且各个请求的连接可以相互复用, 减少重复连接数据库带来 ...

  3. 【转】SSH中 整合spring和proxool 连接池

    [摘要:比来做的一个项目中应用到了毗邻池技巧,大概我们人人比拟认识的开源毗邻池有dbcp,c3p0,proxool.对那三种毗邻池来讲,从机能战失足率来讲,proxool轻微比前两种好些.本日我首要简 ...

  4. MongoDB设置连接池操作百万级以上数据

    开发环境 spring 4.3.7 + springBoot 1.5.2 + dubbo 2.6.5 + mongoDB 4.0.0 连接池配置 mongo-pool.properties sprin ...

  5. Golang 连接 MongoDB使用连接池

    可以免费试用 MongoDB ,500MB 平时做测试没有问题啦,连接数据库可能因为网络有点慢,但是我们是测试啊,不在乎这点吧~ 这是怎么申请试用版的博客,感谢这位大佬.注册好用起来很方便~ 传送门 ...

  6. SSH框架中配置Hibernate使用proxool连接池

    一.导入proxool.jar包 案例用的是proxool-0.8.3.jar,一般通过MyEclipse配置的SSH都会包含这个jar,如果没有,就去网上搜下下载导入就好了. 二.新建Proxool ...

  7. 使用MongoDB 2.6 C++驱动中的连接池

    .post p{text-indent: 2em;} MongoDB2.6的CXX驱动(mongo-cxx-driver-26compat),内置包含了数据库连接池,方便管理数据库连接,但是官方文档说 ...

  8. Spring框架中 配置c3p0连接池 完成对数据库的访问

    开发准备: 1.导入jar包: ioc基本jar jdbcTemplate基本jar c3p0基本jar 别忘了mysql数据库驱动jar 原始程序代码:不使用配置文件方式(IOC)生成访问数据库对象 ...

  9. 在Tomcat中配置连接池和数据源

    1.DataSource接口介绍 (1)DataSource 概述 JDBC1.0原来是用DriverManager类来产生一个对数据源的连接.JDBC2.0用一种替代的方法,使用DataSource ...

随机推荐

  1. 建立与读取.ini文件

    一般读写ini文件被读写Registry所取代,但我们还是可以透过 win31的传统方式读写ini文件,以存程式目前的相关设定,而於下一次程式执行时再 读回来.目前建议使用GetSetting Sav ...

  2. cmd获取批处理文件所在路径

    在批处理开头加入cd /d %~dp0 一行代码就真真实实地做到“编写一次,到处运行”.%0是批处理文件本身的路径,%~dp进行扩展, d向前扩展到驱动器,p往后扩展到路径.例如,你的bat文件在e: ...

  3. java上传excel文件及解析

      java上传excel文件及解析 CreateTime--2018年3月5日16:25:14 Author:Marydon 一.准备工作 1.1 文件上传插件:swfupload: 1.2 文件上 ...

  4. Eureka集群试验的一点总结

    先简单描述一下试验: 试验在一台机器上进行,假设有host文件中配置了以下内容 127.0.0.1 left 127.0.0.1 center 127.0.0.1 right 试验中搭建三个注册中心实 ...

  5. Linux 系统使用 iso 镜像文件或光盘配置本地YUM 源的最简单方式

    1.分配光驱 选择本地的iso系统镜像文件,或者在光驱中放入系统安装盘.之后,在桌面可以看到RHEL-7.2-Server的光盘图标. 2.查看光驱挂载的位置 使用df -h 命令可以看到光驱或镜像文 ...

  6. bzoj1296【SCOI2009】粉刷匠

    1296: [SCOI2009]粉刷匠 Time Limit: 10 Sec  Memory Limit: 162 MB Submit: 1479  Solved: 837 [id=1296" ...

  7. 解决sitemesh3装饰页面不能使用freemarker标签问题

    如题,这个问题其实在sitemesh2中已经很好的解决了,不过在sitemesh3中可能没有解决,所以要自己写代码解决了,下面我先讲下sitemesh2是如何解决的: <servlet> ...

  8. 深入PHP内核之全局变量

    在阅读PHP源码的时候,会遇到很多诸如:CG(),EG() ,PG(),FG()这样的宏,如果不了解这些宏的意义,会给理解源码造成很大困难 EG().这个宏可以用来访问符号表,函数,资源信息和常量 C ...

  9. js removeChild

    removeChild():删除元素只能通过直接父元素删除,没有自删 1 <select id="city" size="6" style="w ...

  10. php Zend虚拟机

    在前⾯的章节中,我们了解到⼀个PHP⽂件在服务器端的执⾏过程包括以下两个⼤的过程:1. 递给php程序需要执⾏的⽂件, php程序完成基本的准备⼯作后启动PHP及Zend引擎, 加载注册的扩展模块.2 ...