--数据较少时,可以手工同步,更方便控制--用触发器即时同步两个表的实例:--测试环境:SQL2000,远程主机名:xz,用户名:sa,密码:无,数据库名:test--创建测试表,不能用标识列做主键,因为不能进行正常更新
--在远程主机上建表
if exists (select * from dbo.sysobjects where id = object_id(N'[test]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [test]create table test(id int not null constraint PK_test primary key
,name varchar(10))
go--以下操作在本机进行
--在本机上建表及做同步处理的工作
if exists (select * from dbo.sysobjects where id = object_id(N'[test]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [test]create table test(id int identity(1,1) primary key
,name varchar(10))
go--创建同步的触发器
create trigger t_test on test
for insert,update,delete
as
set XACT_ABORT on
--启动远程服务器的MSDTC服务
exec master..xp_cmdshell 'isql /S"xz" /U"sa" /P"" /q"exec master..xp_cmdshell ''net start msdtc'',no_output"',no_output--启动本机的MSDTC服务
exec master..xp_cmdshell 'net start msdtc',no_output--进行分布事务处理,如果表用标识列做主键,用下面的方法
BEGIN DISTRIBUTED TRANSACTION
delete from openrowset('sqloledb','xz';'sa';'',test.dbo.test)
where id in(select id from deleted)
insert into openrowset('sqloledb','xz';'sa';'',test.dbo.test)
select * from inserted
commit tran
go--插入数据测试
insert into test
select 1,'aa'
union all select 2,'bb'
union all select 3,'c'
union all select 4,'dd'
union all select 5,'ab'
union all select 6,'bc'
union all select 7,'ddd'--删除数据测试
delete from test where id in(1,4,6)--更新数据测试
update test set name=name+'_123' where id in(3,5)--显示测试的结果
select * from test a full join
openrowset('sqloledb','xz';'sa';'',test.dbo.test) b on a.id=b.id
--在远程主机上建表
if exists (select * from dbo.sysobjects where id = object_id(N'[test]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [test]create table test(id int not null constraint PK_test primary key
,name varchar(10))
go--以下操作在本机进行
--在本机上建表及做同步处理的工作
if exists (select * from dbo.sysobjects where id = object_id(N'[test]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [test]create table test(id int identity(1,1) primary key
,name varchar(10))
go--创建同步的触发器
create trigger t_test on test
for insert,update,delete
as
set XACT_ABORT on
--启动远程服务器的MSDTC服务
exec master..xp_cmdshell 'isql /S"xz" /U"sa" /P"" /q"exec master..xp_cmdshell ''net start msdtc'',no_output"',no_output--启动本机的MSDTC服务
exec master..xp_cmdshell 'net start msdtc',no_output--进行分布事务处理,如果表用标识列做主键,用下面的方法
BEGIN DISTRIBUTED TRANSACTION
delete from openrowset('sqloledb','xz';'sa';'',test.dbo.test)
where id in(select id from deleted)
insert into openrowset('sqloledb','xz';'sa';'',test.dbo.test)
select * from inserted
commit tran
go--插入数据测试
insert into test
select 1,'aa'
union all select 2,'bb'
union all select 3,'c'
union all select 4,'dd'
union all select 5,'ab'
union all select 6,'bc'
union all select 7,'ddd'--删除数据测试
delete from test where id in(1,4,6)--更新数据测试
update test set name=name+'_123' where id in(3,5)--显示测试的结果
select * from test a full join
openrowset('sqloledb','xz';'sa';'',test.dbo.test) b on a.id=b.id
--测试环境,SQL Server2000,远程服务器名:xz,用户名为:sa,无密码,测试数据库:test
--服务器上的表(查询分析器连接到服务器上创建)
if exists (select * from dbo.sysobjects where id = object_id(N'[user]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [user]create table [user](id int primary key,number varchar(4),name varchar(10))
go--以下在局域网(本机操作)
--state字段为辅助更新而设置的附加字段,字段值说明:null 表示新增记录,1 表示修改过的记录,0 表示无变化的记录
if exists (select * from dbo.sysobjects where id = object_id(N'[user]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
drop table [user]
GO
create table [user](id int identity(1,1) primary key,number varchar(4),name varchar(10),state bit)
go
--创建触发器,维护state字段的值
create trigger t_state on [user]
after update
as
update [user] set state=1
from [user] a join inserted b on a.id=b.id
where a.state is not null
go--为了方便同步处理,创建链接服务器到要同步的服务器
--这里的远程服务器名为:xz,用户名为:sa,无密码
if exists(select 1 from master..sysservers where srvname='srv_lnk')
exec sp_dropserver 'srv_lnk','droplogins'
go
exec sp_addlinkedserver 'srv_lnk','','SQLOLEDB','xz'
exec sp_addlinkedsrvlogin 'srv_lnk','false',null,'sa'
go--创建同步处理的存储过程
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[p_synchro]') and OBJECTPROPERTY(id, N'IsProcedure') = 1)
drop procedure [dbo].[p_synchro]
GO
create proc p_synchro
as
/*--因为MSDTC服务(分布式事务处理需要)工作不稳定,所以下面部分为选用内容
--set xact_abort on
--启动远程服务器的MSDTC服务
--exec master..xp_cmdshell 'isql /S"xz" /U"sa" /P"" /q"exec master..xp_cmdshell ''net start msdtc'',no_output"',no_output--启动本机的MSDTC服务
--exec master..xp_cmdshell 'net start msdtc',no_output--进行分布事务处理,如果表用标识列做主键,用下面的方法
--BEGIN DISTRIBUTED TRANSACTION
--*/
--同步删除的数据
delete from srv_lnk.test.dbo.[user]
where id not in(select id from [user]) --同步新增的数据
insert into srv_lnk.test.dbo.[user]
select id,number,name from [user] where state is null
--同步修改的数据
update srv_lnk.test.dbo.[user] set
number=b.number,name=b.name
from srv_lnk.test.dbo.[user] a
join [user] b on a.id=b.id
where b.state=1
--同步后更新本机的标志
update [user] set state=0 where isnull(state,1)=1
--COMMIT TRAN --如果启用分布式事务处理,加上此句
go--创建作业,定时执行数据同步的存储过程
if exists(SELECT 1 from msdb..sysjobs where name='数据处理')
EXECUTE msdb.dbo.sp_delete_job @job_name='数据处理'
exec msdb..sp_add_job @job_name='数据处理'--创建作业步骤
declare @sql varchar(800),@dbname varchar(250)
select @sql='exec p_synchro' --数据处理的命令
,@dbname=db_name() --执行数据处理的数据库名exec msdb..sp_add_jobstep @job_name='数据处理',
@step_name = '数据同步',
@subsystem = 'TSQL',
@database_name=@dbname,
@command = @sql,
@retry_attempts = 5, --重试次数
@retry_interval = 5 --重试间隔--创建调度
EXEC msdb..sp_add_jobschedule @job_name = '数据处理',
@name = '时间安排',
@freq_type=4, --4 每天,8 每周,16 每月
@freq_interval=1, --作业执行的天数
@freq_subday_type=0, --是否重复执行,0x1 在指定的时间, 0x4 分钟, 0x8 小时
@freq_subday_interval=1, --重复周期
@freq_recurrence_factor=0, --重复执行,则设置为1,否则设置为0
@active_start_time = 00000 --0点开始执行--添加目标服务器
EXEC msdb.dbo.sp_add_jobserver
@job_name = @jobname ,
@server_name = N'(local)'
go
Oracle与SQL Server的互连 -------------------------------------------------------------------------
作者:gototop
-------------------------------------------------------------------------另一篇
http://www.csdn.net/develop/author/columnAuthor/hochihyi/Article/SqlServer/002.htm
-----------------------------------------------------------------------------------不同数据库平台的互连一般称之为数据库的异构服务,现在各大数据库之间都可以实现这样的异构互连,只是各厂商的具体实现技术不一样,如:在SQL SERVER里面叫做LINKED SERVER,通过ODBC实现与其它数据库的互联。而ORACLE实现异构服务的技术叫做透明网关(Transparent Gateway),当然之前ORACLE还采用过通用连接技术。目前ORACLE利用透明网关可以实现和SQL SERVER、SYBASE、DB2等多种数据库的互联。透明网关的体系结构也很简单,在ORACLE和SQL SERVER之间使用ORACLE透明网关服务器实现互连互通,其中透明网关服务器可以与ORACLE或SQL SERVER数据库在同一台主机上,也可以是在独立的一台主机上。下面是具体步骤,如有疑问欢迎和我联系,MSN: [email protected]。1、在SQL SERVER数据库上创建测试账号和表这里我用的是10.16.74.140的PUBS数据库,账号cyx,create table t (c char(10));2、我测试所用数据库和透明网关是在同一台机器上,在我本机:10.16.98.16,透明网关在oracle默认安装时是不安装的,所以如果你想用需要选择这一选项。3、安装透明网关for sql server的软件后,可以在$ORACLE_HOME下看到tg4msql目录,编辑$ORACLE_HOME/tg4msql/admin/inittg4msql.sql文件确认这一行正确:HS_FDS_CONNECT_INFO="SERVER=10.16.74.140;DATABASE=pubs"4、修改透明网关server上的listener.ora,在SID_LIST中加入以下内容:(SID_NAME = tg4msql) # SID自己命名 (ORACLE_HOME = c:) (PROGRAM = tg4msql) 5、在oracle server上的tnsnames.ora中加入到透明网关的tnsname,内容如下:sql2k = (DESCRIPTION = (ADDRESS_LIST = (ADDRESS = (PROTOCOL = TCP)(HOST = 10.16.98.16)(PORT = 1521)) #此处HOST填的是透明网关SERVER的地址) (CONNECT_DATA = (SID = tg4msql) ) #此SID应和透明网关SERVER上设定的SID相同(HS=OK) ) 6、修改ORACLE SERVER的初始化参数,将global_names设为false,因为我们并不使用GLOBAL NAME。然后重起数据库。7、现在在ORACLE SERVER上创建DB LINK就可以了。下面实验数据:------------ http://www.ncn.cn/ ------------- gototop --------------C:>sqlplus /nologSQL*Plus: Release 9.2.0.1.0 - Production on 星期三 6月 25 13:29:41 2003Copyright (c) 1982, 2002, Oracle Corporation. All rights reserved.SQL> conn sys/change_on_install as sysdba已连接。SQL> create user cyx identified by cyx default tablespace users;用户已创建SQL> grant connect to cyx;授权成功。SQL> grant resource to cyx;授权成功。SQL> conn cyx/cyx已连接。SQL> create database link tosql2k connect to cyx identified by cyx using 2 'sql2k';数据库链接已创建。SQL> select * from t@tosql2k;c----------abcaaabbbcyxgototopncn11111已选择7行。SQL> insert into t@tosql2k values('ncn.cn');已创建 1 行。SQL> commit;提交完成。SQL> select * from t@tosql2k;c----------abcaaabbbcyxgototopncn11111ncn.cn已选择8行。------------ http://www.ncn.cn/ ------------- gototop --------------以上示例,oracle server和透明网关server都是在同一台机器上,像在开始说明的那样,我们同样可以在其他下面oracle server中通过透明网关来访问sql server的数据。下面是示例:现在这个oracle server上添加tnsname。------------ http://www.ncn.cn/ ------------- gototop --------------hawk3$sqlplus cyxSQL*Plus: Release 8.1.7.0.0 - Production on Wed Jun 25 14:00:34 2003(c) Copyright 2000 Oracle Corporation. All rights reserved.Enter password:Connected to:Oracle8i Enterprise Edition Release 8.1.7.0.0 - ProductionWith the Partitioning optionJServer Release 8.1.7.0.0 - ProductionSQL> create database link hawk3_sql2k connect to cyx identified by cyx2 using 'sql2k';Database link created.SQL> select * from t@hawk3_sql2k;c--------------------abcaaabbbcyxgototopncn11111ncn.cn8 rows selected.------------ http://www.ncn.cn/ ------------- gototop -------------- gototop 2003.7.25注:很多朋友问到关于透明网关的一些问题,在此加以说明如下: 1、Oracle For SQL Server的透明网关在UNIX下无法实现,目前只支持WIN; 原因很简单,SQL Server本身不支持UNIX,所以Oracle也无法直接在UNIX下访问SQL Server。 2、Oracle For其它数据库的透明网关,如SYBASE等有UNIX本版本的数据库在UNIX可以实现。 3、Oracle透明网关软件在Oracle 8i时是需要花钱另买的,大约1万$;到Oracle 9i时是作为数据库的一个组件免费发布的。安装时在组件种选择即可。 4、针对我们的实际应用,如果有需要实现Oracle 到SQL Server的互连,我们需要另外用一台WIN下的Oracle 9i来做透明网关服务器,其它UNIX下的Oracle通过这个透明网关来访问SQL Server。 5、不同数据库间的数据处理需使用标准SQL来实现。 6、各数据库中特殊的数据类型,需要在程序中实现转换,应尽量避免使用无法转换的数据类型。
1,必须要用SET XACT_ABORT ON
SET XACT_ABORT Off
2,过程中最好不能出错,否则oracle方会造成一定时间内的锁,清除锁后过一定时间才能正常工作,可以测试一下