100

What will the command

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

exactly do while connecting to a Oracle database? Is there an alternate way of doing the same thing?

Mark Rotteveel
  • 100,966
  • 191
  • 140
  • 197
Aravind
  • 2,188
  • 4
  • 24
  • 28
  • 6
    Related: http://stackoverflow.com/questions/5992126/loading-jdbc-driver Note that you need to call it **only once**, during your application's startup; you don't need to call it everytime before getting a connection during application's lifetime. – BalusC Nov 08 '11 at 15:59
  • @BalusC Suppose I have my connection detail in separate class `A` where I call `Class.forName("oracle.jdbc.driver.OracleDriver")` in class `A` constructor, and I create `A's` object to get connection field for each servlet where I need connection then java will skip `Class.forName("oracle.jdbc.driver.OracleDriver")` or will load again? – Asif Mushtaq Oct 18 '15 at 09:59

7 Answers7

82

It obtains a reference to the class object with the FQCN (fully qualified class name) oracle.jdbc.driver.OracleDriver.

It doesn't "do" anything in terms of connecting to a database, aside from ensure that the specified class is loaded by the current classloader. There is no fundamental difference between writing

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

Class.forName("com.example.some.jdbc.driver") calls show up in legacy code that uses JDBC because that is the legacy way of loading a JDBC driver.

From The Java Tutorial:

In previous versions of JDBC, to obtain a connection, you first had to initialize your JDBC driver by calling the method Class.forName. This methods required an object of type java.sql.Driver. Each JDBC driver contains one or more classes that implements the interface java.sql.Driver.
...
Any JDBC 4.0 drivers that are found in your class path are automatically loaded. (However, you must manually load any drivers prior to JDBC 4.0 with the method Class.forName.)

Further reading (read: questions this is a dup of)

Community
  • 1
  • 1
Matt Ball
  • 354,903
  • 100
  • 647
  • 710
  • 31
    In other words, it allows you to use the Driver class without having an explicit import for your class. This allows you to build the project without having to have the Oracle driver in your classpath. – JustinKSU Nov 08 '11 at 15:48
  • 3
    should note though that in the "legacy way" you would call `Class.forName()` without capturing the reference to the driverClass returned, so it seems at first glance like a no-op operation – matt b Nov 08 '11 at 15:56
  • 12
    That is because a JDBC driver should have a static initializer which registers the driver with the DriverManager. When using Class.forName() this initializer is executed and the driver is registered. Since JDBC 4.0 the DriverManager itself uses ServiceLoader to find drivers on the classpath. – Mark Rotteveel Nov 08 '11 at 16:29
  • 1
    @MattBall, Regarding pre-JDBC 4.0, obtaining a reference to the driver or calling a static function of that driver class would already auto-load the driver class. So why do we have to manually do `Class.forName("etc.driver")` ? – Pacerier Aug 28 '14 at 22:52
  • 1
    @Pacerier incorrect assumption. JDBC does not know which driver you want to load, so there's nothing in JDBC (which is driver-agnostic) that knows to refer to the driver class. So you need _something_ which triggers a class load. I suppose that a static method would work instead of `Class.forName(...)`. – Matt Ball Aug 28 '14 at 23:02
  • 1
    @MattBall, That's what I'm talking about. Why do we need to explicitly load the class with `Class.forName` when we can simply do `Driver.getInstance` or `Driver.setSettings` or `Driver.Anything`? – Pacerier Aug 29 '14 at 00:27
  • 1
    Presumably because there's no way to know which static method, if any, to call. You can't enforce the presence of a static method in an interface. – Matt Ball Aug 29 '14 at 13:07
  • @JustinKSU No. It registers the driver with the JDBC driver manager. It's part of the JDBC architecture pre 2007. There was never a requirement for you to import the class yourself or use it in any way in your code. – user207421 Sep 21 '16 at 17:07
14

It registers the driver; something of the form:

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

  //etc: implemented methods
}
McDowell
  • 107,573
  • 31
  • 204
  • 267
7

From the Java JDBC tutorial:

In previous versions of JDBC, to obtain a connection, you first had to initialize your JDBC driver by calling the method Class.forName. Any JDBC 4.0 drivers that are found in your class path are automatically loaded. (However, you must manually load any drivers prior to JDBC 4.0 with the method Class.forName.)

So, if you're using the Oracle 11g (11.1) driver with Java 1.6, you don't need to call Class.forName. Otherwise, you need to call it to initialise the driver.

Jonathan
  • 7,536
  • 4
  • 30
  • 44
  • 1
    @Jonathanwhat do you mean by "manually load any drivers prior to JDBC 4.0 with the method Class.forName" can you please explain? – Aravind Nov 08 '11 at 16:57
  • The `Class.forName` call forces the classloader to load the given class. This is the manual loading step described in the tutorial. – Jonathan Nov 09 '11 at 00:05
  • @Jonathan So that's why my connection still working without `class.forName();` :) – Asif Mushtaq Apr 08 '16 at 17:45
2

Pre Java 6 the DriverManager class wouldn't have known which JDBC driver you wanted to use. Class.forName("...") was a way on pre-loading the driver classes.

If you are using Java 6 you no longer need to do this.

Qwerky
  • 18,217
  • 6
  • 44
  • 80
  • Yes, one needs to use: OracleDataSource now http://docs.oracle.com/cd/B28359_01/java.111/b31224/urls.htm#i1070726 and it makes the url on its own: final OracleDataSource ds = new OracleDataSource(); ds.setDriverType("thin"); ds.setServerName(hostName); ds.setPortNumber(port); //ds.setDatabaseName(dbName); ds.setServiceName(dbName); connection = ds.getConnection(user, pwd); – Rajesh Goel Jun 21 '16 at 01:42
1

This command loads class of Oracle jdbc driver to be available for DriverManager instance. After the class is loaded system can connect to Oracle using it. As an alternative you can use registerDriver method of DriverManager and pass it with instance of JDBC driver you need.

anatolich
  • 11
  • 3
1

An alternative would to use the jdbc.drivers System property to specify your required drivers(s) on the command line when you start the JVM.

ewan.chalmers
  • 16,145
  • 43
  • 60
0

Use oracle.jdbc.OracleDriver, not oracle.jdbc.driver.OracleDriver. You do not need to register it if the driver jar file is in the "WEB-INF\lib" directory, if you are using Tomcat. Save this as test.jsp and put it in your web directory, and redeploy your web app folder in Tomcat manager:

<%@ 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
        }
    }
}

%>
Tom
  • 31