核心 JDBC URL 格式
Oracle JDBC 连接的 URL(也称为连接字符串)遵循基本格式:

jdbc:oracle:thin:@<host>:<port>:<service_name_or_sid>
或者使用更现代的连接描述符格式(推荐):
jdbc:oracle:thin:@//<host>:<port>/<service_name>
格式解析:
jdbc:oracle:thin:: 协议部分。jdbc: 表示这是一个 JDBC 连接。oracle: 表示数据库供应商是 Oracle。thin: 表示使用纯 Java 的瘦客户端驱动,无需本地库,这是最常用的方式。
- 分隔符。
<host>: 数据库服务器的 IP 地址或主机名。<port>: 数据库监听器的端口号,默认为1521。<service_name_or_sid>:- Service Name (服务名): Oracle 10g 及以后版本推荐的方式,一个服务可以包含多个实例,更灵活,格式为
<service_name>。 - SID (系统标识符): Oracle 10g 之前版本的主要方式,一个 SID 对应一个数据库实例,格式为
<sid>。
- Service Name (服务名): Oracle 10g 及以后版本推荐的方式,一个服务可以包含多个实例,更灵活,格式为
常用连接参数 (属性)
在 JDBC URL 的末尾,您可以添加 key=value 对形式的参数,多个参数用 & 分隔,这些参数用于控制连接的行为、性能和安全性。
以下是常用参数的分类说明:

连接与认证参数
| 参数 | 描述 | 示例 |
|---|---|---|
user |
数据库用户名。 | user=myuser |
password |
数据库密码。 | password=mypassword |
internal_logon |
以管理员身份登录。SYSDBA 或 SYSOPER。 |
internal_logon=sysdba |
连接池与性能参数
| 参数 | 描述 | 示例 |
|---|---|---|
defaultRowPrefetch |
(非常重要) 设置从数据库预取的行数,可以显著减少网络往返次数,提升查询性能,默认为 1,建议设置为 50 到 200 之间。 |
defaultRowPrefetch=100 |
includeSynonyms |
是否包含同义词,默认为 true。 |
includeSynonyms=false |
restrictGetTables |
限制 DatabaseMetaData.getTables() 的返回结果,提高性能。 |
restrictGetTables=true |
连接超时与重试参数
| 参数 | 描述 | 示例 |
|---|---|---|
oracle.net.CONNECT_TIMEOUT |
(非常重要) 建立连接的超时时间(毫秒),如果在此时间内无法建立连接,连接将失败。 | oracle.net.CONNECT_TIMEOUT=5000 (5秒) |
oracle.net.READ_TIMEOUT |
(非常重要) 网络读取数据的超时时间(毫秒),如果一个查询长时间不返回数据,连接将抛出超时异常。 | oracle.net.READ_TIMEOUT=30000 (30秒) |
oracle.jdbc.retryOnBreak |
当连接因网络中断等 SQLRecoverableException 错误中断时,驱动是否自动重试执行最后一次操作,默认为 true。 |
oracle.jdbc.retryOnBreak=true |
字符集与国际化参数
| 参数 | 描述 | 示例 |
|---|---|---|
oracle.jdbc.defaultNChar |
是否默认使用 NCHAR, NVARCHAR2, NCLOB 等国家字符集类型,默认为 false。 |
oracle.jdbc.defaultNChar=true |
v$session.program |
设置在 V$SESSION 视图中显示的客户端程序名,便于在数据库端识别连接来源。 |
v$session.program=MyJavaApp |
高级与诊断参数
| 参数 | 描述 | 示例 |
|---|---|---|
oracle.jdbc.fanEnabled |
是否启用 Fast Application Notification (FAN) 事件通知,当集群实例发生故障时,应用可以快速收到通知并切换连接,建议在 RAC 环境中设置为 true。 |
oracle.jdbc.fanEnabled=true |
oracle.jdbc.J2EE13Compliant |
强制驱动遵循 J2EE 1.3 规范,可能会影响某些行为,如 NULL 值的处理,通常保持默认 false。 |
oracle.jdbc.J2EE13Compliant=true |
logLevel |
设置 JDBC 驱动的日志级别(如 OFF, SEVERE, WARNING, INFO, CONFIG, FINE, FINER, FINEST),对调试非常有用。 |
logLevel=FINE |
URL 完整示例
示例 1:基本连接 (使用 Service Name)
假设数据库主机是 mydbhost,端口是 1521,服务名是 ORCLPDB1。
String url = "jdbc:oracle:thin:@//mydbhost:1521/ORCLPDB1"; String user = "scott"; String password = "tiger"; // 在代码中拼接 String fullUrl = "jdbc:oracle:thin:@" + url + "?user=" + user + "&password=" + password; // 更推荐使用 Properties 对象
示例 2:包含关键性能和超时参数的连接
这是生产环境中非常推荐的配置。
String url = "jdbc:oracle:thin:@//mydbhost:1521/ORCLPDB1";
Properties props = new Properties();
props.put("user", "scott");
props.put("password", "tiger");
// 性能参数:预取100行
props.put("defaultRowPrefetch", "100");
// 连接超时:10秒
props.put("oracle.net.CONNECT_TIMEOUT", "10000");
// 读取超时:60秒
props.put("oracle.net.READ_TIMEOUT", "60000");
// 标识应用来源
props.put("v$session.program", "MyJavaApplication");
Connection conn = DriverManager.getConnection(url, props);
示例 3:连接到 RAC 集群 (使用 TNSNames.ora 或 EZConnect)
对于 RAC 环境,可以使用 TNS 别名。
方式 A: 使用 EZConnect (类似前面的格式,但指向 SCAN)
// SCAN (Single Client Access Name) 提供了集群的统一入口 String url = "jdbc:oracle:thin:@//my-scan-cluster:1521/MY_SERVICE";
方式 B: 使用 TNSNames.ora 文件
-
在客户端机器的
$ORACLE_HOME/network/admin目录下创建tnsnames.ora文件:MY_SERVICE = (DESCRIPTION = (ADDRESS = (PROTOCOL = TCP)(HOST = my-scan-cluster)(PORT = 1521)) (CONNECT_DATA = (SERVER = DEDICATED) (SERVICE_NAME = MY_SERVICE) ) ) -
在 JDBC URL 中直接使用 TNS 别名:
String url = "jdbc:oracle:thin:@MY_SERVICE";
最佳实践
-
始终使用连接池:在高并发应用中,绝对不要在每次请求时都创建和销毁连接,使用连接池(如 HikariCP, DBCP, C3P0)可以复用连接,极大地提升性能和资源利用率,HikariCP 是目前公认的性能最好的连接池。
-
使用
Service Name而非SID:Service Name是 Oracle 推荐的现代方式,功能更强大,尤其在 RAC 和 Data Guard 环境中。 -
设置合理的超时时间:必须设置
CONNECT_TIMEOUT和READ_TIMEOUT,以防止因网络问题或数据库hang住而导致的应用线程长时间阻塞。 -
配置
defaultRowPrefetch:对于查询密集型应用,适当设置defaultRowPrefetch可以显著减少数据库与应用之间的网络交互次数,是提升性能最简单有效的方法之一。 -
使用
Properties对象传递参数:将用户名、密码和其他属性放在Properties对象中,而不是直接拼接到 URL 字符串里,这样代码更清晰、更安全。 -
管理驱动版本:确保你使用的 JDBC 驱动版本(ojdbcX.jar)与你的 Oracle 数据库版本兼容,使用数据库版本相同或更新的驱动是最佳选择。
-
关闭资源:确保在
finally块中或使用try-with-resources语句(Java 7+)来关闭Connection,Statement, 和ResultSet,以避免资源泄漏。// try-with-resources 示例 (推荐) String sql = "SELECT * FROM employees"; try (Connection conn = dataSource.getConnection(); PreparedStatement stmt = conn.prepareStatement(sql); ResultSet rs = stmt.executeQuery()) { while (rs.next()) { // 处理结果集 } } catch (SQLException e) { e.printStackTrace(); } // conn, stmt, rs 会自动关闭
