JDBC connect SCAN IP

kakaxi9521發表於2016-12-05

SCAN(Single Client Access Name)是Oracle從11g R2開始推出的,客戶端可以透過SCAN特性負載均衡地連線到RAC資料庫。SCAN提供一個域名來訪問RAC,域名可以解析1個到3個(注意,最多3個)SCAN IP,我們可以透過DNS或者GNS來解析實現。其中DNS大家都很熟悉,這裡不多說。GNS(Grid Naming Service)則是Oracle 11g R2的新功能,可以透過DHCP服務為節點和SCAN分配VIP和SCAN IP。另外還有個優點是,對於新加入叢集的節點,它會自動分配VIP地址,更新叢集資源,客戶端依然透過SCAN特性負載均衡地連線到新增叢集節點上。除了DNS和GNS解析方法外,SCAN也可以使用hosts檔案來解析。客戶原來使用的Oracle 10g R2單機,現在使用的是Oracle 11g R2 RAC,客戶應用程式模組不完全是透過Weblogic的jdbc資料來源來連線資料庫,有個別模組單獨執行jdbc連線,其連線程式碼如下:

 Connection con=null;
		try
		{
			Class.forName("oracle.jdbc.driver.OracleDriver");
			con=DriverManager.getConnection("jdbc:oracle:thin:@10.10.12.3:1521:RLZY","xxxxx","xxxxx");
		}
		catch(Exception e)
		{
			e.printStackTrace();
		}  

程式執行出現如下錯誤

 java.sql.SQLException: Listener refused the connection with the following error:
ORA-12505, TNS:listener does not currently know of SID given in connect descriptor
 
	at oracle.jdbc.driver.T4CConnection.logon(T4CConnection.java:489)
	at oracle.jdbc.driver.PhysicalConnection.(PhysicalConnection.java:553)
	at oracle.jdbc.driver.T4CConnection.(T4CConnection.java:254)
	at oracle.jdbc.driver.T4CDriverExtension.getConnection(T4CDriverExtension.java:32)
	at oracle.jdbc.driver.OracleDriver.connect(OracleDriver.java:528)
	at java.sql.DriverManager.getConnection(DriverManager.java:571)
	at java.sql.DriverManager.getConnection(DriverManager.java:215)
	at t.testdb.execute(testdb.java:19)
	at t.testdb.main(testdb.java:63)
Caused by: oracle.net.ns.NetException: Listener refused the connection with the following error:
ORA-12505, TNS:listener does not currently know of SID given in connect descriptor
 
	at oracle.net.ns.NSProtocol.connect(NSProtocol.java:399)
	at oracle.jdbc.driver.T4CConnection.connect(T4CConnection.java:1140)
	at oracle.jdbc.driver.T4CConnection.logon(T4CConnection.java:340)
	... 8 more
Exception in thread "main" java.lang.NullPointerException
	at t.testdb.execute(testdb.java:30)
	at t.testdb.main(testdb.java:63)  

錯誤資訊說明不能識別連線字串中的SID,這裡為什麼會顯示使用的是SID,我們指定的是SERVICE_NAME,這就與JDBC連線字串的寫法有關。如果使用jdbc:oracle:thin:@10.10.12.3:1521:RLZY,JDBC會將RLZY解析為SID,如果是10.10.12.3:1521/RLZY,JDBC會將RLZY解析為服務名。對於單例項來說,一般SID與SERVICE_NAME相同,但是對於RAC來說,SID與SERVICE_NAME是不一樣的。對於11g RAC要使用SCAN IP來連線,那麼只能使用SERVICE_NAME,將程式碼修改成如下格式:

 Connection con=null;
		try
		{
			Class.forName("oracle.jdbc.driver.OracleDriver");
			con=DriverManager.getConnection("jdbc:oracle:thin:@10.10.12.3:1521/RLZY","xxx","xxx");
		}
		catch(Exception e)
		{
			e.printStackTrace();
		}  

總結,對於jdbc連線資料庫不管是單例項還是RAC,都建議使用在連線字串中使用jdbc:oracle:thin:@IP:PORT/SERVICE_NAME這種方法就可以完美處理這種問題。

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/21374452/viewspace-2129748/,如需轉載,請註明出處,否則將追究法律責任。

相關文章