实施别的系统时遇到一个问题,就是在SQL Server中中使用新建服务器连接方式连接到数据库Oracle时查询和写入某个表时出错,后来想到用一个外挂的程序来操作,可需要触发条件,轮询的话涉及到及时性和网络负荷问题.到网上一搜索,发现可以在SQL Server的存储过程或触发器中调用COM组件,这就比较好解决了.
首先建立一个COM服务器,只在里面写一个测试方法:Hello:
1 function TCotest.Hello(const Value: WideString): WideString;
2 begin
3 Result:='您输入的是:'+Value;
4 end;
2 begin
3 Result:='您输入的是:'+Value;
4 end;
可以在IDE中注册这个服务器,或者在初始化代码后加入自动注册的代码:
1 initialization
2 TComponentFactory.Create(ComServer, TCotest,
3 Class_Cotest, ciMultiInstance, tmApartment);
4 ComServer.UpdateRegistry(true);
5 end.
2 TComponentFactory.Create(ComServer, TCotest,
3 Class_Cotest, ciMultiInstance, tmApartment);
4 ComServer.UpdateRegistry(true);
5 end.
从D2007开始需要手工加入:
ComServer.UpdateRegistry(true);
否则COM服务器不能自动注册(当然可以手工注册) .
好了,可以先写个客户端测试一下,放个TDCOMConnection组件,设定好服务器的名称,OK,可以正常激活这个COM组件.
用代码来调用测试一下吧:
1 var
2 v:Variant;
3 s:string;
4 begin
5 v:=CreateOleObject('Project4.Cotest');
6 s:=v.Hello('Garfield');
7 ShowMessage(s);
8 v := Unassigned;
9 end;
2 v:Variant;
3 s:string;
4 begin
5 v:=CreateOleObject('Project4.Cotest');
6 s:=v.Hello('Garfield');
7 ShowMessage(s);
8 v := Unassigned;
9 end;
注意:要引用ComObj单元.
程序可以正常执行并返回结果,说明COM组件运行正常.
好了,让我们来到关键的SQL Server中,可以在查询分析器中或建立一个储存过程来测试一下调用:
(注:参考了网络上的代码)
1 declare @i int
2 declare @strRet varchar(50)
3 declare @strRetCode int
4 DECLARE @strErr varchar (255)
5 DECLARE @strErr1 varchar (255)
6 /* 首先创建Com 实例 */
7 exec @strRetCode = sp_OACreate "Project4.Cotest", @i out
8 IF @strRetCode <> 0
9 BEGIN
10 /* 创建实例 失败 */
11 EXEC sp_OAGetErrorInfo @i, @strErr OUT, @strErr1 OUT
12 PRINT '创建实例失败,失败的原因是:' + @strErr + '' + @strErr1
13 RETURN
14 END
15 /* 创建成功,开始调用 */
16 EXEC @strRetCode = sp_OAMethod @i,'Hello',@strRet OUT,'Garfield'
17 IF @strRetCode <> 0
18 BEGIN
19 /* 调用方法出错 */
20 EXEC sp_OAGetErrorInfo @i, @strErr OUT, @strErr1 OUT
21 PRINT '调用方法失败,失败的原因是::' + @strErr + @strErr1
22 EXEC sp_OADestroy @i
23 RETURN
24 END
25 PRINT '返回的结果是:' + @strRet
26 exec sp_OADestroy @i
2 declare @strRet varchar(50)
3 declare @strRetCode int
4 DECLARE @strErr varchar (255)
5 DECLARE @strErr1 varchar (255)
6 /* 首先创建Com 实例 */
7 exec @strRetCode = sp_OACreate "Project4.Cotest", @i out
8 IF @strRetCode <> 0
9 BEGIN
10 /* 创建实例 失败 */
11 EXEC sp_OAGetErrorInfo @i, @strErr OUT, @strErr1 OUT
12 PRINT '创建实例失败,失败的原因是:' + @strErr + '' + @strErr1
13 RETURN
14 END
15 /* 创建成功,开始调用 */
16 EXEC @strRetCode = sp_OAMethod @i,'Hello',@strRet OUT,'Garfield'
17 IF @strRetCode <> 0
18 BEGIN
19 /* 调用方法出错 */
20 EXEC sp_OAGetErrorInfo @i, @strErr OUT, @strErr1 OUT
21 PRINT '调用方法失败,失败的原因是::' + @strErr + @strErr1
22 EXEC sp_OADestroy @i
23 RETURN
24 END
25 PRINT '返回的结果是:' + @strRet
26 exec sp_OADestroy @i
注意,只有 sysadmin 固定服务器角色的成员才能执行 sp_OACreate。
执行一下,看到COM组件成功地在储存过程中返回了结果.
(测试环境:Win7+Delphi2010+SQL Server 2000)