您的位置:首页 > 数据库

HubbleDotNet 开源全文搜索数据库项目--自动和现有表同步

2010-08-25 14:20 627 查看
作者:eaglet

转载需注明出处

对于大部分应用来说,全文搜索功能只是应用的部分功能而非全部功能,很多系统在设计之初往往缺乏全文搜索方面的设计,搜索功能多是用数据库的like语句来实现,随着系统容量的增大和用户数量的增加,这种like无论从性能还是功能方面都无法满足站内搜索的需要。HubbleDotNet为这部分用户提供了松耦合度的系统集成方案,用户只需一小时不到时间就可以实现现有系统的全文搜索功能的后台部分,无需对现有数据库表结构做任何改动,无需编写大量代码。其中自动和现有表数据同步是这个解决方案中的重要一环。本文重点介绍如何设置,以完成全文索引和现有数据表的数据同步。

适用版本:HubbleDotNet0.9.6.0

项目首页:http://www.hubbledotnet.com/

下载地址:http://hubbledotnet.codeplex.com/

适用范围:本文适用于被动模式索引的两种模式AppendOnly和Updatable

功能简介:

针对现有数据表进行索引,只能使用被动模式建立索引

详见:为数据库现有表或视图建立全文索引(一)AppendOnly模式和HubbleDotNet开源全文搜索数据库项目--为数据库现有表建立全文索引(二)Updatable模式

在0.9版本以前,被动模式索引(IndexOnly=true)是无法实现自动同步的,由于HubbleDotNet全文索引和数据库之间缺乏触发机制,数据库中数据表的增加,更改和删除无法被hubbledotnet获知,用户必须手工方式和数据库同步,详见:通过程序和现有表或视图同步。

0.9.6.0版本以后,HubbleDotNet提供了自动和数据库现有表同步的机制,用户只要调用Hubble.SqlClient中提供的一个类,就可以触发HubbleDotNet和数据库进行同步,用户可以根据自己的实际情况确定何时触发同步,同步周期是多少。HubbleDotNet暂时没有提供自动的同步任务,这是因为目前这方面需求还不是很明确,不同项目可能对同步的触发时间和同步周期有不同的要求,比如有的用户可能希望夜里才触发同步,有的用户可能希望每5分钟就同步一次等等。由于需求差异较大,HubbleDotNet目前版本暂时确定把这个触发同步的主动权交给用户,当然这个触发同步操作是非常简单的,只需3行代码就可以完成。

下面重点谈谈如何设置自动同步

Appendonly模式

Appendonly模式下,自动同步设置非常简单,只需要在TableInfo中将TableSynchronization设置为ture。就可以了。





同步流程

如上图所示,用户在执行Hubble.SqlClient提供的类TableSynchronization的Synchronize方法后,会先判断目前是否正在同步,如果正在同步,将返回False,用户可以在等待本次同步完成后,再执行这个方法触发同步。触发同步成功后,HubbleDotNet的Server端将扫描数据库中未建立索引的新增记录,对这些记录进行索引,索引完成后,按照用户指定的优化方案对索引进行优化。

HubbleDotNet的查询分析器(QueryAnalyzer)提供了同步数据调用的界面,这个也作为同步数据的示例代码供使用者参考。

下面给出一个简单的例子,表结构如下:





同步设置如下:





执行同步操作





点Start开始同步

参数说明:

Step:表示同步时每次从数据库读取多少条记录。假如设置为5000,待同步的记录为12000条,则开始同步后,Server端会进行3次批量索引,前两次每次批量索引5000条,最后一次2000条。批量索引完所有待同步的记录后开始优化。如果搞不清这个地方是干什么的,请保持这个数值不变,5000是我测试过的一个比较理想的数值。

Optimizeoption:指明优化策略。默认按最小方式优化。如果索引文件较大,按最小方式优化会比较耗时,可以选择按这种方式优化,即Middle方式。





点Start后,同步操作就开始执行,你可以点Stop去停止同步。





同步完成





Updatable模式

Updatable模式即原来的Append,update,delete模式。这种模式由于存在删除和更改操作,同步工作会比较复杂一些。我们需要建立一个辅助表来实现

下面以具体例子来说明:

要索引的表结构





创建辅助触发表(TriggerTable)

createtableHBTrigger_EnglishNews
(
Serialbigintidentity(1,1)notnullprimarykey,
Idintnotnull,
Oprchar(16),
Fieldsnvarchar(4000)null,
)

.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

gocreateindexITriggerOprSerialonHBTrigger_EnglishNews(Opr,Serial)

表结构如上所述,辅助触发表必须遵照这个表结构创建,表名可以随便设置。

Id字段对于索引表中DocidField这个字段,这里对于索引表中的Id字段。如果索引表中DocIdField字段是bigint,这里需要指定为bigin。

Opr字段告诉hubbledotnet改动是更新,还是删除。

Fields字段只有更新(Update)时有效,告诉hubbledotnet更新操作修改了哪几个字段。

如果你的数据库不是SQLSERVER,请按照这个表结构创建对应数据库的辅助触发表。

注意:辅助触发表必须和主表在同一个数据库中。由于要用到对Opr和Serial同时查询,所以建议按上述SQL建一个复合索引。

设置TableInfo

按下图所示设置TableSynchronization设置为ture并指定辅助触发表的表名。





创建一个更新触发器

如果你的现有表有更新操作,你就必须创建更新触发器,数据更新时,更新触发器会把哪些Id,哪些字段更新的信息写入到辅助触发表中。

凡是Tokenized和Untokenized类型的字段都需要在更新触发器中设置,更新触发器的示例代码如下:

CreateTriggerHBTrigger_EnglishNews_Update
OnEnglishNews
forUpdate

As
DECLARE@updateFieldsnvarchar(4000)
set@updateFields=''

ifUpdate(GroupId)
begin
set@updateFields=@updateFields+'GroupId,'
end

ifUpdate(SiteId)
begin
set@updateFields=@updateFields+'SiteId,'
end

ifUpdate(Time)
begin
set@updateFields=@updateFields+'Time,'
end

ifUpdate(Title)
begin
set@updateFields=@updateFields+'Title,'
end

ifUpdate(Content)
begin
set@updateFields=@updateFields+'Content,'
end

if@updateFields<>''
begin
insertintoHBTrigger_EnglishNewsselectid,'Update',@updateFieldsfromInserted
end

.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

其中EnglishNews是主表的表名,HBTrigger_EnglishNews是辅助触发表的表名。

GroupId,SiteId等等是主表中untokenized和tokenized字段,这个触发器的工作就是记录表更新时哪些字段发生了变化。

在对具体表实现这个触发器时不可以照搬这个代码,需要根据具体表的索引字段对Time,Title,Content等等这些地方进行修改。

同样如果数据库不是SQLSERVER,请按照对应数据库的触发器语法建立触发器。

创建一个删除触发器

如果你的现有表有删除操作,你就必须创建删除触发器,数据被删除时,删除触发器会把哪些被删除的Id信息写入到辅助触发表中。

CreateTriggerHBTrigger_EnglishNews_Delete
OnEnglishNews
forDelete
As
insertintoHBTrigger_EnglishNewsselectid,'Delete',''fromDeleted


.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

增量的同步

对于增量(Insert)数据的同步,Updatable和Appendonly的方式类似,不需要通过触发器来实现,所以如果你的表频繁增量,你完全没有比较担心触发器对数据插入性能的影响,因为增量时不会触发任何触发器。

执行同步操作





点Start开始同步

参数说明:

Step:表示同步时每次从数据库读取多少条记录。假如设置为5000,待同步的记录为12000条,则开始同步后,Server端会进行3次批量索引,前两次每次批量索引5000条,最后一次2000条。批量索引完所有待同步的记录后开始优化。如果搞不清这个地方是干什么的,请保持这个数值不变,5000是我测试过的一个比较理想的数值。

Optimizeoption:指明优化策略。默认按最小方式优化。如果索引文件较大,按最小方式优化会比较耗时,可以选择按这种方式优化,即Middle方式。





点Start后,同步操作就开始执行,你可以点Stop去停止同步。





同步完成





同步流程





触发器对性能的影响

触发器只对更改和删除操作的性能造成影响,由于触发器只记录更改或删除的ID号和更改字段,而不记录更改的实际内容,所以即使有影响,这个影响也是有限的。如果某些应用中,使用者觉得这种影响无法接受,那么只能参照这篇文章通过程序和现有表或视图同步通过程序手动同步数据了。

通过后台任务自动定时同步

你可以有两种方式来触发同步,一种是通过HubbleDotNet的后台任务自动来实现定时同步,见下面文章

通过后台任务自动同步或优化索引

你也可以通过自己写程序来触发同步操作,下面是程序调用方法

程序调用

可参考QueryAnalyzer下的FormTableSynchronization.cs

引用Hubble.SQLClient

TableSynchronization的实例化

TableSynchronization_TableSync;
TableSynchronization.OptimizeOptionoption=TableSynchronization.OptimizeOption.Minimum;
intstep=(int)numericUpDownStep.Value;
HubbleConnectionconn=newHubbleConnection(connectString);
conn.Open();
_TableSync=newTableSynchronization(DataAccess.Conn,TableName,step,option);


.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

触发同步:

_TableSync.Synchronize();

这个函数返回True,表示触发同步成功。

获取同步进度:

doubleprogress=_TableSync.GetProgress();

这个函数会返回同步进度的百分比,如果返回100,表示同步完成。
.csharpcode,.csharpcodepre
{
font-size:small;
color:black;
font-family:consolas,"CourierNew",courier,monospace;
background-color:#ffffff;
/*white-space:pre;*/
}
.csharpcodepre{margin:0em;}
.csharpcode.rem{color:#008000;}
.csharpcode.kwrd{color:#0000ff;}
.csharpcode.str{color:#006080;}
.csharpcode.op{color:#0000c0;}
.csharpcode.preproc{color:#cc6633;}
.csharpcode.asp{background-color:#ffff00;}
.csharpcode.html{color:#800000;}
.csharpcode.attr{color:#ff0000;}
.csharpcode.alt
{
background-color:#f4f4f4;
width:100%;
margin:0em;
}
.csharpcode.lnum{color:#606060;}

停止同步

_TableSync.Stop();

如果当前表正在同步,这些这个函数,同步操作将被终止。

返回Hubble.net技术详解
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐