http://guoyunsky.iteye.com/blog/759148
Solr有个很方便的处理器叫DataImportHandler,可以通过配置配置db-data-config.xml配置各种数据源然后
从中导入数据进行索引,很方便我们进行开发.但是之前从数据库导入数据一直有个问题,就是如果数据库中数据过大,就会导致内存溢出.自己经过阅读源码以及发邮件到Solr邮件列表,终于找到了解决办法,这里拿出来共享.
这里我的Solr版本是Solr1.4.0,数据库是Sql Server2005.其他数据库可能有些不适用(请在其他数据库运行成功的同学也分享下),但根据这个思路应该都有自己的解决方案.
DataImportHandler中从数据库导入数据进行索引主要通过JDBC进行处理.由于自己对JDBC的认识浅薄,一直认为JDBC是一次性将要查询的数据从数据库中数据读取过去.但没有想到其实从数据库获取数据其实也是以流的形式,可以一段段的获取.也就是可以在客户端每获取一条再从流中取新的一条数据如此取完为止(这里感谢高手提示).由于使用的数据库是Sql Server2005,本想通过它的sqljdbc.jar中获取些提示(尝试下源码没有成功),从Jar中大概发现Sql Server有这样的设置,于是上微软官网的MSDN获取到了答案(URL:http://msdn.microsoft.com/zh-cn/library/ms378663(SQL.90).aspx):
Sets the default cursor type that is used for all result sets that are created by using this SQLServerDataSource object.
复制
public void setSelectMethod(java.lang.String selectMethod)
参数
selectMethod
A String value that contains the default cursor type.
备注
The selectMethod is the default cursor type that is used for a result set. This property is useful when you are dealing with large result sets and do not want to store the whole result set in memory on the client side. By setting the property to "cursor," you can create a server-side cursor that can fetch smaller chunks of data at a time. If the selectMethod property is not set, getSelectMethod returns the default value of "direct".
同时这样做的话也要设置Connection的两个属性:ResultSet.TYPE_FORWARD_ONLY,ResultSet.CONCUR_READ_ONLY.但跟踪源码发现Solr中已经有这样的设置.于是可以直接在db-data-config.xml中配置即可完成,具体配置如下:
<dataSource name="dsSqlServer" type="JdbcDataSource" driver="com.microsoft.sqlserver.jdbc.SQLServerDriver" batchSize="3000" url="jdbc:sqlserver://192.168.1.5:1433; DatabaseName=testDatabase;responseBuffering=adaptive;selectMethod=cursor" user="sa" password="12345" />
其中只要在URL中加上responseBuffering=adaptive;selectMethod=cursor即可,无论多大的表根据这个配置Solr都可以从中读取数据并索引完成,当然,前提是不发生什么故障,如网络故障.这一想法也得到了Solr开发人员的验证,以下是他们给我回复的邮件:
That's not really true. DataImportHandler streams the result from database query and adding documents into index. So it shouldn't load all database data into memory. Disabling autoCommit, warming queries and spellcheckers usually decreases required amount of memory during
indexing process.Please share your hardware details, jvm options, solrconfig and schema configuration, etc.
但如此还是会造成一种隐患,就是如果表数据太大.如此会导致Solr一直在那获取数据并且索引.一旦发生什么故障如网络问题,Solr之前所做的索引就会前功尽弃,因为我们根本不知道它索引了多少条,索引到了哪里(后来看代码其实这种担忧是多余的,一旦发生网络异常,Solr会抛出异常,然后进行回滚,将索引恢复到索引之前的状态,也就是说之前做的一切根本
是白做,而Lucene写索引的速度又是相当慢,在如此长的时间内发生不可预见的问题绝对有可能).同时Solr要写完一次索引才会通知IndexSearcher让IndexReader去reopen,所以在那么长一段时间内所索引的数据你是无法搜索到.于是自己想通过ID(Solr里设置的<uniqueKey>)分批来处理.但这个ID是数字要更方便,比如设置个起点,和一次索引多少条.如起点为1,一次索引10000条。如此Solr会从1-10000,10001-20000,如此一直不停的索引下去.本想自己继承个DataImportHandler去处理,后来Solr开发者给我回复的邮件告诉我,Solr通过配置也完全可以实现,邮件内容具体如下:
You can _batch_ import your data using full import command by providing additional request parameter (see
http://wiki.apache.org/solr/DataImportHandler#Accessing_request_parameters), i.e.
query="SELECT * FROM my_table ORDER BY id LIMIT 1000000 OFFSET ${dataimporter.request.offset}"
and then calling full-import command several times:
1) /dataimport?clean=true&offset=0
2) /dataimport?clean=false&offset=1000000
3) /dataimport?clean=false&offset=2000000
etc
于是我在db-data-config.xml中用如下配置:
<entity name="TestEntity" dataSource="dsSqlServer" pk="Id" query="SELECT Id,Title,Author,Content,Url,AddOn FROM Test WHERE Id>=${dataimporter.request.offset} And Id<=${dataimporter.request.offset}+10000" >
同时运用
1) /dataimport?clean=true&offset=0
2) /dataimport?clean=false&offset=1000000
3) /dataimport?clean=false&offset=2000000
这些URL去请求SOlr进行索引.Solr会读取offset这个参数区建立query查询语句,然后去获取这些查询语句的数据去索引.但如此最好还是自己写个类做下控制.可以一开始获取表的总结果条数然后通过以上循环迭代完成.其中里面的+10000也可以设置为一个参数,如${dataimporter.request.intervalRows}表示一次获取多少条,然后在URL里加&intervalRows这个参数,具体我还还没试过.同时由于索引还是个长期的过程,所以这里最好记录好每次索引索引成功的间隔.比如在30000-40000索引成功的时候将他们记录日志.如此在索引40000-50000的时候一旦发生问题,我们可以通过日志获取上一次成功索引的间隔数,再从这个间隔去重新生成URL去索引数据.
以上希望起个抛砖引玉的作用,能对大家有所帮助,如果还有什么问题请留言。同时我这里处理的仅仅是SqlServer2005,其他数据库上操作成功的请分享下。同时如果你可以保证你间隔获取的数据如10000-20000这些数据不会导致内存溢出,那么你也可以不使用responseBuffering=adaptive;selectMethod=cursor这种配置.直接通过设置请求URL的offset来处理.
相关推荐
在本文中,我们将探讨如何使用SpringBoot集成EasyPoi库,实现从MySQL数据库中导出数据到Excel文件,以及从Excel文件中导入数据到MySQL数据库的功能。首先,我们需要理解EasyPoi是一个Java处理Excel的开源工具,它...
2. 数据丢失或溢出:当导入大量数据时,可能会遇到单元格超出列数限制的问题。这时可调整工作表的列宽,或者在导入前先将数据源的列合并。 3. 拼写错误或编码问题:非英文字符可能导致导入失败。检查文件编码是否为...
- 分页时应避免加载过多数据,尤其是在大数据量的情况下,这可能会导致内存溢出。合理设置每页记录数和优化数据库查询至关重要。 - 考虑缓存策略,例如使用Spring的`@Cacheable`注解,以减少对数据库的访问。 - ...
"SMART 200系列地址库:灵活配置的位读写系统",SMART 200 寻址-库 6个子 位:一个读,一个写 读:例如 读取从V0.0开始的第N个位的状态 写:例如 将值写入V0.0开始的第N个位中 起始地址和第几个位都可自定义 字节:读写一体,引脚控制读或写 字:读写一体,引脚控制读或写 双字:读写一体,引脚控制读或写 实数:读写一体,引脚控制读或写 ,核心关键词:SMART 200; 寻址-库; 子位; 读; 写; 起始地址; 自定义; 字节; 字; 双字; 实数。,"SMART 200库:位寻址与多读写功能"
1、文件内容:perl-ExtUtils-Manifest-1.61-244.el7.rpm以及相关依赖 2、文件形式:tar.gz压缩包 3、安装指令: #Step1、解压 tar -zxvf /mnt/data/output/perl-ExtUtils-Manifest-1.61-244.el7.tar.gz #Step2、进入解压后的目录,执行安装 sudo rpm -ivh *.rpm 4、安装指导:私信博主,全程指导安装
多水下航行器协同定位的MATLAB仿真:基于《Cooperative Localization for Autonomous Underwater Vehicles》的研究与实践,【7】MATLAB仿真 多水下航行器协同定位,有参考文档。 主要参考文档: 1. Cooperative Localization for Autonomous Underwater Vehicles,The International Journal of Robotics Research 主要供文档方法的学习 非全文复现。 ,MATLAB仿真; 多水下航行器协同定位; 参考文档; 自主水下航行器; 机器人学国际期刊; Cooperative Localization。,MATLAB仿真:多水下航行器协同定位研究参考国际期刊论文
基于大语言模型的多模态社交媒体信息流行度预测研究
1、文件内容:perl-Algorithm-Diff-1.1902-17.el7.rpm以及相关依赖 2、文件形式:tar.gz压缩包 3、安装指令: #Step1、解压 tar -zxvf /mnt/data/output/perl-Algorithm-Diff-1.1902-17.el7.tar.gz #Step2、进入解压后的目录,执行安装 sudo rpm -ivh *.rpm 4、安装指导:私信博主,全程指导安装
《基于分时电价下电动汽车多类型充放电调度策略优化及其经济与负荷曲线改善分析》,11-分时电价下电动汽车充放电调度策略优化-100% 摘要:代码主要做的是分时电价下电动汽车充放电策略的优化,电动汽车选取了四种典型的类型,包括比亚迪EV,尼桑EV,宝马mini以及三菱EV,四种类型电动汽车取若干辆,约束重点关注充放电约束、蓄电量约束、0-1启停约束等等,目标函数为经济效益最优,同时考虑负荷曲线的改善,并通过图展示其结果,具体看下图。 ,核心关键词: 分时电价; 电动汽车; 充放电策略优化; 类型; 约束; 经济效益; 负荷曲线改善; 图展示。,电价优化下电动汽车充放电调度策略研究
IMG_20250130_120659.jpg
该项目是一款基于JavaScript、TypeScript和微信小程序开发的火车票购票系统源码,包含1634个文件,涵盖395个JavaScript文件、293个TypeScript文件、271个JSON配置文件、240个WXML模板文件、232个WXSS样式文件、138个WXS脚本文件,并辅以22个PNG图片、19个Markdown文档和1个JPG图片。该系统旨在提供便捷的火车票购票服务。
驱动DHT11要学会看数据手册
《COMSOL模拟增强型地热开采采热井温度变化一年周期的瞬态分析》,comsol增强型地热开采 本模型采用达西定律接口、多孔介质传热接口、非等温管道流接口,采用瞬态求解器,求解采热井一年的温度变化 ,comsol; 增强型地热开采; 达西定律接口; 多孔介质传热接口; 非等温管道流接口; 瞬态求解器; 采热井温度变化,《COMSOL模型在地热开采中模拟采热井一年温度变化的研究》
0016-08-16122503-曾洋.zip
1.版本:matlab2014/2019a/2024a 2.附赠案例数据可直接运行matlab程序。 3.代码特点:参数化编程、参数可方便更改、代码编程思路清晰、注释明细。 4.适用对象:计算机,电子信息工程、数学等专业的大学生课程设计、期末大作业和毕业设计。
week01_lab_solutions.ipynb
免费JAVA毕业设计 2024成品源码+论文+录屏+启动教程 启动教程:https://www.bilibili.com/video/BV1SzbFe7EGZ 项目讲解视频:https://www.bilibili.com/video/BV1Tb421n72S 二次开发教程:https://www.bilibili.com/video/BV18i421i7Dx
Golang. KisFlow(Keep It Simple Flow).
免费JAVA毕业设计 2024成品源码+论文+录屏+启动教程 启动教程:https://www.bilibili.com/video/BV1SzbFe7EGZ 项目讲解视频:https://www.bilibili.com/video/BV1Tb421n72S 二次开发教程:https://www.bilibili.com/video/BV18i421i7Dx
1.版本:matlab2014/2019a/2024a 2.附赠案例数据可直接运行matlab程序。 3.代码特点:参数化编程、参数可方便更改、代码编程思路清晰、注释明细。 4.适用对象:计算机,电子信息工程、数学等专业的大学生课程设计、期末大作业和毕业设计。