entre Desarrolladores

Recibe ayuda de expertos

Registrate y pregunta

Es gratis y fácil

Recibe respuestas

Respuestas, votos y comentarios

Vota y selecciona respuestas

Recibe puntos, vota y da la solución

Pregunta

1voto

Consulta a mysql con jtable

por favor alguien podria ayudarme, el proyecto trata de hacer un sistema de ventas a nivel nacional, conociendo desde cualquier local la cantidad de instrumentos de otro local, la base de datos esta en mysql y el codigo fuente en java.
como puedo usar hibernate, soap, rest, etc.
quiero mejorar el tiempo de respuesta de una consulta con java y mysql.
como explique en mi consulta anterior demora 10 segundos en mostrarme los datos en una tabla. y si es con operacion matematica demora mas dependiente de la cantidad de registros.
utilizo jdbc driver

clic para ver video en youtube

1voto

white comentado

Podrias agregar el código donde haces la consulta y agregas los datos a la tabla?
Talvez debas hacer la consulta en un hilo separado, en ocasiones el problema viene por que al hacerlo en el hilo principal congelamos la interfaz de usuario.

1voto

leog.1992 comentado

Mi codigo para cargar el form:
Frm_ver_Empleados

public frm_ver_empleados() {
    initComponents();
    con.conectar();
    String ver_emp = "select e.dni_col, e.nom_col, cat.descripcion, e.est_col, c.desc_car from Colaborador as e inner join Cargo as c on e.idCargo=c.idCargo inner join Categoria_Empleado as cat on e.idCat_Emp = cat.idCat_Emp order by e.nom_col asc";
    ver_empleado(ver_emp);
    funcion = "empleado";
}

0voto

leog.1992 comentado

ufgh

private void ver_empleado (String query){
  try {
    mostrar = new DefaultTableModel()  {@Override
 public boolean isCellEditable (int fila, int columna) {
     return false;
 }};
    Statement st= con.conexion();
    ResultSet rs = con.consulta(st, query);
    //Establecer como cabezeras el nombre de las colimnas
    mostrar.addColumn("DNI");
    mostrar.addColumn("Nombre y Apellidos");
    mostrar.addColumn("Categoria");
    mostrar.addColumn("Cargo");
    mostrar.addColumn("Fec. Ingreso");
    mostrar.addColumn("Contrato");
    mostrar.addColumn("Fec. Ven. Co.");
    mostrar.addColumn("Poliza SCTR");
    mostrar.addColumn("EMO");
    mostrar.addColumn("Ant. Polic.");
    mostrar.addColumn("Ant. Penales");
    mostrar.addColumn("Ant. Judic.");
    mostrar.addColumn("Estado");

    //Creando las filas para el JTable
    while (rs.next()) {
        Object[] fila = new Object[13];
        fila[0]=rs.getObject("e.dni_col");
        emp.setDni(rs.getInt("e.dni_col"));
        fila[1]=rs.getObject("e.nom_col");
        fila[2]=rs.getObject("cat.descripcion");
        fila[3]=rs.getObject("c.desc_car");
        fila[4]="-";
        try {
            Statement st1 = con.conexion();
            String ver_cont = "select fec_ini from Contrato_Colaborador where dni_col = '"+emp.getDni()+"' and estado = '1' order by "
                    + "idContrato_Colaborador desc limit 1";
            ResultSet rs1 = con.consulta(st1, ver_cont);
            if (rs1.next()) {
                fila[5]="SI";
                fila[6]=rs1.getString("fec_ini");
            } else {
                fila[5]="NO";
                fila[6]="-";
            }
            con.cerrar(rs1);
            con.cerrar(st1);
        } catch (SQLException ex) {
            System.out.print(ex);
        }
        fila[7]="-";
        fila[8]="-";
        fila[9]="-";
        fila[10]="-";
        fila[11]="-";
        if (rs.getString("e.est_col").equals("1")) {
            fila[12] = "ACTIVO";
        } else {
            fila[12] = "-";
        }
        mostrar.addRow(fila);
    }
    con.cerrar(st);
    con.cerrar(rs);
    t_empleados.setModel(mostrar);
    t_empleados.getColumnModel().getColumn(0).setPreferredWidth(80);
    t_empleados.getColumnModel().getColumn(1).setPreferredWidth(300);
    t_empleados.getColumnModel().getColumn(2).setPreferredWidth(90);
    t_empleados.getColumnModel().getColumn(3).setPreferredWidth(200);
    t_empleados.getColumnModel().getColumn(4).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(5).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(6).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(7).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(8).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(9).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(10).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(11).setPreferredWidth(70);
    t_empleados.getColumnModel().getColumn(12).setPreferredWidth(50);
    ven.centrar_celda(t_empleados, 0);
    ven.centrar_celda(t_empleados, 4);
    ven.centrar_celda(t_empleados, 5);
    ven.centrar_celda(t_empleados, 6);
    ven.centrar_celda(t_empleados, 7);
    ven.centrar_celda(t_empleados, 8);
    ven.centrar_celda(t_empleados, 9);
    ven.centrar_celda(t_empleados, 10);
    ven.centrar_celda(t_empleados, 11);
    ven.centrar_celda(t_empleados, 12);
    mostrar.fireTableDataChanged();
}
catch (SQLException e) {
    System.out.print(e);
}

}

0voto

white comentado

Cual es el codigo de tu clase donde conectas y realizas consultas a la base de datos (con)?

puedes hacer un benchmark a modo de asegurarse que la consulta tarde mas de lo esperado, cuanto te imprime al hacer benchmark?


PD: Puede que el problema principal sea de latencia, en ese caso tendras que hacer la conexión al principio de tu aplicacion y mantenerla abierta.

haz 2 benchmarks:

long start = System.currentTimeMillis();
con.conectar();
System.out.println("tiempo de conexion:");
System.out.println(System.currentTimeMillis() - start);

long start = System.currentTimeMillis();
Statement st= con.conexion();
ResultSet rs = con.consulta(st, query);
System.out.println("tiempo de consulta:");
System.out.println(System.currentTimeMillis() - start);

Cuentanos despues cuanto te da en tiempo de conexion y cuanto en tiempo de consulta.

0voto

leog.1992 comentado

package Clases; 
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.sql.*;
import javax.swing.JOptionPane;
/**
 *
 * @author Administrador
 */
public class Cl_Conectar {
    private static Connection conexion = null;
    private static String bd = "conmetal_erp"; // Nombre de BD.
    private static String user = "conmetal_root"; // Usuario de BD.
    private static String password = "*******"; // Password de BD.
//    private static String bd = "erp_metalmecanica"; // Nombre de BD.
//    private static String user = "root"; // Usuario de BD.
//    private static String password = "******"; // Password de BD.
    // Driver para MySQL en este caso.
    private static String driver = "com.mysql.jdbc.Driver";
    // Ruta del servidor.
    String server = "jdbc:mysql://conmetalperu.com:3306/" + bd;
//    String server = "jdbc:mysql://"+leer()+"/" + bd;

     private String leer () {
        String server = null;
    try {  
            File Ffichero=new File("server.txt");

            /*Si existe el fichero*/  
            if(Ffichero.exists()){  
                /*Abre un flujo de lectura a el fichero*/  
                BufferedReader Flee= new BufferedReader(new FileReader(Ffichero));  
                String Slinea;  
                //System.out.println("**********Leyendo Fichero***********");  
                /*Lee el fichero linea a linea hasta llegar a la ultima*/  
                while((Slinea=Flee.readLine())!=null) {  
                    /*Imprime la linea leida*/  
                    server = Slinea;
                   // System.out.println(Slinea);                
                }  
                //System.out.println("*********Fin Leer Fichero**********");  
                /*Cierra el flujo*/  
                Flee.close(); 
                //return txt_alm;
            }else{  
                System.out.println("Fichero No Existe");  
            }  
        } catch (IOException ex) {  
            /*Captura un posible error y le imprime en pantalla*/   
            System.out.println(ex.getMessage());  
        } 
        return server;
    }

    /**
     * Método neecesario para conectarse al Driver y poder usar MySQL.
     */

    public  void conectar()  {
         try {

            Class.forName(driver);
            conexion = DriverManager.getConnection(server, user, password);

        } catch (Exception e) {
            JOptionPane.showMessageDialog(null,"Error: Imposible realizar la conexion a BD.");
            System.exit(0);
            e.printStackTrace();

        }
    }

    /**
     * Método para establecer la conexión con la base de datos.
     *
     * @return
     */

    public Connection conx(){
        return conexion;
    }
    public  Statement conexion() {
        Statement st = null;
        try {
            st = conexion.createStatement();
        } catch (SQLException e) {
            System.out.println("Error: Conexión incorrecta.");
            e.printStackTrace();
        }
        return st;
    }

    /**
     * Método para realizar consultas del tipo: SELECT * FROM tabla WHERE..."
     *
     * @param st
     * @param cadena La consulta en concreto
     * @return
     */
    public  ResultSet consulta (Statement st, String cadena) {
        ResultSet rs = null;
        try {
            rs = st.executeQuery(cadena);
        } catch (SQLException e) {
            System.out.println("Error con: " + cadena);
            System.out.println("SQLException: " + e.getMessage());
            e.printStackTrace();
        }
        return rs;
    }

    /**
     * Método para realizar consultas de actualización, creación o eliminación.
     *
     * @param st
     * @param cadena La consulta en concreto
     * @return
     */
    public  int actualiza (Statement st, String cadena) {
        int rs = -1;
        try {
            rs = st.executeUpdate(cadena);
        } catch (SQLException e) {
            System.out.println("Error con: " + cadena);
            System.out.println("SQLException: " + e.getMessage());
            e.printStackTrace();
        }
        return rs;
    }

    /**
     * Método para cerrar la consula
     *
     * @param rs
     */
    public  void cerrar(ResultSet rs) {
        if (rs != null) {
            try {
                rs.close();
            } catch (Exception e) {
                System.out.print("Error: No es posible cerrar la consulta.");
            }
        }
    }

    /**
     * Método para cerrar la conexión.
     *
     * @param st
     */
    public  void cerrar(java.sql.Statement st) {
        if (st != null) {
            try {
                st.close();
            } catch (Exception e) {
                System.out.print("Error: No es posible cerrar la conexión.");
            }
        }
    }
}

Codigo de Clase Conectar (con)

0voto

leog.1992 comentado

acabo de aplicar el codigo de medicion de tiempos
resulta
tiempo de conexion:
2169
tiempo de consulta:
159
tiempo de muestra en jtable:
4251

1 Respuesta

2votos

white Puntos75820

Veamos, tienes opciones, a mi se me ocurre lanzar en un hilo aparte y no en el hilo principal la conexion a la base de datos.

al principio de tu aplicacion vas a incluir:

Thread connectThread = new Thread(new Runnable() {
    public void run()
    {
            // conectamos a la base de datos en este hilo
            con.conectar();

            // a modo de interactuar con el usuario
            // agregamos un boton y lo desactivamos
            // se activara cuando la conexion se realize
            boton_ver_empleados.setEnabled(true);
    }
});

connectThread.start(); // iniciamos este hilo

esto crea un nuevo hilo para la conexion, con esto permites que el hilo principal en swing no se congele por la conexion a la base de datos dandote mas velocidad en la carga de la interfaz.

No conozco el codigo de tu metodo initComponents() pero doy por hecho de que inicializas ahí swing y los componentes, recuerda incializarlos al principio de tu aplicacion.

para los metodos frm_ver_empleados y ver_empleado, podrian estar así:

public void frm_ver_empleados()
{
    initComponents();

    mostrar = new DefaultTableModel()  {
        @Override
        public boolean isCellEditable (int fila, int columna) {
            return false;
        }
    };

    ver_empleado();
}

private void ver_empleado ()
{
    LinkedHashMap<String, Integer> columnsProps = new LinkedHashMap<>();
    columnsProps.put("DNI", 80);
    columnsProps.put("Nombre y Apellidos", 300);
    columnsProps.put("Categoria", 90);
    columnsProps.put("Cargo", 200);
    columnsProps.put("Fec. Ingreso", 70);
    columnsProps.put("Contrato", 70);
    columnsProps.put("Fec. Ven. Co.", 70);
    columnsProps.put("Poliza SCTR", 70);
    columnsProps.put("EMO", 70);
    columnsProps.put("Ant. Polic.", 70);
    columnsProps.put("Ant. Penales", 70);
    columnsProps.put("Ant. Judic.", 70);
    columnsProps.put("Estado", 50);

    for (Map.Entry<String, Integer> column : columnsProps.entrySet())
    {
        mostrar.addColumn(column.getKey());
    }

    try
    {
        String query = "SELECT e.dni_col, e.nom_col, cat.descripcion, e.est_col, c.desc_car, "
                     + "cc.fec_ini "
                     + "FROM Colaborador as e "
                     + "INNER JOIN Cargo as c ON(e.idCargo = c.idCargo) "
                     + "INNER JOIN Categoria_Empleado as cat ON(e.idCat_Emp = cat.idCat_Emp) "
                     + "LEFT JOIN Contrato_Colaborador as cc ON(cc.dni_col = e.dni_col) "
                     + "ORDER BY e.nom_col ASC";

        Statement st = con.conexion();
        ResultSet rs = st.executeQuery(query);

        while (rs.next())
        {
            // emp.setDni(rs.getInt("e.dni_col"));

            Object fila[] = new Object[14];
            fila[0]  = rs.getObject("e.dni_col");
            fila[1]  = rs.getObject("e.nom_col");
            fila[2]  = rs.getObject("cat.descripcion");
            fila[3]  = rs.getObject("c.desc_car");
            fila[4]  = "-";
            fila[5] = "NO";
            fila[6] = "-";

            if( rs.getObject("cc.fec_ini") != null )
            {
                fila[5] = "SI";
                fila[6] = rs.getObject("cc.fec_ini");
            }

            fila[7]  = fila[8] = fila[9]
                     = fila[10] = fila[11] = "-";
            fila[12] = rs.getString("e.est_col").equals("1") ? "ACTIVO" : "-";

            tableModel.addRow(fila);
        }

        con.cerrar(st);
        con.cerrar(rs);

        /*ven.centrar_celda(t_empleados, 0);
        ven.centrar_celda(t_empleados, 4);
        ven.centrar_celda(t_empleados, 5);
        ven.centrar_celda(t_empleados, 6);
        ven.centrar_celda(t_empleados, 7);
        ven.centrar_celda(t_empleados, 8);
        ven.centrar_celda(t_empleados, 9);
        ven.centrar_celda(t_empleados, 10);
        ven.centrar_celda(t_empleados, 11);
        ven.centrar_celda(t_empleados, 12);
        tableModel.fireTableDataChanged();*/
    }
    catch (Exception e) { System.out.print(e); }

    int columnIndex = 0;

    for (Map.Entry<String, Integer> column : columnsProps.entrySet())
    {
        t_empleados.getColumnModel().getColumn(columnIndex++).setMinWidth(column.getValue());
    }
}

para no quedarme con la duda, hize una prueba con una base de datos remota, use adicionalmente throttling y como maximo me da 3000 ms en benchmark, lo cual es aceptable y puede variar dependiendo de tu velocidad de conexion, lo que sucede es que al conectar a la base de datos remota, envias y recibes paquetes tomando un pequeño tiempo entre ese lapso, que sucede con mysql workbench o algun software similar, la conexion se mantiene en una instancia, es por eso que en mysql workbench lo ves mucho mas rápido.


Solucion 2

Otra solucion es usar RESTful junto con json, las pruebas fueron notablemente mejor en comparacion que con el driver JDBC.

Hize un script simple en php, el benchmark en la consola me dió entre 500 ms y 1000 ms como máximo

El script php en cuestion es:

get_empleados.php

<?php

function response($message, $error = false)
{
    $output = array(($error ? 'error' : 'data') => $message);

    header('Content-Type: application/json; charset=utf-8');

    die(json_encode($output));
}

$mysqli = new mysqli(
     "servidor",
     "usuario",
     "clave",
     "base de datos"
 );

if ( $mysqli->connect_errno )
{
    response($mysqli->connect_error, true);
}

$result = $mysqli->query("SELECT e.dni_col, e.nom_col, cat.descripcion, e.est_col, c.desc_car, cc.fec_ini
                             FROM Colaborador as e
                             INNER JOIN Cargo as c ON(e.idCargo = c.idCargo)
                             INNER JOIN Categoria_Empleado as cat ON(e.idCat_Emp = cat.idCat_Emp)
                             LEFT JOIN Contrato_Colaborador as cc ON(cc.dni_col = e.dni_col)
                             ORDER BY e.nom_col ASC");

$output = array();

while($row = $result->fetch_assoc())
{
    $empleado = array(
        'dni_col' => $row['dni_col'],
        'nom_col' => utf8_encode($row['nom_col']),
        'descripcion' => $row['descripcion'],
        'est_col' => $row['est_col'],
        'desc_car' => $row['desc_car']
    );

    if ( !empty($row['fec_ini']) )
        $empleado['fec_ini'] = $row['fec_ini'];

    $output[] = $empleado;
}

$result->close();
$mysqli->close();

response($output);

y el método ver_empleado() en tu aplicación:

https://gist.github.com/anonymous/014a7c3fdce1013800ee

reemplazar http://tupagina.com/get_empleados.php por la pagina de tu sitio, donde subiste el fichero php.

0voto

leog.1992 comentado

Gracias brother, son muy buenas tus soluciones, pero en la solucion 2, yo uso swing y es java para escritorio no estoy haciendo un sistema web, como puedo usar el rest para sistemas de escritorio en java.

0voto

white comentado

La solucion 2 sirve tanto para una aplicacion de escritorio como una aplicacion web, de hecho la solucion 2 la probe con swing como dices.

creo que malinterpretaste como funciona el RESTful, la idea es que en el mismo servidor donde tienes tu base de datos, agreges un script PHP o algun script de otro lenguaje, la idea es hacer la consulta en el servidor para hacerlo mas ágil.

olvide mencionarte que para la aplicacion de escritorio necesitas interpretar el codigo JSON, para ello utilize una libreria Json processing de oracle, te dejo el enlace:

https://jsonp.java.net/

0voto

GusGarsaky comentado

No es necesario hacer el REST en PHP. Puedes hacerlo con Java usando Jersey. Y sí será necesario un servidor donde se aloje el REST, te traerá beneficios viéndolo desde una perspectiva arquitectónica.

Por favor, accede o regístrate para responder a esta pregunta.

Otras Preguntas y Respuestas


...

Bienvenido a entre Desarrolladores, donde puedes realizar preguntas y recibir respuestas de otros miembros de la comunidad.

Conecta