JDBC CRUD usando servlets y pool de conexiones (apache dbcp2)
JDBC CRUD usando servlets y pool de conexiones (apache dbcp2)
Proyecto en funcionamiento para el modelo de personas:
Estructura del proyecto:
Implementacion de los operaciones usando transacciones PersonaDaoImpl:
package sga.eis.dao;
import sga.eis.dto.*;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import java.util.ArrayList;
public class PersonaDaoImpl implements PersonaDao{
private Connection conn = null;
//Utilizamos el patron singleton, solo existen un objeto de tipo UsuarioService en Memoria
private static PersonaDao personaDaoInstance;
//Creamos una nueva y unica instancia si es que no existe
public static PersonaDao getInstance() {
if(personaDaoInstance == null) {
personaDaoInstance = new PersonaDaoImpl();
}
return personaDaoInstance;
}
//Queries select
protected final String SQL_SELECT = "SELECT id_persona, nombre, apellido FROM " +"persona"+ "";
//Queries select by id
protected final String SQL_SELECT_BY_ID = "SELECT id_persona, nombre, apellido FROM persona WHERE id_persona = ?";
//insert
protected final String SQL_INSERT = "INSERT INTO " + "persona" + " ( nombre, apellido ) VALUES ( ?, ? )";
//update
protected final String SQL_UPDATE = "UPDATE " + "persona" + " SET nombre = ?, apellido = ? WHERE id_persona = ?";
//delete
protected final String SQL_DELETE = "DELETE FROM " + "persona" + " WHERE id_persona = ?";
@Override
public List<Persona> findAll() {
/**
* Metodo que regresa el contenido de la tabla de personas
*/
PreparedStatement stmt = null;
ResultSet rs = null;
Persona persona = null;
List<Persona> personas = new ArrayList<Persona>();
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_SELECT);
rs = stmt.executeQuery();
conn.commit(); // si todo va bien hacemos commit y guardamos los datos
while (rs.next()) {
int id_persona = rs.getInt(1);
String nombre = rs.getString(2);
String apellido = rs.getString(3);
/*System.out.print(" " + id_persona);
System.out.print(" " + nombre);
System.out.print(" " + apellido);
System.out.println();
*/
persona = new Persona();
persona.setIdPersona(new Integer(id_persona));
persona.setNombre(nombre);
persona.setApellido(apellido);
personas.add(persona);
}
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
} finally {
ResourceManager.close(rs);
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return personas;
}
@Override
public Persona getPersonaById(Integer idPersona) {
PreparedStatement stmt = null;
ResultSet rs = null;
Persona persona = null;
List<Persona> personas = new ArrayList<Persona>();
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_SELECT_BY_ID);
stmt.setInt(1, idPersona);
rs = stmt.executeQuery();
conn.commit();
rs.next();
int id_persona = rs.getInt(1);
String nombre = rs.getString(2);
String apellido = rs.getString(3);
persona = new Persona();
persona.setIdPersona(new Integer(id_persona));
persona.setNombre(nombre);
persona.setApellido(apellido);
} catch (SQLException e) {
e.printStackTrace();
} finally {
ResourceManager.close(rs);
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return persona;
}
@Override
public boolean deletePersonas(List<Integer> idPersonas) {
PreparedStatement stmt = null;
int rows = 0;
boolean status=true;
try {
conn = ResourceManager.getConexion();
for(Integer index:idPersonas) {
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_DELETE);
stmt.setInt(1, index);
stmt.executeUpdate();
conn.commit();
}
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
@Override
public boolean savePersona(Persona persona) {
PreparedStatement stmt = null;
ResultSet rs = null;//no se utiliza en este ejercicio
int rows = 0; //registros afectados
boolean status = true;
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_INSERT);
int index = 1;//contador de columnas
stmt.setString(index++, persona.getNombre());//param 1 => ?
stmt.setString(index++, persona.getApellido());//param 2 => ?
rows = stmt.executeUpdate();//no. registros afectados
conn.commit();
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
@Override
public boolean updatePersona(Persona persona) {
PreparedStatement stmt = null;
ResultSet rs = null;//no se utiliza en este ejercicio
int rows = 0; //registros afectados
boolean status = true;
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_UPDATE);
int index = 1;//contador de columnas
stmt.setString(index++, persona.getNombre());//param 1 => ?
stmt.setString(index++, persona.getApellido());//param 2 => ?
stmt.setInt(index++, persona.getIdPersona());//param 3 => ?
rows = stmt.executeUpdate();//no. registros afectados
conn.commit();
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
}
listadoPersonas.jsp
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
<meta charset="UTF-8">
<title>Listado de Personas</title>
</head>
<body>
<div id="wrap">
<div id="header">
<jsp:include page="/WEB-INF/pages/commons/header.jsp"/>
</div>
<div id="nav">
<jsp:include page="/WEB-INF/pages/commons/menu.jsp"/>
</div>
<div id="msg">
<jsp:include page="/WEB-INF/pages/commons/messages.jsp"/>
</div>
<div id="main">
<!--Es importante definir el id de la forma, ya que se validara con JavaScript -->
<form id="form1" name="form1" action="${pageContext.request.contextPath}/ServletControlador" method="post">
<!-- Esta accion se va modificar por JavaScript según la opción seleccionada -->
<input type="hidden" name="accion" id="accion"/>
<div class="subtitulo">
Listado de Personas
</div>
<div class="tabla">
<table align="center" class="elemento" >
<tr>
<th><input type="checkbox" name="controladorCheckbox" onclick="selectAllCheckboxes(this);" /> </th>
<th>Id. Persona</th>
<th>Nombre</th>
<th>Apellido</th>
</tr>
<c:forEach var="persona" items="${listaPersonas}" varStatus="row">
<tr class="${ (row.count % 2) == 0 ? "row1" : "row2" }" >
<td align="center">
<input type="checkbox" name="personas" id="personas" value="${persona.idPersona}">
</td>
<td onclick="editaRegistro(${row.count});">
${persona.idPersona}
</td>
<td onclick="editaRegistro(${row.count});">
${persona.nombre}
</td>
<td onclick="editaRegistro(${row.count});">
${persona.apellido}
</td>
</tr>
</c:forEach>
</table>
<input id="botonAgregar" type="button" value="Agregar" onclick="validaFormularioListadoPersonas(this);">
<input id="botonEditar" type="button" value="Editar" onclick="validaFormularioListadoPersonas(this);">
<input id="botonEliminar" type="button" value="Eliminar" onclick="validaFormularioListadoPersonas(this);">
</div>
</form>
</div>
<div id="footer">
<jsp:include page="/WEB-INF/pages/commons/footer.jsp"/>
</div>
</div>
</body>
</html>
detallePersonas.jsp: como parte destacable de los JSPs tenemos el uso de los tag jstl y la notacion: action="${pageContext.request.contextPath}/ServletControlador"
para consumir un recurso
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
<meta charset="UTF-8">
<title>Listado de Personas</title>
</head>
<body>
<div id="wrap">
<div id="header">
<jsp:include page="/WEB-INF/pages/commons/header.jsp"/>
</div>
<div id="nav">
<jsp:include page="/WEB-INF/pages/commons/menu.jsp"/>
</div>
<div id="msg">
<jsp:include page="/WEB-INF/pages/commons/messages.jsp"/>
</div>
<div id="main">
<div class="subtitulo">
Detalle Persona
</div>
<div class="formulario">
<!--Es importante definir el id de la forma, ya que se validara con JavaScript -->
<form id="form1" name="form1" action="${pageContext.request.contextPath}/ServletControlador" method="post" >
<!-- Esta accion se va modificar por JavaScript según la opción seleccionada -->
<input type="hidden" name="accion" id="accion" value="guardarPersona"/>
<!--nos va a servir para que javascript tome el valor dinamicamente
del nombre de la aplicacion-->
<input type="hidden" name="contexto" id="contexto" value="${pageContext.request.contextPath}"/>
<!--Id persona. Si estamos editando, reenviamos el id_persona al servidor
Esto nos permitirá distinguir si estamos Agregando(insert) o
modificando (update) -->
<input type="hidden" name="idPersona" value="${persona.idPersona}" />
<table align="center" class="elemento">
<tr>
<td>Nombre:</td>
<td><input type="text" name="nombre" value="${persona.nombre}" /></td>
</tr>
<tr>
<td>Apellido:</td>
<td><input type="text" name="apellido" value="${persona.apellido}" /></td>
</tr>
</table>
<input type="submit" value="Guardar" />
<input type="button" value="Cancelar" onclick="cancelar();" />
</form>
</div>
</div>
<div id="footer">
<jsp:include page="/WEB-INF/pages/commons/footer.jsp"/>
</div>
</div>
</body>
</html>
Proyecto en funcionamiento para el modelo de personas:
Estructura del proyecto:
Puntos y clases importantes:
Implementacion del pool Resource Manager:
Esta clase implementa el pool mediante la clase de BasicDataSource, el cual manejamos el patron de diseño singleton para generar la instancia de conexión.
package sga.eis.dao;
import java.sql.*;
import java.util.Enumeration;
import java.util.Properties;
import java.util.ResourceBundle;
import javax.sql.DataSource;
import org.apache.commons.dbcp2.BasicDataSource;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
public class ResourceManager {
private static String JDBC_DRIVER;// = "com.mysql.jdbc.Driver";
private static String JDBC_URL;// =
// "jdbc:mysql://localhost/sga";
private static String JDBC_USER;// = "root";
private static String JDBC_PASS;// = "admin";
private static int MAX_POOL_SIZE;
private static int IDLE_TIME_POOL;
private static Driver driver = null;
private static String JDBC_FILE_NAME = "ConexionJDBC";
Logger log = LogManager.getLogger(ResourceManager.class);
private static BasicDataSource ds = null;
/**
* Funcion para el manejo de los valores de la conexion en un
* archivo de propidades
*
* @param file
* @return
*/
public static Properties loadProperties(String file) {
Properties prop = new Properties();
ResourceBundle bundle = ResourceBundle.getBundle(file);
Enumeration e = bundle.getKeys();
String key = null;
while (e.hasMoreElements()) {
key = (String) e.nextElement();
prop.put(key, bundle.getObject(key));
}
// Asignamos los valores del archivo de propiedades
// a las variables de la clase
JDBC_DRIVER = prop.getProperty("driver");
JDBC_URL = prop.getProperty("url");
JDBC_USER = prop.getProperty("user");
JDBC_PASS = prop.getProperty("pass");
MAX_POOL_SIZE = Integer.parseInt(prop.getProperty("max_pool_size"));
IDLE_TIME_POOL = Integer.parseInt(prop.getProperty("idle_time"));
// Regresamos el objeto properties con los valores
// de la conexion a la BD
return prop;
}
/**
* Funciona que nos regresa un DataSource considerando valores
* de un pool de conexiones
*
* @return
*/
public static DataSource getDataSource() {
if(ds == null) {
// Cargamos los valores del archivo de propiedades
loadProperties(JDBC_FILE_NAME);
ds = new BasicDataSource();
ds.setDriverClassName(JDBC_DRIVER);
ds.setUrl(JDBC_URL);
ds.setUsername(JDBC_USER);
ds.setPassword(JDBC_PASS);
// Definimos el tamaño del pool de conexiones
//ds.setMaxActive(MAX_POOL_SIZE);// en este caso son 20
// conexiones abiertas
//ds.setMaxIdle(IDLE_TIME_POOL);// definimos el tiempo de espera
// antes de cerrar la conexion
/**nuevas configuraciones*/
ds.setInitialSize(MAX_POOL_SIZE);
ds.setMaxIdle(IDLE_TIME_POOL);
ds.setMaxTotal(MAX_POOL_SIZE);
ds.setMaxWaitMillis(2000);
}
return ds;
}
public static synchronized Connection getConexion() throws SQLException {
return getDataSource().getConnection();
}
public static void close(Connection conn) {
try {
if (conn != null) {
conn.close();
}
} catch (SQLException sqle) {
sqle.printStackTrace();
}
}
public static void close(PreparedStatement stmt) {
try {
if (stmt != null) {
stmt.close();
}
} catch (SQLException sqle) {
sqle.printStackTrace();
}
}
public static void close(ResultSet rs) {
try {
if (rs != null) {
rs.close();
}
} catch (SQLException sqle) {
sqle.printStackTrace();
}
}
}
Servlet controlador: Servlet que maneja las peticiones del cliente:
como parte destacable tenemos la forma de redireccionar:
request.getRequestDispatcher("/WEB-INF/pages/sga/detalleUsuario.jsp").forward(request, response);
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package sga.eis.controller;
import sga.eis.dto.*;
import sga.eis.services.*;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
/**
*
* @author ci
*/
@WebServlet(name = "ServletControlador", urlPatterns = {"/ServletControlador"})
public class ServletControlador extends HttpServlet {
protected void processRequest(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Revisamos los casos de uso del sistema SGA
String accion = request.getParameter("accion");
if ("listarPersonas".equals(accion)) {
this.confirmarUsuarioEnSession(request, response);
} else if ("validarUsuario".equals(accion)) {
this.validarUsuario(request, response);
} else if ("agregarPersona".equals(accion)) {
this.agregarPersona(request, response);
} else if ("editarPersona".equals(accion)) {
this.editarPersona(request, response);
} else if ("eliminarPersona".equals(accion)) {
this.eliminarPersona(request, response);
} else if ("guardarPersona".equals(accion)) {
this.guardarPersona(request, response);
} else if ("salir".equals(accion)) {
this.salir(request, response);
} else if ("listarUsuarios".equals(accion)) {
this.confirmarUsuarioEnSession(request, response);
} else if ("editarUsuario".equals(accion)) {
this.editarUsuario(request, response);
} else if ("guardarUsuario".equals(accion)) {
this.guardarUsuario(request, response);
} else if ("agregarUsuario".equals(accion)) {
this.agregarUsuario(request, response);
} else if ("eliminarUsuario".equals(accion)) {
this.eliminarUsuario(request, response);
} else {
this.accionPorDefault(request, response);
}
}
//Metodo para procesar validar si el usuario ya inicio sesion
private void confirmarUsuarioEnSession(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Revisamos si ya está el usuario en la sesion
HttpSession session = request.getSession();
/**Si no esta logueado se manda a login y se pierde la accion listarUsuarios por validarUsuario**/
String usuario = (String) session.getAttribute("usuario");
if (usuario != null) {
String accion = request.getParameter("accion");
System.out.println("accion: "+accion);
if(accion.equals("listarPersonas")){
this.listarPersonas(request, response);
}else{
this.listarUsuarios(request, response);
}
} else {
System.out.println("confirmar usuario en sesion: "+request.getParameter("accion"));
session.setAttribute("accionTmp", request.getParameter("accion"));
request.getRequestDispatcher("/WEB-INF/pages/sga/login.jsp").forward(request, response);
//lo manda accion = validarUsuario
}
}
//Metodo para procesar el caso de uso de listarPersonas
private void listarPersonas(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
System.out.println("Listar personas");
//Revisamos si ya está el usuario en la sesion
HttpSession session = request.getSession();
String usuario = (String) session.getAttribute("usuario");
//Si el usuario ya esta en session, lo redireccionamos al listado de personas
if (usuario != null) {
//Recuperamos el listado de personas, utilizamos el servicio de Personas
PersonaService personaService = PersonaServiceImpl.getInstance();
List<Persona> personas = personaService.getAllPersonas();
//Si se encontraron personas, las compartimos en la pagina Web
if (personas != null && personas.size() > 0) {
request.setAttribute("listaPersonas", personas);
}
request.getRequestDispatcher("/WEB-INF/pages/sga/listadoPersonas.jsp").forward(request, response);
}
}
//Metodo para procesar el caso de uso de listarUsuarios
private void listarUsuarios(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Revisamos si ya está el usuario en la sesion
HttpSession session = request.getSession();
String usuario = (String) session.getAttribute("usuario");
//Si el usuario ya esta en session, lo redireccionamos al listado de Usuarios
/*if (usuario != null) {
//Recuperamos el listado de usuarios, utilizamos el servicio de Usuarios
UsuarioService usuarioService = UsuarioServiceImpl.getInstance();
List<Usuario> usuarios = usuarioService.getAllUsuarios();
//Si se encontraron personas, las compartimos en la pagina Web
if (usuarios != null && usuarios.size() > 0) {
request.setAttribute("listaUsuarios", usuarios);
}
//Si se encontraron personas, las compartimos en la pagina Web
if (usuarios != null && usuarios.size() > 0) {
request.setAttribute("listaUsuarios", usuarios);
}
request.getRequestDispatcher("/WEB-INF/pages/sga/listadoUsuarios.jsp").forward(request, response);
}*/
}
//Metodo para validar si el usuario y password proporcinados son correctos
private void validarUsuario(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Recuperamos los parametros del formulario
String usuarioParam = request.getParameter("username");
String passwordParam = request.getParameter("password");
//Creamos el objeto DTO a enviar a la capa de servicio
Usuario usuarioDto = new Usuario();
usuarioDto.setUsername(usuarioParam);
usuarioDto.setPassword(passwordParam);
//Revisamos si existen el usuario y el password en la BD
//Utilizamos el servicio de Usuarios
//UsuarioService usuarioService = UsuarioServiceImpl.getInstance();
//boolean usuarioValido = usuarioService.usuarioExistente(usuarioDto);
boolean usuarioValido = true;
//Si el usuario es válido, lo redireccionamos al caso de listarPersonas
if (usuarioValido) {
//Agregamos el usuario a la session
HttpSession session = request.getSession();
session.setAttribute("usuario", usuarioDto.getUsername());
String opc = (String) session.getAttribute("accionTmp");
if(opc!= null && opc.equals("listarUsuarios")){
this.listarUsuarios(request, response);
}else{
this.listarPersonas(request, response);
}
} else {
//si el usuario no es valido, lo mandamos a la pagina de login nuevamente
request.setAttribute("mensaje", "El usuario o password son incorrectos");
request.getRequestDispatcher("/WEB-INF/pages/sga/login.jsp").forward(request, response);
}
}
private void salir(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Eliminamos la session del servidor y redireccionamos a la pagina de inicio
request.getSession().invalidate();
request.getRequestDispatcher("index.jsp").forward(request, response);
}
private void accionPorDefault(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
//Redireccionamos a la pagina de inicio
String mensaje = "Acción no proporcionada o desconocida";
request.setAttribute("mensaje", mensaje);
request.getRequestDispatcher("index.jsp").forward(request, response);
}
// <editor-fold defaultstate="collapsed" desc="HttpServlet methods. Click on the + sign on the left to edit the code.">
/**
* Handles the HTTP <code>GET</code> method.
* @param request servlet request
* @param response servlet response
* @throws ServletException if a servlet-specific error occurs
* @throws IOException if an I/O error occurs
*/
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
/**
* Handles the HTTP <code>POST</code> method.
* @param request servlet request
* @param response servlet response
* @throws ServletException if a servlet-specific error occurs
* @throws IOException if an I/O error occurs
*/
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
processRequest(request, response);
}
/**
* Returns a short description of the servlet.
* @return a String containing servlet description
*/
@Override
public String getServletInfo() {
return "Short description";
}// </editor-fold>
private void agregarPersona(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//No procesamos ningun parametro, sino que solo redireccionamos a la vista
//para agregar una nueva persona
request.getRequestDispatcher("/WEB-INF/pages/sga/detallePersona.jsp").forward(request, response);
}
private void agregarUsuario(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//No procesamos ningun parametro, sino que solo redireccionamos a la vista
//para agregar una nueva usuario
request.getRequestDispatcher("/WEB-INF/pages/sga/detalleUsuario.jsp").forward(request, response);
}
private void editarPersona(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String mensaje = null;
//Recuperamos el identificador a procesar y reenviamos a la pagina de detalle
String idPersonaParam = request.getParameter("personas");
Integer idPersona = null;
if (idPersonaParam != null && !idPersonaParam.trim().equals("")) {
idPersona = new Integer(idPersonaParam);
//Utilizamos el servicio de persona para recuperar el objeto de la BD
PersonaService personaService = PersonaServiceImpl.getInstance();
Persona persona = personaService.getPersonaById(idPersona);
System.out.println("Editar: "+persona.getIdPersona()+" "+persona.getNombre()+" "+persona.getApellido());
//compartimos el objeto persona obtenido, para poderlo modificar
request.setAttribute("persona", persona);
request.getRequestDispatcher("/WEB-INF/pages/sga/detallePersona.jsp").forward(request, response);
} else {
mensaje = "Debe seleccionar un elemento a Editar";
request.setAttribute("mensaje", mensaje);
//Reutilizamos el caso de listarPersonas
this.listarPersonas(request, response);
}
}
private void editarUsuario(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
/*
String mensaje = null;
//Recuperamos el identificador a procesar y reenviamos a la pagina de detalle
String idUsuarioParam = request.getParameter("usuarios");
Integer idUsuario = null;
if (idUsuarioParam != null && !idUsuarioParam.trim().equals("")) {
idUsuario = new Integer(idUsuarioParam);
//Utilizamos el servicio de persona para recuperar el objeto de la BD
UsuarioService usuarioService = UsuarioServiceImpl.getInstance();
Usuario usuario = usuarioService.getUsuarioById(idUsuario);
//compartimos el objeto persona obtenido, para poderlo modificar
request.setAttribute("user", usuario);
request.getRequestDispatcher("/WEB-INF/pages/sga/detalleUsuario.jsp").forward(request, response);
} else {
mensaje = "Debe seleccionar un elemento a Editar";
request.setAttribute("mensaje", mensaje);
//Reutilizamos el caso de listarPersonas
this.listarUsuarios(request, response);
}
*/
}
private void eliminarPersona(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String mensaje = null;
//1. Procesamos los parametros
//Recuperamos TODOS los objetos seleccionados
String[] idPersonaParams = request.getParameterValues("personas");
List<Integer> idPersonas = new ArrayList<Integer>();
//2. Utilizamos los objetos de Modelo (Persona)
//Validamos los parametros a eliminar
if (idPersonaParams != null && idPersonaParams.length > 0) {
for (String persona : idPersonaParams) {
idPersonas.add(new Integer(persona));
}
//3.Utilizamos la capa de servicio para eliminar los objetos
PersonaService personaService = PersonaServiceImpl.getInstance();
boolean registrosEliminados = personaService.eliminarPersonas(idPersonas);
if (registrosEliminados) {
mensaje = "Se eliminaron correctamente los registros";
}
} else {
mensaje = "Debe seleccionar uno o varios elementos a Eliminar";
}
//4. Redireccionamos al listado de personas (ya no debe de mostrar los registros eliminados)
request.setAttribute("mensaje", mensaje);
this.listarPersonas(request, response);
}
private void eliminarUsuario(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
/*
String mensaje = null;
//1. Procesamos los parametros
//Recuperamos TODOS los objetos seleccionados
String[] idUsuarioParams = request.getParameterValues("usuarios");
List<Integer> idUsers = new ArrayList<Integer>();
//2. Utilizamos los objetos de Modelo (Persona)
//Validamos los parametros a eliminar
if (idUsuarioParams != null && idUsuarioParams.length > 0) {
for (String user : idUsuarioParams) {
idUsers.add(new Integer(user));
System.out.println("ids a eliminar: "+user);
}
//3.Utilizamos la capa de servicio para eliminar los objetos
UsuarioService usuarioService = UsuarioServiceImpl.getInstance();
boolean registrosEliminados = usuarioService.eliminarPersonas(idUsers);
if (registrosEliminados) {
mensaje = "Se eliminaron correctamente los registros";
}
} else {
mensaje = "Debe seleccionar uno o varios elementos a Eliminar";
}
//4. Redireccionamos al listado de personas (ya no debe de mostrar los registros eliminados)
request.setAttribute("mensaje", mensaje);
this.listarUsuarios(request, response);
*/
}
//Este metodo nos permite insertar o modificar una persona
//La diferencia va a estar si recibimos o no una llave primaria por parte del formulario
private void guardarPersona(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String mensaje = null;
//1. Procesamos los parametros
String idPersonaParam = request.getParameter("idPersona");
String nombreParam = request.getParameter("nombre");
String apellidoParam = request.getParameter("apellido");
System.out.println("Guardar: "+idPersonaParam+" "+nombreParam+" "+apellidoParam);
//Validamos la PK
Integer idPersona = null;
if (idPersonaParam != null && !idPersonaParam.trim().equals("")) {
idPersona = new Integer(idPersonaParam);
}
//2. Utilizamos el objeto Modelo
Persona persona = new Persona();
persona.setIdPersona(idPersona); //si no venia en los parametros, se coloca null
persona.setNombre(nombreParam);
persona.setApellido(apellidoParam);
//3. Utilizamos la capa de servicio
PersonaService personaService = PersonaServiceImpl.getInstance();
boolean elementoGuardado = personaService.guardarPersona(persona);
//4. Redireccionamos dependiendo del resultado
if (elementoGuardado) {
mensaje = "Se guardó el elemento correctamente";
request.setAttribute("mensaje", mensaje);
} else {
mensaje = "No se guardo correctamente el elemento";
request.setAttribute("mensaje", mensaje);
}
//Reutilizamos el caso de listarPersonas
request.setAttribute("mensaje", mensaje);
this.listarPersonas(request, response);
}
private void guardarUsuario(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
/*
String mensaje = null;
//1. Procesamos los parametros
String idUsuarioParam = request.getParameter("idUsuario");
String idPersonaParam = request.getParameter("idPersona");
String usernameParam = request.getParameter("username");
String passwordParam = request.getParameter("password");
System.out.println("params: "+idUsuarioParam+" "+idPersonaParam+" "+usernameParam+" "+passwordParam);
//Validamos la PK
Integer idUsuario = null;
if (idUsuarioParam != null && !idUsuarioParam.trim().equals("")) {
idUsuario = new Integer(idUsuarioParam);
}
//Validamos la PK de IdPersona
Integer idPersona = null;
if (idPersonaParam != null && !idPersonaParam.trim().equals("")) {
idPersona = new Integer(idPersonaParam);
}
//1.5 validamos la llave del idPersona
PersonaService personaService = PersonaServiceImpl.getInstance();
System.out.println("Buscar ....."+idPersona);
personaService.getAllPersonas();
try{
Persona persona = personaService.getPersonaById(idPersona);
//2. Utilizamos el objeto Modelo
Usuario usuario = new Usuario();
usuario.setIdUsuario(idUsuario); //si no venia en los parametros, se coloca null
usuario.setIdPersona(idPersona);
usuario.setUsername(usernameParam);
usuario.setPassword(passwordParam);
//3. Utilizamos la capa de servicio
UsuarioService usuarioService = UsuarioServiceImpl.getInstance();
boolean elementoGuardado = usuarioService.guardarUsuario(usuario);
//4. Redireccionamos dependiendo del resultado
if (elementoGuardado) {
mensaje = "Se guardó el elemento correctamente";
request.setAttribute("mensaje", mensaje);
} else {
mensaje = "No se guardo correctamente el elemento";
request.setAttribute("mensaje", mensaje);
}
}catch(Exception e){
//Reutilizamos el caso de listarPersonas
mensaje = "Error, no existe una persona con ese Id";
request.setAttribute("mensaje", mensaje);
}
this.listarUsuarios(request, response);
*/
}
}
package sga.eis.dao;
import sga.eis.dto.*;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import java.util.ArrayList;
public class PersonaDaoImpl implements PersonaDao{
private Connection conn = null;
//Utilizamos el patron singleton, solo existen un objeto de tipo UsuarioService en Memoria
private static PersonaDao personaDaoInstance;
//Creamos una nueva y unica instancia si es que no existe
public static PersonaDao getInstance() {
if(personaDaoInstance == null) {
personaDaoInstance = new PersonaDaoImpl();
}
return personaDaoInstance;
}
//Queries select
protected final String SQL_SELECT = "SELECT id_persona, nombre, apellido FROM " +"persona"+ "";
//Queries select by id
protected final String SQL_SELECT_BY_ID = "SELECT id_persona, nombre, apellido FROM persona WHERE id_persona = ?";
//insert
protected final String SQL_INSERT = "INSERT INTO " + "persona" + " ( nombre, apellido ) VALUES ( ?, ? )";
//update
protected final String SQL_UPDATE = "UPDATE " + "persona" + " SET nombre = ?, apellido = ? WHERE id_persona = ?";
//delete
protected final String SQL_DELETE = "DELETE FROM " + "persona" + " WHERE id_persona = ?";
@Override
public List<Persona> findAll() {
/**
* Metodo que regresa el contenido de la tabla de personas
*/
PreparedStatement stmt = null;
ResultSet rs = null;
Persona persona = null;
List<Persona> personas = new ArrayList<Persona>();
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_SELECT);
rs = stmt.executeQuery();
conn.commit(); // si todo va bien hacemos commit y guardamos los datos
while (rs.next()) {
int id_persona = rs.getInt(1);
String nombre = rs.getString(2);
String apellido = rs.getString(3);
/*System.out.print(" " + id_persona);
System.out.print(" " + nombre);
System.out.print(" " + apellido);
System.out.println();
*/
persona = new Persona();
persona.setIdPersona(new Integer(id_persona));
persona.setNombre(nombre);
persona.setApellido(apellido);
personas.add(persona);
}
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
} finally {
ResourceManager.close(rs);
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return personas;
}
@Override
public Persona getPersonaById(Integer idPersona) {
PreparedStatement stmt = null;
ResultSet rs = null;
Persona persona = null;
List<Persona> personas = new ArrayList<Persona>();
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_SELECT_BY_ID);
stmt.setInt(1, idPersona);
rs = stmt.executeQuery();
conn.commit();
rs.next();
int id_persona = rs.getInt(1);
String nombre = rs.getString(2);
String apellido = rs.getString(3);
persona = new Persona();
persona.setIdPersona(new Integer(id_persona));
persona.setNombre(nombre);
persona.setApellido(apellido);
} catch (SQLException e) {
e.printStackTrace();
} finally {
ResourceManager.close(rs);
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return persona;
}
@Override
public boolean deletePersonas(List<Integer> idPersonas) {
PreparedStatement stmt = null;
int rows = 0;
boolean status=true;
try {
conn = ResourceManager.getConexion();
for(Integer index:idPersonas) {
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_DELETE);
stmt.setInt(1, index);
stmt.executeUpdate();
conn.commit();
}
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
@Override
public boolean savePersona(Persona persona) {
PreparedStatement stmt = null;
ResultSet rs = null;//no se utiliza en este ejercicio
int rows = 0; //registros afectados
boolean status = true;
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_INSERT);
int index = 1;//contador de columnas
stmt.setString(index++, persona.getNombre());//param 1 => ?
stmt.setString(index++, persona.getApellido());//param 2 => ?
rows = stmt.executeUpdate();//no. registros afectados
conn.commit();
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
@Override
public boolean updatePersona(Persona persona) {
PreparedStatement stmt = null;
ResultSet rs = null;//no se utiliza en este ejercicio
int rows = 0; //registros afectados
boolean status = true;
try {
conn = ResourceManager.getConexion();
conn.setAutoCommit(false);
stmt = conn.prepareStatement(SQL_UPDATE);
int index = 1;//contador de columnas
stmt.setString(index++, persona.getNombre());//param 1 => ?
stmt.setString(index++, persona.getApellido());//param 2 => ?
stmt.setInt(index++, persona.getIdPersona());//param 3 => ?
rows = stmt.executeUpdate();//no. registros afectados
conn.commit();
} catch (SQLException e) {
try {
System.out.println("Entramos al rollback");
//Imprimimos la excepcion a la consola
e.printStackTrace(System.out);
//Hacemos rollback
conn.rollback();
} catch (SQLException e1) {
e1.printStackTrace(System.out);
}
status=false;
} finally {
ResourceManager.close(stmt);
ResourceManager.close(conn);
}
return status;
}
}
Creacion del servicio usando el patron de diseño singleton (tambien en dao y pool)
package sga.eis.services;
import java.util.List;
import sga.eis.dao.*;
import sga.eis.dto.Persona;
public class PersonaServiceImpl implements PersonaService{
//Utilizamos el patron singleton, solo existen un objeto de tipo UsuarioService en Memoria
private static PersonaService personaServiceInstance;
//Creamos una nueva y unica instancia si es que no existe
public static PersonaService getInstance() {
if (personaServiceInstance == null) {
personaServiceInstance = new PersonaServiceImpl();
}
return personaServiceInstance;
}
//Constructor sin argumentos privado, para implementar el patron singleton
private PersonaServiceImpl() {
}
//Objeto el cual sera creado solo una vez
PersonaDao personaDao;
@Override
public List<Persona> getAllPersonas() {
try {
this.personaDao = PersonaDaoImpl.getInstance();
return this.personaDao.findAll();
} catch (Exception ex) {
ex.printStackTrace();
return null;
}
}
@Override
public Persona getPersonaById(Integer idPersona) {
try {
this.personaDao = PersonaDaoImpl.getInstance();
return this.personaDao.getPersonaById(idPersona);
} catch (Exception ex) {
ex.printStackTrace();
return null;
}
}
@Override
public boolean eliminarPersonas(List<Integer> idPersonas) {
try {
this.personaDao = PersonaDaoImpl.getInstance();
return this.personaDao.deletePersonas(idPersonas);
} catch (Exception ex) {
ex.printStackTrace();
return false;
}
}
@Override
public boolean guardarPersona(Persona persona) {
try {
this.personaDao = PersonaDaoImpl.getInstance();
if(persona.getIdPersona() == null) {
return this.personaDao.savePersona(persona);
}else {
return this.personaDao.updatePersona(persona);
}
} catch (Exception ex) {
ex.printStackTrace();
return false;
}
}
}
Dependencias maven: pom.xml se agregan las dependenicas del pool dbcp2, y jstl para los servlets
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.mx</groupId>
<artifactId>SGAServletsJDBCPool</artifactId>
<version>1.0</version>
<packaging>war</packaging>
<name>SGAServletsJDBCPool</name>
<dependencies>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.10.0</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.10.0</version>
</dependency>
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-web-api</artifactId>
<version>8.0</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.36</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-dbcp2</artifactId>
<version>2.1.1</version>
</dependency>
<dependency>
<groupId>jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
<scope>compile</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.3</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.7.0</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
</plugins>
</build>
</project>
listadoPersonas.jsp
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
<meta charset="UTF-8">
<title>Listado de Personas</title>
</head>
<body>
<div id="wrap">
<div id="header">
<jsp:include page="/WEB-INF/pages/commons/header.jsp"/>
</div>
<div id="nav">
<jsp:include page="/WEB-INF/pages/commons/menu.jsp"/>
</div>
<div id="msg">
<jsp:include page="/WEB-INF/pages/commons/messages.jsp"/>
</div>
<div id="main">
<!--Es importante definir el id de la forma, ya que se validara con JavaScript -->
<form id="form1" name="form1" action="${pageContext.request.contextPath}/ServletControlador" method="post">
<!-- Esta accion se va modificar por JavaScript según la opción seleccionada -->
<input type="hidden" name="accion" id="accion"/>
<div class="subtitulo">
Listado de Personas
</div>
<div class="tabla">
<table align="center" class="elemento" >
<tr>
<th><input type="checkbox" name="controladorCheckbox" onclick="selectAllCheckboxes(this);" /> </th>
<th>Id. Persona</th>
<th>Nombre</th>
<th>Apellido</th>
</tr>
<c:forEach var="persona" items="${listaPersonas}" varStatus="row">
<tr class="${ (row.count % 2) == 0 ? "row1" : "row2" }" >
<td align="center">
<input type="checkbox" name="personas" id="personas" value="${persona.idPersona}">
</td>
<td onclick="editaRegistro(${row.count});">
${persona.idPersona}
</td>
<td onclick="editaRegistro(${row.count});">
${persona.nombre}
</td>
<td onclick="editaRegistro(${row.count});">
${persona.apellido}
</td>
</tr>
</c:forEach>
</table>
<input id="botonAgregar" type="button" value="Agregar" onclick="validaFormularioListadoPersonas(this);">
<input id="botonEditar" type="button" value="Editar" onclick="validaFormularioListadoPersonas(this);">
<input id="botonEliminar" type="button" value="Eliminar" onclick="validaFormularioListadoPersonas(this);">
</div>
</form>
</div>
<div id="footer">
<jsp:include page="/WEB-INF/pages/commons/footer.jsp"/>
</div>
</div>
</body>
</html>
detallePersonas.jsp: como parte destacable de los JSPs tenemos el uso de los tag jstl y la notacion: action="${pageContext.request.contextPath}/ServletControlador"
para consumir un recurso
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
<meta charset="UTF-8">
<title>Listado de Personas</title>
</head>
<body>
<div id="wrap">
<div id="header">
<jsp:include page="/WEB-INF/pages/commons/header.jsp"/>
</div>
<div id="nav">
<jsp:include page="/WEB-INF/pages/commons/menu.jsp"/>
</div>
<div id="msg">
<jsp:include page="/WEB-INF/pages/commons/messages.jsp"/>
</div>
<div id="main">
<div class="subtitulo">
Detalle Persona
</div>
<div class="formulario">
<!--Es importante definir el id de la forma, ya que se validara con JavaScript -->
<form id="form1" name="form1" action="${pageContext.request.contextPath}/ServletControlador" method="post" >
<!-- Esta accion se va modificar por JavaScript según la opción seleccionada -->
<input type="hidden" name="accion" id="accion" value="guardarPersona"/>
<!--nos va a servir para que javascript tome el valor dinamicamente
del nombre de la aplicacion-->
<input type="hidden" name="contexto" id="contexto" value="${pageContext.request.contextPath}"/>
<!--Id persona. Si estamos editando, reenviamos el id_persona al servidor
Esto nos permitirá distinguir si estamos Agregando(insert) o
modificando (update) -->
<input type="hidden" name="idPersona" value="${persona.idPersona}" />
<table align="center" class="elemento">
<tr>
<td>Nombre:</td>
<td><input type="text" name="nombre" value="${persona.nombre}" /></td>
</tr>
<tr>
<td>Apellido:</td>
<td><input type="text" name="apellido" value="${persona.apellido}" /></td>
</tr>
</table>
<input type="submit" value="Guardar" />
<input type="button" value="Cancelar" onclick="cancelar();" />
</form>
</div>
</div>
<div id="footer">
<jsp:include page="/WEB-INF/pages/commons/footer.jsp"/>
</div>
</div>
</body>
</html>
La estructura de la tabla de la BD se puede observar en la clase DTO de Persona
No hay comentarios.