企業常因歷史系統共存,需在 Oracle 直接查詢 SQL Server 資料。Oracle 的異構服務技術演進經歷:Generic Connectivity → Transparent Gateway (TG) → Oracle Database Gateway (DG)。本文以 Oracle Transparent Gateway for SQL Server (TG4MSQL) 為例,詳述從軟體安裝、Listener/TNS 設定、資料庫連結建立,到常見錯誤排解的完整流程。
Oracle Client (SQL*Plus, App)
│
▼
Oracle Database (Local/Remote)
│ Database Link (DBLINK)
▼
Oracle Net Listener (Port 1521)
│ SID = tg4msql
▼
Transparent Gateway Process (tg4msql executable)
│ HS_FDS_CONNECT_INFO → SQL Server
▼
SQL Server (Target Database)
pubs, 帳號 cyx)-- 在 SQL Server 執行
CREATE LOGIN cyx WITH PASSWORD = 'StrongPwd123';
CREATE USER cyx FOR LOGIN cyx;
GRANT SELECT ON SCHEMA::dbo TO cyx;
CREATE TABLE dbo.t (c CHAR(10));
INSERT INTO dbo.t VALUES ('test001'), ('test002');
$ORACLE_HOME/tg4msql/ 目錄應包含 admin/, bin/, lib/編輯 $ORACLE_HOME/tg4msql/admin/inittg4msql.ora(或 inittg4msql.sql 視版本):
# 核心連線字串:指向 SQL Server
HS_FDS_CONNECT_INFO = "SERVER=10.16.74.140;DATABASE=pubs;UID=cyx;PWD=StrongPwd123"
# 選擇性調校
HS_FDS_TRACE_LEVEL = OFF
HS_FDS_FETCH_ROWS = 100
HS_NLS_NCHAR = UCS2
HS_LANGUAGE = AMERICAN_AMERICA.AL32UTF8
編輯 $ORACLE_HOME/network/admin/listener.ora,在 SID_LIST_LISTENER 區塊新增:
SID_LIST_LISTENER =
(SID_LIST =
(SID_DESC =
(SID_NAME = tg4msql)
(ORACLE_HOME = /u01/app/oracle/product/19.0.0/dbhome_1)
(PROGRAM = tg4msql)
(ENVS = "LD_LIBRARY_PATH=/u01/app/oracle/product/19.0.0/dbhome_1/lib")
)
# ... 其他 SID ...
)
重新載入 Listener:lsnrctl reload
編輯 $ORACLE_HOME/network/admin/tnsnames.ora:
SQLSERVER_PUBS =
(DESCRIPTION =
(ADDRESS_LIST =
(ADDRESS = (PROTOCOL = TCP)(HOST = 10.16.98.16)(PORT = 1521))
)
(CONNECT_DATA =
(SID = tg4msql)
)
(HS = OK)
)
關鍵:HS = OK 告知 Oracle 這是異構服務連線;HOST 指向 Listener 所在主機(若 Gateway 與 Oracle 同機則為 localhost)。
-- 在 Oracle 執行
CREATE DATABASE LINK sqlserver_pubs
CONNECT TO "cyx" IDENTIFIED BY "StrongPwd123"
USING 'SQLSERVER_PUBS';
-- 測試查詢
SELECT * FROM "t"@sqlserver_pubs;
注意:SQL Server 物件名稱在 Oracle 端需用雙引號保持大小寫,且 schema 預設為 dbo。
| 錯誤代碼/現象 | 原因 | 解決 |
|---|---|---|
| ORA-28500 / ORA-02019 | Gateway 進程啟動失敗 | 檢查 listener.log、tg4msql 執行權限、LD_LIBRARY_PATH、HS_FDS_CONNECT_INFO 格式 |
| ORA-28528: Heterogeneous Services datatype conversion error | 資料型別對應失敗 (如 SQL Server datetime2, geography) |
在 SQL Server View 中轉換為相容型別,或升級 Oracle Database Gateway 19c+ |
| ORA-02070: database does not support TO_SAVEPOINT | 分散式交易不支援 | 僅執行 SELECT,或設定 HS_FDS_SUPPORT_STATISTICS=FALSE,避免 DML |
| 中文亂碼 | 字元集不匹配 | 確認 HS_LANGUAGE、NLS_LANG、SQL Server Collation 三方一致 (建議 AL32UTF8) |
| 連線緩慢 / Timeout | 網路延遲、Gateway 參數未調校 | 增加 HS_FDS_FETCH_ROWS、啟用 HS_FDS_BULK_FETCH=ON、檢查防火牆 |
Transparent Gateway 是 Oracle 連接 SQL Server 的經典路徑,核心在於 Listener 代理 Gateway 進程 → HS_FDS_CONNECT_INFO 指向目標 → TNS 別名 + HS=OK → Database Link。部署時最易踩坑的三點:字元集一致性、Gateway 進程權限與環境變數、SQL Server 型別相容性。新專案優先評估 Database Gateway 或 CDC 同步方案,降低執行期耦合風險。