Java y MySQL
Desarrollo de aplicaciones de escritorio en Java y MySQL.
Para poder desarrollar la aplicaciones en esta unidad necesitamos
el siguiente software:
Conexion a la base de datos con phpmyadmin o con Workbench
Entorno de Java SDK
Base de datos MySQL
Admnistrador de base de datos: phpmyadmin (necesario instalar Apache y
MySQL, opcionalmente PHP, para windows se puede usar WAMP "Windows
Apache MySQL Php", en LINUX es LAMP "Linux Apache MySQL Php" ó Workbench
que no requiere el servidor Apache solo MySQL (mariaDB).
Ejemplo de conexion a MySQL:
Para ello usamos phpmyadmin para iniciar MySQL (Maria DB),



crearemos una bsase de datos llamada "Escuela"

con una tabla simple
que se llamara "persona"

con los siguientes campos:

Previsualizar el comando SQL:

Al ejecutar la secuencia de SQL:

Agregamos unos datos para la prueba que nos ocupa:
Usaremos la pestaña llamada Insertar:


Despúes de hacer un clic en el botón Continuar agregara 2 filas a la tabla:

Al terminar con el boton Continuar, usamos la pestaña examinar

Con esto podemos trabajar a manera de ejemplo.
Proseguimos con NetBeans para crear con un frame el ejemplo con un botón para la consulta de la base de datos.
Iniciamos co una nueva aplicacion en: Java---> Java Aplication

Le establecemos el nombre como SQL, y no creamos la clase principal (se retira la marca Create Main Class):

Al formarse el proyecto se vera de la siguiente forma:

En la sección Libraries (Bibliotecas)
realizamos un clic con el botón derecho, mostrando una lista de
elementos y seleccionamos Add Library ... buscamos
MySQL JDBC Driver que es el conector entre JAVA y MySQL, es
indispensable para poder leer, escribir información en MySQL.
(si se usa Eclipse debera de
agregarese el conector de forma manual, buscando el conector en
internet, y descargarlo, e indicar en donde se localizara para poder
usarlo)

Solo queda por hacer clic en Add Library... y se observara dfe la siguiente forma:

Se crea un paquete en Source package ... hacer un clic botón derecho y seleccionar New -> Java Package ...

Se le establece el nombre como app, hacemos clic en Finish....

Agregamos un Nuevo Formulario de JFrame. Form....

Lo que la llamaremos conexion

A lo cual genera el frame para agregar botones, cuadros, etc en el,
del lado derecho tenemos los controles para usar en el frame
usamos Button, se cambia el nombre del botón a Conexion, con Edit
Text, y cambaiamos la variable asociada al botón como btnConexion
(recuerdese la unidad anterior SWING):
Ahora realizamos la programacion para
que este botón al activarse se conecte con SQL, para entrar el código
generado se hace un doble clic en el botón que formamos y véremos el
código generado aqui, lo que se va a realizar es la programación para
indicar la base de datos el nombre de la tabla y los campos a usar,
esto no se puede realizar con el frame.
Agregamos la siguientes lineas en el constructor:
// constructor
public class conexion extends javax.swing.JFrame {
public static final String URL =
"jdbc:mysql://localhost:3306/Escuela"; // el lugar donde se tomaran los
datos jdbc (Java DataBase Connectivity)
// mysql Sistema de base de datos MySQL
// localhost:3306 el servidor local
accediendo por el puerto 3306
// Escuela el nombre de la base de Datos
public static final String USERNAME =
"root";
// el usuario de la base de datos
public static final String PASSWORD =
"xxxxxx";
// xxxxx contraseña para acceso a la BD y la tabla
Hacemos el método para la consulta de los datos a la base de datos,
habremos de explicar la linea que tiene el método
JOptionPane.showMessageDialog(null,"Conexion exitosa")
El método showMessageDialog tiene 3
sobrecargas del método, uno que recibe 2 parametros, otro de 4, y
otro de 5, y vamos
personalizando cada vez más nuestro mensaje, el primero que veremos es
el de dos parametros:
JOptionPane.showMessageDialog(null,"Operacion realizada correctamente")
El primer parámetro, representa el componente padre sobre el cual
el mensaje se mostrará, si nosotros no le enviamos ninguno, como en
este caso lo estamos haciendo, simplemente mostrará una ventana

Si le enviamos un componente, se colocará encima de el, sin
ninguna variación en el funcionamiento, el segundo parámetro
obviamente, es el mensaje que queremos observar, y listo, un mensaje
fácil de hacer, bien, ahora veamos otra cosa, el anterior fue el método
con dos parámetros, ahora bien, cuando utilizamos el método de cuatro
parámetros tenemos un poco más de personalización.
JOptionPane.showMessageDialog(null, "Mensaje dentro de la ventana",
"Mensaje en la barra de titulo", JOptionPane.WARNING_MESSAGE);
El funcionamiento de este método es un poco diferente, pero más útil:
Primer Parámetro: El componente padre sobre el cual se mostrará la ventana de dialogo.
Segundo Parámetro: El mensaje que se mostrará dentro de la ventana.
Tercer Parámetro: El mensaje que se mostrará en la barra de titulo.
Cuarto Parámetro: Una variable Int contenida por JOptionPane, que
representa el icono que se mostrará en la ventana, algunos de los
valores posibles son: INFORMATION_MESSAGE , WARNING_MESSAGE ,
QUESTION_MESSAGE , PLAIN_MESSAGE, ERROR_MESSAGE
En el caso anterior, el mensaje se vería de esta manera (hay un
mensaje en el titulo si no es visible aumenta el brillo del
monitor):

Al usar un WARNING_MESSAGE se presenta con un icono de alerta.
para más información de este método y mas en:
https://serprogramador.es/programando-mensajes-de-dialogo-en-java-parte-1/
Sigamos con la consulta:
public static Connection getConection()
{
Connection con = null; //iniciamos la variable con
//inicia la transaccion
try{
Class.forName("com.mysql.jbdc.Driver"); //uso conector java-sql
con = (Connection) DriverManager.getConnection(URL, USERNAME, PASSWORD); // realiza la conexion y se asigna a la variable con
// el (Connection) es un cast para realizar la conexion, revisar que es el cast
JOptionPane.showMessageDialog(null,"Conexion exitosa");
}catch(Exception e){
System.out.println(e);
} // este procedimiento es para la conexion
return null;
}// termina el procedimiento Connection
/**
* @param args the command line arguments
*/
public static void main(String args[]) {
Debemos importar una biblioteca, para este método, deberá estar despúes de package app, parte superior del programa :
package app;
import com.mysql.jdbc.Connection;
Ahora haremos el procedimieto para el
botón (al hacer clic en el, se ejecuta el codigo), antes dáremos una
introduccion al PreparedStatement
Cuando trabajamos con una base de
datos es posible que haya sentencias SQL que tengamos que ejecutar
varias veces durante la sesión, aunque sea con distintos parámetros.
Por ejemplo, durante una sesión con base de datos podemos querer
insertar varios registros en una tabla. Cada vez los datos que
insertamos serán distintos, pero la sentencia SQL será la misma: Un
INSERT sobre determinada tabla que será simpre igual, salvo los valores
concretos que queramos insertar.
Casi todas las bases de datos tienen previsto un mecanismo para que en
estos casos la ejecución de esas sentencias repetidas sea más rápida.
Si tenemos una tabla person con un id, una edad, un nombre, un apellido
y hacemos, por ejemplo, varios INSERT así
mysql> INSERT INTO person VALUES (null, 23, 'Pedro', 'Perez');
mysql> INSERT INTO person VALUES (null, 33, 'Rodrigo', 'Rodriquez');
En cada caso la base de datos deberá analizar la sentencia SQL,
comprobar que es correcta, convertir los datos al tipo adecuado (por
ejemplo, los enteros a int) y ejecutar la sentencia.
El mecanismo que preven las bases de datos para hacer más eficiente
este proceso es que le indiquemos, previamente, el tipo de sentencia
que vamos a usar, de forma que la base de datos la "precompila" y la
guarda en condiciones de ser ejecutada inmediatamente, sin necesidad de
analizarla en cada caso. Esto es lo que se conoce como una prepared
statement. En el caso de mysql, se haría de esta forma:
mysql> PREPARE INSERT FROM "INSERT INTO persona VALUES (null, ?, ?, ?)";
mysql> SET @edad=23;
mysql> SET @nombre='Pedro';
mysql> SET @apellido='Perez';
mysql> EXECUTE insertar USING @edad,@nombre,@apellido
mysql> SET @edad=33;
mysql> SET @nombre='Rodrigo';
mysql> SET @apellido='Rodriguez';
mysql> EXECUTE insertar USING @edad,@nombre,@apellido;
mysql> DEALLOCATE PREPARE insertar;
donde hemos preparado una
PreparedStatement de nombre insertar con la SQL del INSERT, en la que
hemos reemplazado los valores concretos por interrogantes. Vease que no
hemos puesto comillas entre los interrogantes. Hemos hecho dos
inserciones dando valores a unas variables @edad, @nombre y @apellido,
que son las que se usarán en el EXCECUTE de la PreparedStatement. Una
vez finalizadas las inserciones, avisamos a la base de datos que no
vamos a usar más esta PreparedStatement con un DEALLOCATE.
Si la base de datos soporta
PreparedStatement y el driver/conector que usemos para hablar con esa
base de datos desde java los soporta también, entonces podemos usar los
PreparedStatement desde java.
Si la base de datos no los soporta o el driver/conector no los soporta,
podemos desde java hacer el código igualmente. A la hora de codificar
podemos usar los PreparedStatement independientemente de que la base de
datos y/o el conector los soporten o no, pero no conseguiremos los
beneficios deseados. Aunque usemos PreparedStatement desde java, por
debajo acabarán traduciéndose a statement normal. Si quieres asegurarte
de conseguir todos los beneficios, debes verificar si tu base de datos
y el driver de conexión con ella soportan los prepared statement. En el
caso de MySQL, las versiones modernas lo hacen.
Lo primero de todo es establecer la conexión. En el caso de MySQL
debemos además poner un pequeño parámetro adicional para configurar el
driver para que use las prepared statement en el servidor. Este
parámetro es useServerPrepStmts=true, por lo que la cadena de conexión
completa sería
try {
Class.forName("com.mysql.jdbc.Driver");
// Es necesario useServerPrepStmts=true para que los PreparedStatement
// se hagan en el servidor de bd. Si no lo ponemos, funciona todo
// igual, pero los PreparedStatement se convertirán internamente a
// Statements.
Connection conexion = DriverManager.getConnection(
"jdbc:mysql://servidor/basedatos?useServerPrepStmts=true",
"usuario", "password");
...
} catch (Exception e) {
e.printStackTrace();
}
para mas información revise: http://www.chuidiang.org/java/mysql/PreparedStatement-java-mysql.php
private void
btnConexionActionPerformed(java.awt.event.ActionEvent evt)
{
try{
Connection con = null;
con = getConection(); //solicitamos el procedimiento de la conexion
PreparedStatement ps; // Es una declaración SQL se precompila y se almacena en un objeto PreparedStatement. Este objeto se puede usar para ejecutar
//
esta declaración de manera eficiente varias veces.
ResultSet
res;
//obtener los valores devueltos por la consulta
ps = con.prepareStatement("SELECT * FROM persona");
res = ps.executeQuery();
if(res.next()){ //solo extrae la primer fila
JOptionPane.showMessageDialog(null, res.getString("Nombre")+" "+
res.getString("Domicilio"));
} else {
JOptionPane.showMessageDialog(null,"No existen datos");
}
con.close();
}catch(Exception e){
System.out.println(e);
}
}
Excepciones, o sencillamente problemas.
En la programación siempre se producen
errores, más o menos graves, pero que hay que gestionar y tratar
correctamente. Por ello en java disponemos de un mecanismo consistente
en el uso de bloques try/catch/finally. La técnica básica consiste en
colocar las instrucciones que podrían provocar problemas dentro de un
bloque try, y colocar a continuación uno o más bloques catch, de tal
forma que si se provoca un error de un determinado tipo, lo que haremos
será saltar al bloque catch capaz de gestionar ese tipo de error
específico. El bloque catch contendrá el codigo necesario para
gestionar ese tipo específico de error. Suponiendo que no se hubiesen
provocado errores en el bloque try, nunca se ejecutarían los bloques
catch.
El resultado de este proceso es :
Y aqui todo el codigo del programa para realizar consultas en MySQL.
(recuerde que mucho del codigo aqui visto lo genera el frame tal como
se hace con la biblioteca Swing)
package app;
import com.mysql.jdbc.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import javax.swing.JOptionPane;
// constructor
public class conexion extends javax.swing.JFrame {
public static final String URL = "jdbc:mysql://localhost:3306/Escuela";
public static final String USERNAME = "root";
public static final String PASSWORD = "xxxxx";
public conexion() {
initComponents();
}
/**
* This method is called from within the constructor to initialize the form.
* WARNING: Do NOT modify this code. The content of this method is always
* regenerated by the Form Editor.
*/
@SuppressWarnings("unchecked")
// <editor-fold defaultstate="collapsed"
desc="Generated
Code">
private void initComponents() {
btnConexion = new javax.swing.JButton();
setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
btnConexion.setText("Conexion");
btnConexion.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
btnConexionActionPerformed(evt);
}
});
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
getContentPane().setLayout(layout);
layout.setHorizontalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addGap(153, 153, 153)
.addComponent(btnConexion)
.addContainerGap(172, Short.MAX_VALUE))
);
layout.setVerticalGroup(
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
.addGroup(layout.createSequentialGroup()
.addGap(118, 118, 118)
.addComponent(btnConexion)
.addContainerGap(154, Short.MAX_VALUE))
);
pack();
}//
</editor-fold>
private void
btnConexionActionPerformed(java.awt.event.ActionEvent evt)
{
try{
Connection con = null;
con = getConection();
PreparedStatement ps;
ResultSet res;
ps = con.prepareStatement("SELECT * FROM persona");
res = ps.executeQuery();
if(res.next()){ //solo extrae la primer fila
JOptionPane.showMessageDialog(null, res.getString("Nombre")+" "+
res.getString("Domicilio"));
} else {
JOptionPane.showMessageDialog(null,"No existen datos");
}
con.close();
}catch(Exception e){
System.out.println(e);
}
}
public static Connection getConection()
{
Connection con = null; //iniciamos la variable con.
try{
Class.forName("com.mysql.jdbc.Driver"); //uso conector java-sql
con =
(Connection) DriverManager.getConnection(URL, USERNAME, PASSWORD); //
realiza la conexion y se asigna a la variable con
// el
(Connection) es un cast para realizar la conexion, revisar que es el
cast
JOptionPane.showMessageDialog(null,"Conexion exitosa");
}catch(Exception e){
System.out.println(e);
} // este procedimiento es para la conexion
return con;
}// termina el procedimiento Connection
public static void main(String args[]) {
/* Set the Nimbus look and feel */
//<editor-fold
defaultstate="collapsed" desc=" Look and feel setting code (optional)
">
/* If Nimbus (introduced in
Java SE 6) is not available, stay with the default look and feel.
* For details see
http://download.oracle.com/javase/tutorial/uiswing/lookandfeel/plaf.html
*/
try {
for
(javax.swing.UIManager.LookAndFeelInfo info :
javax.swing.UIManager.getInstalledLookAndFeels()) {
if ("Nimbus".equals(info.getName())) {
javax.swing.UIManager.setLookAndFeel(info.getClassName());
break;
}
}
} catch (ClassNotFoundException ex) {
java.util.logging.Logger.getLogger(conexion.class.getName()).log(java.util.logging.Level.SEVERE,
null, ex);
} catch (InstantiationException ex) {
java.util.logging.Logger.getLogger(conexion.class.getName()).log(java.util.logging.Level.SEVERE,
null, ex);
} catch (IllegalAccessException ex) {
java.util.logging.Logger.getLogger(conexion.class.getName()).log(java.util.logging.Level.SEVERE,
null, ex);
} catch (javax.swing.UnsupportedLookAndFeelException ex) {
java.util.logging.Logger.getLogger(conexion.class.getName()).log(java.util.logging.Level.SEVERE,
null, ex);
}
//</editor-fold>
/* Create and display the form */
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
new conexion().setVisible(true);
}
});
}
// Variables declaration - do not
modify
private javax.swing.JButton btnConexion;
// End of variables
declaration
}
CRUD
Create - Crear
Read - Leer
Update - Actualizar
Delete - Eliminar
Para realizar este
procedimiento modificaremos la base de datos que habíamos creado
anteriormente, la base de datos llamada Escuela, y agregaremos un
campo mas a la tabla persona, que es campo llamado clave varchar(10)
y sera debajo del campo Id, véase las opciones a usar.
Vemos que hemos colocado el campo clave en su primer letra en
minusculas, prara demostrar lo practico de phpmyadmin cambaire de
minuscula a mayuscula y despúes agregaremos directamente a la tabla el
dato, con el mismo phpmyadmin:
Realizamos un nuevo proyecto, donde crearemos un formulario usando
JFrame, y tomando del lado derecho en la seccion Swing Controls
En el área formada de JFrame agregaremos una etiqueta
para identificar el campo que esta en la tabla de la base de datos
Escuela.

Del lado derecho seleccionamos Label y lo pasamos
al área de JFrame editamos el texto, le colocamos el texto Clave:
después agregamos una caja de texto con el control Text Field
editamos el nombre de la variable a txtClave para relacionarla con el
campo de la base de datos, se demostrara para el primer elemento que
es el campo Clave, los siguientes campos los realizaras tu.

Ahora pdemos realizar un cambio, en Genero lo haremos con un ComboBox:
Primero marque el cuadro al lado derecho de la etiqueta Genero, y
borrela con la tecla Supr que hemos formado, seleccionamos el control
Swing de ComboBox, revise el lado derecho de la siguente imagen:

Arrastre el control al la parte derecha del la etiqueta Genero:

Hagamos la secuencia para los items:
Nota: si por alguna accion
equivocada borramos la paleta del aado derecho o cualquier ventana,
podemos restablecer las totalidad de las ventanas usando la opcion
Window -> Reset Windows, con ello regresan todas la ventanas del
área de trabajo que estan por defecto.
Agregar botones para control de las acciones en la base de datos crearemos los botones: Guarda Modifica Eliminar Limpiar
Agregaremos mas botones uno para la busqueda de los datos de la
tabla, y un cuadro de texto para observar el Id, este es automatico y
no es posible cambiarlo solo será mostrado:
Para continuar y comenzar la programacion necesitamos agregar el
proceso de conexion a la base de datos, usamos las mismas instrucciones
que el proyecto anterior, para pasar al codigo y viceversa usamos los
paneles de Source y Design:

lo que esta marcado en rojo es el codigo a agregar al codigo del actual proyecto

package app;
import com.mysql.jdbc.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import javax.swing.JOptionPane;
import java.sql.Date;
// constructor
public class conexion extends javax.swing.JFrame {
public static final String URL = "jdbc:mysql://localhost:3306/Escuela";
public static final String USERNAME = "root";
public static final String PASSWORD = "xxxx";
public conexion() {
initComponents();
}

----------------------------------------------------------- (las
siguientes lineas debéran estar antes de main()
----------------------------------------------------------
public static Connection getConection()
{
Connection con = null; //iniciamos la variable con inicia la transaccion
try{
Class.forName("com.mysql.jbdc.Driver"); //uso conector java-sql
con = (Connection) DriverManager.getConnection(URL, USERNAME, PASSWORD); // realiza la conexion y se asigna a la variable con
// el (Connection) es un cast para realizar la conexion, revisar que es el cast
JOptionPane.showMessageDialog(null,"Conexion exitosa");
}catch(Exception e){
System.out.println(e);
} // este procedimiento es para la conexion
return null;
}// termina el procedimiento Connection
/**
* @param args the command line arguments
*/
Para activar los codigos de cada botón realiza un doble clic sobre
el botón en el diseño, con ello se mostraran en el panel del lado
izquierdo.
Pasamos al codigo del botón Guardar:
Para realizar esto, es buscar en todo el codigo y localizar la
instrucción del botón, y realizarlo con el panel del lado izquierdo
ubicando el procedimiento:
Para el efecto que requerimos de agregar datos es necesario indicar
como se va a realizar la acción de Guardar (vease el codigo en rojo)
public static final String URL = "jdbc:mysql://localhost:3306/Escuela";
public static final String USERNAME = "root";
public static final String PASSWORD = "uss1707";
PreparedStatement ps; // preparar la instruccion para insertar datos
ResultSet rs; // la variable recibe el string de los campos de sql

Ahora realizamos el codigo para el botón Guarda
private void
btnGuardaActionPerformed(java.awt.event.ActionEvent evt)
{
Connection con = null; //asegura que no hay valor previo
try{ //procedimiento para evaluar si se realiza la operacion
con = getConection();
ps =
con.prepareStatement("INSERT INTO persona
(Clave,Nombre,Domicilio,Telefono,Correo_electronico,Fecha_nacimiento,Genero)
VALUES (?,?,?,?,?,?,?)");
// el string establece los campos a actualizar en la tabla, y ???? son
los valores a recibir del formulario adicionalmente evita la inyeccion
a sql
ps.setString(1,txtClave.getText());
ps.setString(2,txtNombre.getText());
ps.setString(3,txtDomicilio.getText());
ps.setString(4,txtTelefono.getText());
ps.setString(5,txtCorreo_electronico.getText());
ps.setDate(6,Date.valueOf(txtFecha_nacimiento.getText())); //para la fecha se usa import java.sql.Date;
ps.setString(7,cbxGenero.getSelectedItem().toString()); // es la forma de tomar el item del combo box
int rs = ps.executeUpdate(); //executeUpdate() regresa un booleano 1 si actualizo 0 no actualizo
if(rs > 0){
JOptionPane.showMessageDialog(null, "Persona agregada");
}else{
JOptionPane.showMessageDialog(null, "Error Persona no agregada");
}
con.close();
} catch(Exception e){
System.err.println(e);
}
}
Formemos el codigo para limpiar los campos (cajas de datos) se agrega despúes de public static Connection getConection()

private void limpiarCajas(){
txtClave.setText(null);
txtNombre.setText(null);
txtDomicilio.setText(null);
txtTelefono.setText(null);
txtCorreo_electronico.setText(null);
txtFecha_nacimiento.setText(null);
cbxGenero.setSelectedIndex(0);
}
Este procedimiento puede ser incluido cuando se guardan los datos en la tabla para esperar mas datos.
int rs = ps.executeUpdate(); //executeUpdate() regresa un booleano 1 si actualizo 0 no actualizo
if(rs > 0){
JOptionPane.showMessageDialog(null, "Persona agregada");
limpiarCajas();
}else{
JOptionPane.showMessageDialog(null, "Error Persona no agregada");
limpiarCajas();
}
con.close();
El proceso se puede ver aqui: