Sei sulla pagina 1di 48

JDBC: Java Database Connectivity

Tecnologias para plataformas abiertas


Ing. Julio Cesar Meza Garca 1

Agenda
Conceptos de la tecnologa JDBC Drivers JDBC Siete pasos bsicos para usar JDBC Obteniendo datos de un ResultSet Declaraciones Excepciones SQL Transacciones
Ing. Julio Cesar Meza Garca 2

Introduccin a JDBC
Son libreras estndar para acceso a bases de datos relacionales
El API JDBC estandariza algunas funciones:
Como se realiza la conexin a la base de datos La ejecucin de consultas La creacin de declaraciones pre-compiladas La estructura de los resultados de una consulta
Filas, columnas Metadatos

El API no estandariza la sintaxis SQL Las clases JDBC estn en el paquete java.sql
Ing. Julio Cesar Meza Garca 3

JDBC no tiene SQL embebido

Drivers JDBC
JDBC consta de dos partes:
El API JDBC, 100% basado en Java El DriverManager, especifico de cada proveedor y que proporciona la comunicacin real con la base de datos.
La traduccin al formato del proveedor es realizada en el cliente El driver se instala unicamente en el cliente.
Aplicacin Java

DriverManager API JDBC Puente JDBC-ODBC Driver JDBC del proveedor

Driver ODBC del proveedor

DBMS

DBMS

Ing. Julio Cesar Meza Garca

Tipos de datos JDBC


Tipo JDBC Tipo Java Tipo JDBC Tipo Java

BIT
TINYINT SMALLINT INTEGER BIGINT REAL FLOAT DOUBLE BINARY VARBINARY LONGVARBINARY

boolean
byte short int long float double byte[]

NUMERIC DECIMAL
DATE TIME TIMESTAMP

BigDecimal
java.sql.Date java.sql.Timestamp

CLOB
BLOB ARRAY STRUCT

Clob
Blob Array Struct

REF String

Ref

CHAR VARCHAR LONGVARCHAR

Ing. Julio Cesar Meza Garca

Siete pasos bsicos en el uso de JDBC


Cargar el Driver Definir el URL de conexin Establecer la conexin Crear el objeto Statement Ejecutar la consulta Procesar los resultados Cerrar la conexin
Ing. Julio Cesar Meza Garca 6

JDBC: Paso a paso


1. Cargar el Driver
Class.forName("org.postgresql.Driver");

2. Definir el URL de conexin


String URL = "jdbc:postgresql://labinfo3/jmezag";

Ing. Julio Cesar Meza Garca

JDBC: Paso a paso


3. Establecer la conexin
String USER = "julio"; String PASS = ""; Connection con = DriverManager.getConnection(URL,USER,PASS);

Opcionalmente puede obtener informacin acerca de la base de datos

DatabaseMetaData dbMetaData = con.getMetaData(); String dbmsName = dbMetaData.getDatabaseProductName(); String dbmsVersion = dbMetaData.getDatabaseVersion();

Ing. Julio Cesar Meza Garca

JDBC: Paso a paso


4. Crear el objeto Statement
Statement stmt = con.createStatement();

Ing. Julio Cesar Meza Garca

JDBC: Paso a paso


5. Ejecutar una consulta
String query = "select * from authors"; ResultSet rs = stmt.executeQuery(query);

Para modificar la base de datos (INSERT, UPDATE o DELETE), utilice el mtodo

executeUpdate
Para establecer el tiempo de espera mximo en la ejecucin de una consulta se utiliza el mtodo

setQueryTimeout
Ing. Julio Cesar Meza Garca 10

JDBC: Paso a paso


6. Procesar el resultado
while ( rs.next() ) { System.out.println( rs.getString(1) + " " + rs.getString(2) + " " + rs.getString(3) ); }

Al abrir el ResultSet la posicin del cursor es antes de la primer tupla

Ing. Julio Cesar Meza Garca

11

JDBC: Paso a paso


7. Cerrar la conexin
con.close();

Ing. Julio Cesar Meza Garca

12

El objeto Statement
Que es?
El objeto Statement se utiliza para enviar sentencias SQL al DBMS

Existen tres tipos de objetos Statement


Statement
Para ejecutar sentencias SQL simples

PreparedStatement
Para ejecutar sentencias SQL precompiladas con pase de parmetros

CallableStatement
Para ejecutar procedimientos almacenados
Ing. Julio Cesar Meza Garca 13

Mtodos del objeto Statement


executeQuery
Ejecuta una sentencia SQL y regresa los datos en una tabla (ResultSet) El ResultSet puede estar vaco, pero nunca ser nulo

executeUpdate
Se utiliza para ejecutar sentencias SQL (INSERT, UPDATE y DELETE) Regresa un valor numrico que indica el nmero de filas afectadas Soporta sentencias DDL (CREATE TABLE, ALTER TABLE, etc)
Ing. Julio Cesar Meza Garca 14

Mtodos del objeto Statement


(continua)

execute
Mtodo genrico utilizado para ejecutar procedimientos almacenados o declaraciones precompiladas. Raramente usado (puede retornar mltiples ResultSet) Puede regresar o no un ResultSet. El mtodo getResultSet indica si existe o no un ResulSet (si el resultado es true pueden existir varios sets de resultados)

getMaxRows/setMaxRows
Determina el nmero mximo de filas que un ResultSet puede tener. Si el nmero de filas es ilimitado regresa 0
Ing. Julio Cesar Meza Garca 15

Mtodos del objeto Statement


(continua) getQueryTimeOut/setQueryTimeOut
Especifica el tiempo que el driver debe esperar para que se ejecute la sentencia SQL antes de regresar una excepcin SQLExcetion.

Ing. Julio Cesar Meza Garca

16

PreparedStatement
Tip
Si va ha ejecutar mltiples consultas similares, puede utilizar el objeto PreparedStatement y utilizar parmetros

El objeto PreparedStatement dispone de los mismos mtodos que el objeto Statement, solo que estos se ejecutan sin parmetros:
executeQuery() executeUpdate() execute()
Ing. Julio Cesar Meza Garca 17

Mtodos de PreparedStatement
setXxx
Escribe valor del parmetro indicado (?) en la sentencia SQL

clearParameters
Limpia todos los parmetros de la declaracin

Ing. Julio Cesar Meza Garca

18

Un ejemplo con el objeto PreparedStatement


Connection conn = DriverManager.getConnection(URL, USUARIO, CLAVE); String QUERY = "select * from empleados where departamento = ?" ; PreparedStatement st = conn.prepareStatement(QUERY);

st.setInt(1, 2); ResultSet rs = st.executeQuery();

Ing. Julio Cesar Meza Garca

19

CallableStatement
Tip
Permite ejecutar procedimientos almacenados en el DBMS

Ventajas
Los errores de sintaxis son detectados en tiempo de compilacin Los procedimientos almacenados se ejecutan ms rpido que las sentencias SQL dinmicas El programador solo requiere conocer los parmetros de E/S del procedimiento almacenado No se requiere conocer la estructura de las tablas o los detalles del procedimiento almacenado.
Ing. Julio Cesar Meza Garca 20

CallableStatement
(continua)

Sintaxis
Procedimientos sin parmetros
{ call procedure_name }

Procedimientos solo con parmetros de entrada


{ call procedure_name(?,?,,?) }

Procedimientos con parmetros de E/S


{ ? = call proccure_name(?,?,,?) }
String queryCall = "{call prodecure(?,?)}"; CallableStatement stmt = con.prepareCall(queryCall);
Ing. Julio Cesar Meza Garca 21

CallableStatement
(continua)

Parmetros de salida
Registre el tipo de dato JDBC de cada parmetro utilizando el mtodo registerOutParameter antes de llamar al mtodo execute
stmt.registerOutParameter(n,Types.Float);

Utilice el mtodo getXxx para acceder los resultados que regresa el procedimiento almacenado. Ing. Julio Cesar Meza Garca

22

Un ejemplo con CallableStatement


String proc = "{? = call esUsuarioValido(?,?)}"; CallableStatement stmt = con.prepareCall(proc); stmt.setString(2,usuario); stmt.setString(3,password); stmt.registerOutParameter(1,Types.BIT); stmt.execute(); if (stmt.getBoolean(1)) { // Usuario y contrasea valido ... } else { // Usuario y/o contrasea no validos ... }
Ing. Julio Cesar Meza Garca 23

ResultSet
Qu es?
Un ResultSet contiene los resultados de una consulta SQL
Representado por una tabla con filas y columnas En JDBC 1.0 nicamente puede avanzar utilizando el mtodo next()

Mtodos disponibles
Todos los mtodos pueden lanzar una excepcin de tipo SQLException

close
Libera los recursos JDBC y de la base de datos El ResultSet es cerrado automticamente cuando con el objeto Statement asociado se ejecuta una nueva consulta.
Ing. Julio Cesar Meza Garca 24

ResultSet
Mtodos disponibles
getMetaDataObject
Regresa un objeto ResultSetMetaData que contiene informacin acerca de las columnas en el ResultSet

next
Intenta mover a la siguiente fila en el ResultSet Si la operacin es exitosa regresa true; el caso contrario, false
La primera llamada posiciona el cursor en la primera fila Su llamada limpia la cadena SQLWarning

getWarning
Regresa el primer SQLWarning o nulo si no han ocurrido eventos.
Ing. Julio Cesar Meza Garca 25

ResultSet
Mtodos disponibles
findColumn
Regresa un valor numrico correspondiente a la posicin de la columna Los nmeros de columna en el ResultSet pueden no corresponder con los de la base de datos

getXxx
Retorna el valor de la columna especificada (por nombre o por ndice) como un tipo de datos Xxx Retorna null si el valor es un SQL NULL Los tipos de datos Xxx validos son:
Double, Byte, Int, Date, String, Float, Short, Long, Time, Object
Ing. Julio Cesar Meza Garca 26

ResultSet
Mtodos disponibles
wasNull
Se utiliza para verificar si la ultima llamada getXxx regreso un SQL NULL

Ing. Julio Cesar Meza Garca

27

Uso de cursores
Por defecto, el Driver recupera todos los resultados al momento de ejecutar la consulta. Para consultas que regresan grandes cantidades de datos esto puede ser un serio inconveniente. Con el uso de cursores podemos controlar la cantidad de registros que sern "cacheados" por el cliente. Ventajas:
Solo se transfieren al cliente los bloques que se requieren.
Ing. Julio Cesar Meza Garca 28

Desventajas de los cursores


Los cursores son soportados nicamente por las versiones de postgresql 7.4 o posteriores. No soporta el modo autocommit
El servidor cierra los cursores al finalizar las transacciones, en modo autocommit el cursor seria cerrado antes de poder leerlo.

La declaracin debe ser creada con un ResultSet de tipo ResultSet.TYPE_FORWARD_ONLY


Ing. Julio Cesar Meza Garca 29

Aplicacin de un cursor
Connection conn = DriverManager.getConnection(URL,USUARIO,CLAVE); // poner autocommit en off conn.setAutoCommit(false); Statement st = conn.createStatement(); // habilitar el cursor st.setFetchSize(50); ResultSet rs = st.executeQuery("select * from empleados"); while (rs.next()) { out.print("a row was returned.<br>"); }
Ing. Julio Cesar Meza Garca 30

Uso de los MetaData


Idea
De un ResultSet (el tipo de objeto creado con executeQuery), obtenga un objeto ResultSetMetaData Use este objeto para obtener el numero, nombres y tipos de datos de las columnas del ResultSet

Con el objeto ResultSetMetaData puede contestar a las siguientes preguntas:


Cuantas columnas hay en mi ResultSet? Cual es el nombre de la columna 2? Los nombres de las columnas son sensibles a minsculas/maysculas? Cul es el tipo de datos de una columna?
Ing. Julio Cesar Meza Garca 31

Mtodos MetaData
getColumnCount
Regresa el nmero de columnas del ResultSet.

getColumnDisplaySize
Regresa el tamao mximo de una columna de tipo carcter.

getColumnName/getColumnLabel
getColumnName regresa el nombre de la columna en la base de datos getColumnLabel regresa el nombre de la columna en el ResultSet

getColumnType
Regresa el tipo de dato de la columna
Ing. Julio Cesar Meza Garca 32

Mtodos MetaData
isNullable
Indica si la columna puede almacenar valores nulos Puede compara el valor retornado con las siguientes constantes del ResultSet: columnNoNulls, columnNullable, columnNullableUnknown

isSearchable
Indica si la columna puede ser utilizada en una clusula where

isReadOnly/isWritable
isReadOnly indica si la columna es definitivamente de solo lectura. isWritable indica si la columna puede ser accesada para escritura,
Ing. Julio Cesar Meza Garca 33

Mtodos MetaData
getColumnTypeName
Regresa una cadena con el nombre del tipo de dato de la columna

Ing. Julio Cesar Meza Garca

34

Ejemplo del uso de MetaData


Connection con = DriverManager.getConnection( url, username, password); // Obtiene informacin del DBMS DatabaseMetaData dbMetaData = con.getMetaData(); String dbmsName = dbMetaData.getDatabaseProductName(); String dbmsVersion = dbMetaData.getDatabaseProductVersion(); out.print( "DBMS= " + dbmsName + "<br>" ); out.print( "Versin= " + dbmsVersion + "<br>" ); ...
Ing. Julio Cesar Meza Garca 35

Ejemplo del uso de MetaData


(continua)
Statement stmt = con.createStatement(); String query = "SELECT * FROM empleados"; ResultSet rs = stmt.executeQuery(query); // Obtiene la MetaData del ResultSet ResultSetMetaData rsMetaData = rs.getMetaData(); int columnas = rsMetaData.getColumnCount(); // Imprime las etiquetas de las columnas for (int i=1; i<columnas+1; i++) { out.print( rsMetaData.getColumnName(i) ); out.print( "<br>" ); } out.print( "<br>" );
Ing. Julio Cesar Meza Garca 36

Manejo de errores
HTTP/1.1 500 Internal Server Error cuando el atributo isErrorPage="true"
IE muestra una pgina de error interno cuando la respuesta del servidor es menor a 512 bytes.

Solucin:
Crear el objeto exception a partir del atributo javax.servlet.jsp.jspException
El atributo vara con otras versiones de tomcat.

Ing. Julio Cesar Meza Garca

37

Manejo de errores encadenados


Cada uno de los mtodos JDBC puede generar una excepcin SQLException si ocurre un error de acceso a los datos Si ocurre ms de un error, estas son encadenadas. Una excepcin SQL contiene:
La descripcin del error, getMessage El SQLState (Especificacin Open Group SQL), identificando la excepcin, getSQLState El cdigo de error especifico del producto, getErrorCode Para acceder la siguiente excepcin SQLException se utiliza getNextExeption
Ing. Julio Cesar Meza Garca 38

Ejemplo de SQLException
try { // Declaraciones JDBC } catch (SQLException e) { while (e != null) { System.out.println("Mensaje: "+e.getMessage()); System.out.println("SQLState: "+e.getSQLState()); System.out.println("Error: "+e.getErrorCode()); e = e.getNextException(); } }

Ing. Julio Cesar Meza Garca

39

Transacciones
Por defecto, una vez que una declaracin es ejecutada, los cambios son automticamente asentados. Para habilitar el uso de transacciones se debe desactivar la caracterstica autocommit connection.setAutoCommit(false)

Llamar el mtodo commit para hacer permanentes las modificaciones Llamar el mtodo rollback para deshacer los cambios si un error se presenta.
Ing. Julio Cesar Meza Garca 40

Transacciones: Ejemplo
Connection connection = DriverManager.getConnection(url, username, passwd); connection.setAutoCommit(false); try { statement.executeUpdate(...); statement.executeUpdate(...); ... } catch (Exception e) { try { connection.rollback(); } catch (SQLException sqle) { // reporte del problema } } finally { try { connection.commit(); connection.close(); } catch (SQLException sqle) { } Ing. Julio Cesar Meza Garca }

41

Mtodos para manejo de transacciones


getAutoCommit/setAutoCommit
Por defecto, una conexin es establecida en autocommit Recupera/establece el modo autocommit

commit
Hace permanentes todos los cambios desde el ltimo commit Los bloqueos a la base de datos hechos desde esta conexin son liberados.

rollback
Deshace los cambios ocurridos desde el ltimo commit. Los bloqueos a la base de datos hechos desde esta conexin son liberados.
Ing. Julio Cesar Meza Garca 42

El problema de la concurrencia
El acceso a aplicaciones web frecuentemente enfrenta problemas de concurrencia. Cuando se incrementa el nmero de usuarios, es muy probable que se inicie una nueva peticin antes de terminar la que esta en proceso. Normalmente cada usuario genera una (o ms conexiones directamente al DBMS), abrindola y cerrndola con cada peticin.

Ing. Julio Cesar Meza Garca

43

El "pool" de conexiones
Un pool de conexiones crea y mantiene un grupo de conexiones al DBMS.
Las conexiones se realizan con un URL nico.

Tomcat abre las conexiones al iniciar la aplicacin Cuando una peticin requiere una conexin simplemente la toma del pool Cuando la peticin termina, la conexin regresa al pool y puede ser utilizada por otra peticin.
Ing. Julio Cesar Meza Garca 44

Configuracin de un "pool" de conexiones


server.xml
<Context path="/path" docBase="c:/docBase" crossContext="true" reloadable="true" debug="1"> <Resource name="jdbc/postgres" auth="Container" type="javax.sql.DataSource" driverClassName="org.postgresql.Driver" url="jdbc:postgresql://localhost:5432/julio" username="username" password="password" maxActive="20" maxIdle="10" maxWait="-1"/> Ing. Julio Cesar Meza Garca </Context>

45

Configuracin de un "pool" de conexiones


web.xml
<resource-ref> <description>postgreSQL Datasource example</description> <res-ref-name>jdbc/postgres</res-ref-name> <res-type>javax.sql.DataSource</res-type> <res-auth>Container</res-auth> </resource-ref>

Ing. Julio Cesar Meza Garca

46

Uso del "pool" de conexiones


<%@ page import="javax.naming.*,javax.sql.*" %> <% // Apertura de la conexion InitialContext cxt = new InitialContext(); Context env = (Context)cxt.lookup("java:/comp/env"); DataSource ds = (DataSource)env.lookup("jdbc/postgres"); Connection conn = ds.getConnection(); ... ...
Ing. Julio Cesar Meza Garca 47

Resumen
Conexin a un DBMS y ejecucin de sentencias SQL Los MetaDataResultSet proporcionan detalles acerca de un ResultSet Puede incrementar el rendimiento utilizando declaraciones precompiladas Debe asegurarse de manejar adecuadamente los valores NULL regresados por los mtodos getXxx Por default las conexiones son abiertas en el modo

autocommit

Las excepciones SQL mltiples pueden formar cadenas

Ing. Julio Cesar Meza Garca

48

Potrebbero piacerti anche