环境:delphi XE10.2.2+kbmMW5.02+uniDac7.02+FB3.0
在日常应用中,我们经常会用到主/从(Master/Detail)关系表,如客户与订单、角色与权限等。在kbmMW中实现Mater/Detail关系表的方法有两种,各有优缺点。下面是我实现这两个方法的过程。
首先,我对kbmMW是不了解的,并受到之前开发的影响,一直认为在客户端一个数据集控件(TkbmMWClientQuery)必须在服务器端有一个(TkbmMWUNIDACQuery)与之联系,结果我的问题变成了怎么在服务器端使两个TkbmMWUNIDACQuery共存并分别响应客户端的请求。
但……。
后来得红鱼儿大侠指导,才知道在服务器端用一个TkbmMWUNIDACQuery就足以响应客户端的请求了。一切才恢复到我的问题上来。
主从关系表的实现在kbmMW中有例子和说明文档。我照着做了,但是却还是遇到问题。下面就将这个过程说一下。
在kbmMW的说明文档中明确说明,kbmMW实现主从关系表有两种方法:
一、第一种方法
当主关系表中的记录变化时,数据库将查询出与之相应的从关系表数据。
优点:
l 会得到最新的从表数据;
l 每次只传送与主表相匹配的从表数据;
缺点:
l 每次主表的记录变化时,都需要调用应用服务器或数据库。当然,如果不想这样,也可以启用从表中的缓存,在缓存中检索从表数据。
实现方法:
创建一个主关系表控件。如。可以是TkbmMWClientQuery并命名为:“kcqMaster”。
或者任何其他TkbmMWxxxxQuery。
创建一个从关系表控件。如。可以是TkbmMWClientQuery并命名为:“kcqDetail”。
或者任何其他TkbmMWxxxxQuery。
到底是TkbmMWClientQuery还是TkbmMWxxxxQuery取决于它是在客户端还是服务器端的主从关系表查询控件。
设置以下属性:
—kcqMaster.Query.Text:= ‘select * from customers’;
—kcqDetail.Query.Text:=' select * fromorders where CustomerID=:CustomerID ';
-将kcqDetail中的CustomerID参数,通过Params属性定义为ftInteger字段类型和ptInput参数类型。
注意:有一点必须强调,上述SQL语句中,参数:CustomerID必须与从表中的字段名(CusstomerID)相同,如果不相同,kbmMW就不认了。也就找不出相应的从表数据。
-添加一个TDatasource,如。dsMaster,并将其数据集属性连接到kcqMaster。
- kcqDetail.MasterSource:= dsMaster;
- kcqDetail.MasterFields:='ID';//这是主表中唯一的关键字段,用于搜索详细记录。如果有多于一个字段,可以通过(;)分号来分隔各个字段;
- kcqDetail.DetailFields:='CustomerID';//这是在从表上的字段,用于查找与特定主表记录匹配的从表记录。同样,如果多于一个字段,也是用(;)分号来分隔。
- kcqDetail.RequeryDetails:= true;//该属性用于当主表记录更改时,将对从表数据进行重新获取。
二、第二种方法
这种方法一次性从数据库中将主从表数据都下载到客户端,当主表记录更改时,kbmMW自动过滤掉与当前主表记录无关的从表数据。
优点:
l 在所有的主从表记录被获取之后,浏览主表非常快。从应用程序服务器或数据库中不需要再进行额外的数据请求。
l 它允许公文包主/从关系模式。这意味着您可以存储主从关系表数据在本地文件中,断开与网络的连接,你的主/从关系表仍然可用。
缺点:
l 所有主表记录的所有从表记录都需要打开。
l 你可能不会在任何时候都有详细记录的最新副本。
实现方法:
同样,在客户端或是服务器端创建两个代表主、从关系表的查询控件。kcqMaster和kcqDetail。
设置以下属性:
- kcqMaster.Query.Text:= ‘select * from customers’;
- kcqDetail.Query.Text:=' select * from orders ';
-添加一个TDatasource,如。dsMaster,并将其数据集属性连接到kcqMaster。
- kcqDetail.MasterSource:= dsMaster;
- kcqDetail.MasterFields:='ID';//这是主表中唯一的关键字段。
- kcqDetail.DetailFields:='CustomerID';//这是应该在细节表上的字段。
- kcqDetail.RequeryDetails:= false;//该入属性在每次主记录更改时将在从表内容中过滤不用的数据。
我想:这两种实现主/从关系表的方法各有优缺点,要选用哪种,看具体情况而定,如果数据从较多的,那还是采用第一种办法的好;如果数据比较少的,那采用第二种方法,将所有数据下载到本地也不是什么问题。
参考文档:
《Master/Detail the kbmMW way forkbmMW v. 1.xx》Kim Madsen(kbmMW作者)