dblink故障一例-阿里云开发者社区

开发者社区> 数据库> 正文

dblink故障一例

简介:
环境:oracle 12.1,一套两节点RAC,两个cdb,要跨cdb从一个cdb中的pdb创建dblink访问另一个cdb中的pdb。
创建完pdb之后,出现如下问题:
e74bcdafd6f70cbd7b15c2b86cbfbfbb379005ad
检查了一下两个节点的tnsnames.ora,并没有发现什么语法问题,但就是连接不上。

下一步,发现两个节点只有一个节点有tnsnames.ora文件,想着是否和单个节点没有tnsnames.ora有关,于是将1节点的tnsnames.ora复制到2节点,再测,仍然有问题。

下一步,想到自己创建一个dblink,在网上翻了翻怎么创建dblink的文章,找到了tom的:
You Asked
how can i create database links to access remote databases. 
please tell me the procedure of creating database links. 

and we said...
You need a tnsnames entry in your tnsnames.ora on the server. If you can: 

sqlplus scott/tiger@some_other_database 

from the machine the server you want to create the database link ON works -- you've gotten the first step done

For example, I can: 

$ sqlplus scott/tiger@ora8idev 

SQL*Plus: Release 8.1.5.0.0 - Production on Thu Jul 20 09:16:25 2000 
(c) Copyright 1999 Oracle Corporation. All rights reserved. 
Connected to: 
Oracle8i Enterprise Edition Release 8.1.5.0.0 - Production 
With the Partitioning and Java options 
PL/SQL Release 8.1.5.0.0 - Production 
scott@DEV8I.WORLD> 

Once you have that setup, you log into the database (the local database -- the one you want to create the database link in to connect to the OTHER database) and issue the create database link command (see the sql reference manual for complete syntax). For example I can: 

scott@8i> create database link ora8idev 
2 connect to scott 
3 identified by tiger 
4 using 'ora8idev' 
5 / 

Database link created. 

scott@8i> select * from dual@ora8idev; 


scott@8i> 

I do not have to use the connect to and identified by clauses, if I do not, it will use the login and password of the currently connected user to connect to the remote database. 

从tom的回答里,我突然得到一个验证dblink的方法,tom将创建dblink分为两步,首先第一步是在客户端服务器创建tnsnames.ora文件,然后通过本地命名的方式验证是否能够访问远程数据库服务器,如果这一步成功,则接下来可进行创建dblink的操作。也就是说,本地命名方式成功访问远程数据库服务器是创建dblink成功的必要条件。
如此一来,我可以先测试本地命名是否能成功登录数据库。经过测试,两节点均不能用本地命名方式登录数据库。可见问题基本定位在此。


这个时候想起创建dblink的两种方式,一种是通过tnsnames.ora来创建,创建命令中只简单包含服务名,第二种则是在创建命令中直接包含所有tnsnames.ora文件信息,这样一来绕过了tnsnames.ora方式无法正常使用dblink,经测试,成功。

下面来验证dblink的两种方式的不同点。
本地服务器主机名为hhu,数据库db_name为PROD;
远端服务器主机名为monit,数据库db_name为ORCL;
1、首先保证两台服务器网络互ping能通
2、在本地没有tnsnames.ora
a7b4df0f78ab1ce5c38f5880ea817c52a97fab30
在PROD上创建dblink,名为non_tns:
create public database link non_tns   
connect to hr identified by hr
using '(DESCRIPTION =
(ADDRESS_LIST=
(ADDRESS=(PROTOCOL=TCP)(HOST=192.168.56.111)(PORT=1521))
)
(CONNECT_DATA=
(SERVER=DEDICATED)
(SERVICE_NAME=ORCL)
)
)';
70596ac1b3cc47357c6cee261fdbc713e7462013
测试能否正常访问:
在ORCL本地查询:
03b605b489fb98edfeff437f9a841483a32c810e
fd87fa9df7e89966dc32cc26326ae45c9b2eec38
a939260b98cfc6419818aedddb3c4c10f96b1f67

d7733ec0ecdb4b45b92e31f61960f6cd66396273

二者查询结果一致,能成功访问到ORCL。说明在此种创建dblink的方式下,不需要在本地配置tnsnames.ora同样可以远程访问数据库。

再来看配置tnsnames.ora创建dblink的情况:
配置完成之后报错:
1d2b217b7321b86df7881cb71b51dcf5db17e029

这个时候使用tnsping命令,可以用来辅助定位故障:
7b282f7b162f5b1c9e1035d301a8aa29c1a0c58e
可见tnsnames.ora文件格式有问题:
b9a4375f7d139d8697fc5df7aa3a2d6aeb4264ab
问题就在于多了一对上图高亮的扩号,删除之后,
e1bb45913897c526585e02da10ada9ed178c8c61
d0ebb3b5d82d670f2299eded219b684b5caf0baf
正常,测试能否通过本地命名访问远程数据库:
aa7ce6c4dfa40145fe4750431ec79a7a1f658f80
1b48ae1fd27e3d9ff5f3fa45f5a12f619f7ff2db
然后创建第二个dblink,名为tns:
create database link tns connect to hr identified by hr using 'tns';
4cf5df371865f7dffb72d8c037d047a8d9d2b5d7
测试能否通过dblink tns访问远程数据库ORCL:
ebd92babde2bbd05783cc72dde8dd7be0ef385e2
b250a6d72ef011977481500078b200bdfd0e495c
同样可以成功访问。
现在将tnsnames.ora改名,再测试dblink tns:
4ec73b2050e8db76238bab13f1361049db25752e

在没有断开原来sqlplus连接的情况下还能访问(因为连接已经建立,没有断开)
febe3783d1631d7334c52a2d42e065c9b6482a92

断开sqlplus会话,重新连接,用dblink tns远程访问ORCL:
在等待几分钟后,会出现如下结果:
8ea64a3782bf2105a6ca458124e9af3f61c06f88
将tnsnames.ora改回来:
82c2b32b62f165c6d70881ecb70c8208e01c713d
0db1e41c525e346ecf6b8434711e37ee4417d1cb
同样需要断开重连:
b62fb432dbe5fea75c376ce3a52ae6cba4406fa1
由此可见,tnsnames.ora在第二种创建dblink的方式中,是dblink正常使用的必要条件,如没有它,则dblink无法正常工作。
两种dblink本质区别的猜想:第一种直接在数据字典中创建了dblink,且dblink所有的信息都存放在数据字典中,这种情况下通过dblink访问远程数据库,只需要进入数据字典查找dblink的相关定义即可,所需的所有信息都能找到;而第二种创建dblink的方式,把dblink的主干信息存放在tnsnames.ora文件中,数据字典中只存放dblink的一个名字,通过dblink远程访问数据库的时候,需要先查找数据库字典中的dblink,进而去tnsnames.ora中查找dblink的具体定义,然后才能远程访问数据库。

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

分享:
数据库
使用钉钉扫一扫加入圈子
+ 订阅

分享数据库前沿,解构实战干货,推动数据库技术变革

其他文章