Sei sulla pagina 1di 5

Viscent’s Blog- AJAX JAVASCRIPT JAVA ARCHITECTURE

« Java and Design Patterns-Preface

Java and Design Patterns-JDBC


Although writing generic JDBC code is tedious with its boilerplate code.The
JDBC itself is well-designed (architected).This article covers the application
of below patterns in the JDBC:

» Factory Method Pattern


» Iterator Pattern
» Strategy Pattern
» Bridge Pattern

JDBC Design Goals and Architecture


One of the design goals of the JDBC is “Offer vendor-neutral access to
common features”, that means it allows your application to talk with multiple
database systems in the same way and when there is a need to switch one
database system to another, there is no need to change a lot of your code!
How JDBC archives this? This is where the patterns listed above come into
play.
JDBC and Various Design Patterns
Let’s inspect the architecture of the JDBC:

(Figure 1)
From the above figure, we can see that application code talks to databases
From the above figure, we can see that application code talks to databases
via JDBC API.This API is the key to satisfy JDBC’s design goals. But, from
the API doc we can see that, this API is only a set of interfaces:

(Figure 2)
Interface is only an abstraction, it cannot do anything. So there must be
something that really do the job (talk to database)—it’s the JDBC Driver that
does this behind the scene.When you are talking to Oracle, the Oracle JDBC
Driver is used, when talking to DB2, the DB2 JDBC Driver used.Well, another
question emerges, how the API and the JDBC Driver collaborates, since our
application code is talking to the JDBC API? This is done by employing the
Factory Pattern.Let’s review a typical usage of JDBC, we will understand this
well.
Suppose we are talking to Oracle.First we obtain a JDBC connection via:

1. Class.forName(“oracle.jdbc.driver.OracleDriver”);

2. Connection
cnn=DriverManager.getConnection(“jdbc:oracle:thin:@localhost:1521
:viscent”,

3. “userName”, “password”);

java.sql.Connection is an interface, so the connection we get is actually


some concrete class that implements java.sql.Connection,but it is not
directly exposed to our application code, we
still talk to java.sql.Connection only.For now, we can view the getConnection
method as a Factory method.
Let’s recall the intent of the Factory Method Pattern:

Define an interface for creating an object, but let subclasses


decide which class to instantiate. Factory Method lets a class
defer instantiation to subclasses.
S o , getConnection is the interface (method) for creating an instance of
database connection (javax.sql.Connection, the ‘product’).
Then, we will issue SQL commands with the obtained connection:

1. String sql="SELECT id,name,tel FROM contacts";

2. Statement stmt=null;

3. ResultSet rs=null;

4. try {

5. stmt = cnn.createStatement();

6. rs=stmt.executeQuery(sql);

7. } catch (SQLException e) {

8. e.printStackTrace();

9. }

Note the way we get a Statement, it is an interface, and we don’t have get it
with new keyword,
instead, the c reateStatement of java.sql.Connection is called.The
createStatement is also a Factory method with the Statement as its
product.Similarly, if we want to issue prepared SQL or to call a stored
procedure, we will call prepareStatement a n d prepareCall, then we get
PreparedStatement and CallableStatement(again they are intefaces!)—again,
Factory method does the job!
Now, let’s review the way we deal with the recordset.

1. try {

2. while(rs.next()){

3. int id=rs.getInt(0);

4. String name=rs.getString(1);

5. //…

6. }

7. } catch (SQLException e) {

8. e.printStackTrace();

9. }

We loop through the resultset with the call to next, this is where the Iterator
pattern comes into play. Recall the intent of this pattern:

Provide a way to access the elements of an aggregate object


sequentially without exposing its underlying representation.

The ResultSet (interface) wraps a set of records (the ‘aggregate object’), but
we don’t need to care about what (concrete classes) really they are, as long
as calling to next allows us to go forward from one record to another. In this
way, we deal with recordset using the interface ResultSet without knowing
what concrete class it is.Hence the abstraction (ResultSet) and its
implementation (part of JDBC Driver that implements the ResultSet interface)
are decoupled.
From above steps, we can see that from the beginning to end the application
code talks only to the JDBC API. And this API makes heavy use of the
Factory Method Pattern.We don’t talk to JDBC drivers directly, and it looks
as if they don’t exist at all.This is really important to achieve the goal “Offer
vendor-neutral access to common features”.Because JDBC drivers are
vendor-specific, application code should not directly talk to them.However, as
mentioned previously, JDBC drivers do the real job to talk to database.The
question is how those drivers play their role?This is where the Bridge Pattern
comes into play.
Previously, we view the getConnection method of DriverManager as a
Factory method.
Factory method.
This is actually an outward view. Internally, DriverManager itself doesn’t
know how to create a database connection at all. Further more it should not
know how to create one at all for the sake of maintainability and extensibility
of the JDBC:
There are many database systems the JDBC should support at present, and
in the future, it may need support other database systems, if the knowledge
of creating a database connection is placed in DriverManager,it might need to
be changed frequently which is not desirable.That’s why there are JDBC
Drivers. The JDBC Driver is pluggable, when a JDBC Driver class is loaded,
it will register an instance of the Driver with the DriverManager.When we
asking DriverManager for a connection (by calling getConnection),
DriverManager will loop through all Drivers register with it, and call
acceptsURL on them,if the return is true, DriverManager will understand that
current driver are able to handle current connection url, then it will call
connect on the selected Driver to get a connection and return
it to our application code.
In this way, if we need JDBC to support a new database system, there is no
need to change JDBC itself at all, only need to create a new Driver for the
new database system! That’s why I call the Drivers are pluggable. We will
examine how JDBC achieve this pluggability.

(Figure 3)
From figure3 we can see that:
This is actually an example of the Bridge Pattern. Let’s review the intent of
this pattern:

Decouple an abstraction from its implementation so that the two


can vary independently.

In this case, DriverManager is actually the abstraction for creating a


database connection via its getConnection method. However, DriverManager
itself doesn’t really know how to create a connection. It will ask its
implementations (Drivers) to create one and return it to its client.The JDBC
Drivers is actually implementations for creating a database connection in this
case.
The process of deciding which Driver can handle current connection url
involves another commonly used design pattern—the Strategy Pattern.
The acceptsURL method of Driver encapsulates the knowledge of whether a
specific Driver is able to handle specified connection url or not, and hence
allows DriverManager need not to know what exact the Driver is, whether it is
an OracleDriver or a DB2Driver.This leads to loose coupling between the
DriverManager and Drivers, because it is sufficient for Drivermanger talking
to JDBC Drivers with the interface java.sql.Driver only without caring about
its concrete class.
Conclusion
The JDBC applies a set of design patterns to achieve its design goals,
The JDBC applies a set of design patterns to achieve its design goals,
leading to an loose coupling and open-to-extend API that supports multiple
database systems.

Tags : Bridge Pattern, design patterns, Factory Method, Iterator Pattern,


Java, jdbc, Strategy Pattern

This entry was posted on Saturday, August 15th, 2009 at 6:33 am and is filed under
Desgin/Architecture, Java. You can follow any responses to this entry through the RSS
2.0 feed. You can leave a response, or trackback from your own site.

Leave a Reply
Name (required)

Mail (will not be published) (required)

Website

Submit Comment

Powered by WordPress
Entries (RSS) and Comments (RSS).

Search Engine Submission - AddMe

Potrebbero piacerti anche