Class.forName (“ oracle.jdbc.driver.OracleDriver”) ใช้งานจริงเป็นอย่างไรขณะเชื่อมต่อกับฐานข้อมูล


93

จะสั่งอะไร

Class.forName("oracle.jdbc.driver.OracleDriver")

ขณะเชื่อมต่อกับฐานข้อมูล Oracle หรือไม่ มีวิธีอื่นในการทำสิ่งเดียวกันหรือไม่?


6
ที่เกี่ยวข้อง: stackoverflow.com/questions/5992126/loading-jdbc-driverโปรดทราบว่าคุณต้องเรียกใช้เพียงครั้งเดียวในระหว่างการเริ่มต้นแอปพลิเคชันของคุณ คุณไม่จำเป็นต้องเรียกมันว่าทุกครั้งก่อนที่จะเชื่อมต่อระหว่างอายุการใช้งานของแอปพลิเคชัน
BalusC

@BalusC สมมติว่าฉันมีรายละเอียดการเชื่อมต่อของฉันในคลาสแยกต่างหากAที่ฉันเรียกClass.forName("oracle.jdbc.driver.OracleDriver")ในตัวAสร้างคลาสและฉันสร้างA'sอ็อบเจกต์เพื่อรับฟิลด์การเชื่อมต่อสำหรับแต่ละ servlet ที่ฉันต้องการการเชื่อมต่อจากนั้น java จะข้ามClass.forName("oracle.jdbc.driver.OracleDriver")หรือจะโหลดอีกครั้ง?
Asif Mushtaq

คำตอบ:


71

มันได้รับการอ้างอิงไปยังวัตถุชั้นกับ FQCN oracle.jdbc.driver.OracleDriver(ชื่อชั้นที่มีคุณสมบัติครบถ้วน)

มันไม่ได้ "ทำ" อะไรในแง่ของการเชื่อมต่อกับฐานข้อมูลนอกเหนือจากการตรวจสอบให้แน่ใจว่าชั้นที่ระบุมีการโหลดโดย ClassLoader ไม่มีความแตกต่างพื้นฐานระหว่างการเขียน

Class<?> driverClass = Class.forName("oracle.jdbc.driver.OracleDriver");
// and
Class<?> stringClass = Class.forName("java.lang.String");

Class.forName("com.example.some.jdbc.driver")โทรแสดงขึ้นในมรดกรหัสที่ใช้ JDBC เนื่องจากว่าเป็นมรดกทางของการโหลดไดรเวอร์ JDBC

จากบทช่วยสอน Java :

ในรุ่นก่อนหน้าของ JDBC ที่จะได้รับการเชื่อมต่อครั้งแรกที่คุณจะต้องเริ่มต้นไดรเวอร์ JDBC Class.forNameของคุณโดยการเรียกวิธีการ java.sql.Driverวิธีการนี้ต้องวัตถุของการพิมพ์ แต่ละไดรเวอร์ JDBC java.sql.Driverมีมากกว่าหนึ่งชั้นเรียนที่ดำเนินการอินเตอร์เฟซ
...
ไดรเวอร์ JDBC 4.0 ใด ๆ ที่พบในพา ธ คลาสของคุณจะถูกโหลดโดยอัตโนมัติ (อย่างไรก็ตามคุณต้องโหลดไดรเวอร์ก่อน JDBC 4.0 ด้วยตนเองด้วยวิธีClass.forNameนี้)

อ่านเพิ่มเติม(อ่าน: คำถามนี้เป็นข้อมูลซ้ำซ้อน)


29
กล่าวอีกนัยหนึ่งก็คืออนุญาตให้คุณใช้คลาสไดรเวอร์โดยไม่ต้องมีการนำเข้าอย่างชัดเจนสำหรับคลาสของคุณ สิ่งนี้ช่วยให้คุณสร้างโปรเจ็กต์ได้โดยไม่ต้องมีไดรเวอร์ Oracle ใน classpath ของคุณ
JustinKSU

3
ควรสังเกตว่าใน "วิธีเดิม" คุณจะโทรClass.forName()โดยไม่จับการอ้างอิงถึง driverClass ที่ส่งคืนดังนั้นในตอนแรกดูเหมือนว่าจะไม่มีการดำเนินการใด ๆ
matt b

11
นั่นเป็นเพราะไดรเวอร์ JDBC ควรมีตัวเริ่มต้นแบบคงที่ซึ่งลงทะเบียนไดรเวอร์กับ DriverManager เมื่อใช้ Class.forName () ตัวเริ่มต้นนี้จะถูกเรียกใช้งานและลงทะเบียนไดรเวอร์แล้ว เนื่องจาก JDBC 4.0 DriverManager เองใช้ ServiceLoader เพื่อค้นหาไดรเวอร์บน classpath
Mark Rotteveel

1
@MattBall เกี่ยวกับ pre-JDBC 4.0 การได้รับการอ้างอิงถึงไดรเวอร์หรือการเรียกใช้ฟังก์ชันคงที่ของคลาสไดรเวอร์นั้นจะโหลดคลาสไดรเวอร์โดยอัตโนมัติ แล้วทำไมเราต้องทำด้วยตนเองClass.forName("etc.driver")?
Pacerier

1
@Pacerier สมมติฐานที่ไม่ถูกต้อง JDBC ไม่ทราบว่าคุณต้องการโหลดไดรเวอร์ใดดังนั้นจึงไม่มีอะไรใน JDBC (ซึ่งเป็นไดรเวอร์ที่ไม่เชื่อเรื่องพระเจ้า) ที่รู้ว่าอ้างถึงคลาสไดรเวอร์ ดังนั้นคุณต้องมีบางอย่างที่ทำให้เกิดการโหลดคลาส Class.forName(...)ผมคิดว่าวิธีการแบบคงที่จะทำงานแทน
Matt Ball

13

มันลงทะเบียนไดรเวอร์ บางอย่างในรูปแบบ:

public class SomeDriver implements Driver {
  static {
    try {
      DriverManager.registerDriver(new SomeDriver());
    } catch (SQLException e) {
      // TODO Auto-generated catch block
    }
  }

  //etc: implemented methods
}

6

จากบทช่วยสอน Java JDBC :

ในรุ่นก่อนหน้าของ JDBC ที่จะได้รับการเชื่อมต่อครั้งแรกที่คุณจะต้องเริ่มต้นไดรเวอร์ JDBC Class.forNameของคุณโดยการเรียกวิธีการ ไดรเวอร์ JDBC 4.0 ใด ๆ ที่พบในพา ธ คลาสของคุณจะถูกโหลดโดยอัตโนมัติ (อย่างไรก็ตามคุณต้องโหลดไดรเวอร์ก่อน JDBC 4.0 ด้วยตนเองด้วยวิธีClass.forNameนี้)

ดังนั้นถ้าคุณกำลังใช้ Oracle 11g (11.1) คนขับกับ Java 1.6 Class.forNameคุณไม่จำเป็นต้องโทร มิฉะนั้นคุณจะต้องเรียกมันเพื่อเริ่มต้นไดรเวอร์


1
@Jonathan คุณหมายถึงอะไรโดย "โหลดไดรเวอร์ใด ๆ ด้วยตนเองก่อน JDBC 4.0 ด้วยวิธี Class.forName" คุณช่วยอธิบายได้ไหม
Aravind

การClass.forNameเรียกใช้บังคับให้ classloader โหลดคลาสที่กำหนด นี่คือขั้นตอนการโหลดด้วยตนเองที่อธิบายไว้ในบทช่วยสอน
Jonathan

@Jonathan นั่นคือเหตุผลที่การเชื่อมต่อของฉันยังคงทำงานโดยไม่มีclass.forName();:)
Asif Mushtaq

2

Pre Java 6 DriverManagerคลาสจะไม่ทราบว่าคุณต้องการใช้ไดรเวอร์ JDBC ตัวใด Class.forName("...")เป็นวิธีการโหลดคลาสไดรเวอร์ล่วงหน้า

หากคุณใช้ Java 6 คุณไม่จำเป็นต้องทำสิ่งนี้อีกต่อไป


ใช่ต้องใช้: OracleDataSource ตอนนี้docs.oracle.com/cd/B28359_01/java.111/b31224/urls.htm#i1070726และสร้าง url ด้วยตัวเอง: สุดท้าย OracleDataSource ds = OracleDataSource ใหม่ (); ds.setDriverType ("บาง"); ds.setServerName (hostName); ds.setPortNumber (พอร์ต); //ds.setDatabaseName(dbName); ds.setServiceName (dbName); การเชื่อมต่อ = ds.getConnection (ผู้ใช้, pwd);
Rajesh Goel

1

คำสั่งนี้โหลดคลาสของไดรเวอร์ Oracle jdbc เพื่อให้พร้อมใช้งานสำหรับอินสแตนซ์ DriverManager หลังจากโหลดคลาสแล้วระบบสามารถเชื่อมต่อกับ Oracle โดยใช้มัน คุณสามารถใช้วิธี registerDriver ของ DriverManager และส่งผ่านอินสแตนซ์ของไดรเวอร์ JDBC ที่คุณต้องการได้



0

ใช้ oracle.jdbc.OracleDriver ไม่ใช่ oracle.jdbc.driver.OracleDriver คุณไม่จำเป็นต้องลงทะเบียนหากไฟล์ jar ของไดรเวอร์อยู่ในไดเร็กทอรี "WEB-INF \ lib" หากคุณใช้ Tomcat บันทึกสิ่งนี้เป็น test.jsp และวางไว้ในไดเรกทอรีเว็บของคุณและปรับใช้โฟลเดอร์เว็บแอปของคุณอีกครั้งในตัวจัดการ Tomcat:

<%@ page import="java.sql.*" %>

<HTML>
<HEAD>
<TITLE>Simple JSP Oracle Test</TITLE>
</HEAD><BODY>
<%
Connection conn = null;
try {
    Class.forName("oracle.jdbc.OracleDriver");
    conn = DriverManager.getConnection("jdbc:oracle:thin:@XXX.XXX.XXX.XXX:XXXX:dbName", "user", "password");
    Statement stmt = conn.createStatement();
    out.println("Connection established!");
}
catch (Exception ex)
{
    out.println("Exception: " + ex.getMessage() + "");

}
finally
{
    if (conn != null) {
        try {
            conn.close();   
        }
        catch (Exception ignored) {
            // ignore
        }
    }
}

%>
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.