Solr数据备份包括如下这些文件:
- solr config文件包括:
- solr.xml, 它位于SOLR_HOME下
- schema.xml, solrconfig.xml,stopwords.txt,synonyms.txt等和你应用相关的配置文件,他们通常位于SOLR_HOME/conf下。
- lucene index文件,它通常位于SOLR_HOME/data下面。该目录下面存放了真正的数据,我们主要就是讨论如何备份这里的数据。
备份方法
备份lucene index数据文件也分成两种方式:冷备份和热备份。
所谓冷备份就是指关闭solr,然后将SOLR_HOME/data下面的所有数据拷贝到一个安全的位置。这种方法简单,可靠,index数据文件不会产生不一致。但是缺点很明显,就是系统要关闭,如果数据量大的话,整个复制过程会比较长。
幸好,solr提供了一种非常简便的热备份方法,也就是利用Solr Replication Handler!Replication Handler的主要作用是在一个load-balancing的solr部署架构中,将index数据复制到各个slave服务器上。但是,即使在没有任何slave服务器的情况下,Replication Handler也可以用来在主服务器上创建index的副本。
那么让我们来看看怎么使用这个功能,其实相当简单,就是通过浏览器或curl等工具发送一个request,它的url是’http://master_server:port/solr/replication?command=backup’。这样备份就创建好了。默认情况下,会创建一个类似“snapshot.20120812201917”这样的文件夹,这个文件夹里面就包括了lucene index的数据备份。当然,你也可以指定该文件夹的位置,只需在url里面增加位置参数,如:&location=/foo/bar。
以alfresco中的solr为例,为了备份lucene的index,你需要发出如下请求:‘https://localhost:8443/solr/alfresco/replication?command=backup’(这里假设localhost是solr主服务器。url中的alfresco代表了solr core,alfresco系统中的solr使用了2个core,一个是alfresco——保存了当前alfresco中所有有效文档的index,另一个是archive——保存了所有被删除文档的index)。然后,你可以在‘alf_data/solr/workspace/SpacesStore/snapshot.20120902041725’中找到你备份的数据(20120902041725代表时间戳。每次备份都会不同)。
假如以上的Replication Handler url在你系统中显示“HTTP Status 404”,别着急,那是因为你还没有配置Replication Handler。你只需要在solrconfig.xml中增加如下的配置:
<requestHandler name=”/replication” >
<lst name=”master”>
<str name=”confFiles”>schema.xml,stopwords.txt</str>
<str name=”backupAfter”>startup</str>
<str name=”backupAfter”>optimize</str>
</lst>
<!–
<lst name=”slave”>
<str name=”masterUrl”>http://localhost:8983/solr/replication</str>
<str name=”pollInterval”>00:00:60</str>
</lst>
–>
</requestHandler>
各参数的具体含义参见:http://wiki.apache.org/solr/SolrReplication 这里就不再熬述。
这里稍作扩展,讨论一下solr Replication Handler 中snapshot的原理。为什么我们不能在solr运行过程中直接复制lucene index文件,而必须通过Replication Handler呢?原因是,假如你直接复制,那么在复制过程中,lucene有可能进行了commit的操作,而commit操作会涉及到对segment文件的merge,如此就很容易造成数据的不一致性的问题。那么Replication Handler是怎么处理的呢?其原理就是在于SnapshotDeletionPolicy。SnapshotDeletionPolicy能使用最近一次commit作为参照,把所有对应该次commit的index数据做一个快照,一直保留着直到系统创建完成所有的备份数据。以下代码就说明了这个原理:
IndexDeletionPolicy policy = new KeepOnlyLastCommitDeletionPolicy(); SnapshotDeletionPolicy snapshotter = new SnapshotDeletionPolicy(policy); IndexWriter writer = new IndexWriter(dir, analyzer, snapshotter, IndexWriter.MaxFieldLength.UNLIMITED); try { IndexCommit commit = snapshotter.snapshot(); Collection fileNames = commit.getFileNames(); /*<iterate over & copy files from fileNames>*/ } finally { snapshotter.release(); }
- 第二行代码创建一个snapshot,
- 你仍旧可以使用第三行创建的IndexWrite去更新数据,但它不会影响这个已创建的snapshot。
- try block里面就是将snapshot对应的index数据创建出来。
大家有兴趣的话可以看一下solr的源码(org.apache.solr.handler. ReplicationHandler中的private void doSnapShoot(SolrParams params, SolrQueryResponse rsp, SolrQueryRequest req)),原理和上面的代码差不多。
恢复
恢复操作很简单,就是把之前备份出来的index数据复制回去。例如,将备份数据复制到SOLR_HOME/data/index下,然后重启solr就搞定了。
对于alfresco中的solr而言,就是将index备份复制回/alf_data/solr/workspace/SpacesStore/index中。
重建索引
假如你没有任何备份,而index数据又崩溃了,最后万不得已,你就只能重建索引了。不过还好,这项工作很简单,你需要做的就是先把solr停止,然后删除SOLR_HOME/data下面的index文件夹以及其他文件夹,再重启solr,根据你应用的情况,solr会自动重建index(例如,alfresco中的solr),或是你手动发起重建index的请求(例如,通过DIH)。