2012-09-28 25 views
5

estoy autentificar el usuario como¿Puedo utilizar la conexión JDBC misma, declaración y de resultados de ejecutar dos consultas en JDBC

public static boolean login(DataManager dataManager, String userName, String password) {  
    boolean authenticated = false;  
    Connection connection = dataManager.getConnection();   
    if (connection != null) {   
     try {       
      Statement s = connection.createStatement(); 
      String sql = "query";     
      try {     
       ResultSet rs = s.executeQuery(sql);          
       try {      
        while (rs.next()) {        
         String group_code = rs.getString(1); 
         String orgaunit = rs.getString(2); 

         authenticated = true;        
        } //end of while()      
       } finally {      
        rs.close();      
       }     
      } finally { 
       s.close();     
      } 

     } catch(SQLException e) {    
      //System.out.println("Could not login from dataabse:" + e.getMessage());     
     } finally {    
      dataManager.putConnection(connection);       
     }     
    } //end of if (connection != null)  
    return authenticated;  
} //end of login() 

estoy cerrando la conexión en dataManager.putConnection(connection). Quiero pedirle al usuario que inicie sesión, luego tengo que actualizar el estado del usuario y mantener el historial de registro. ¿Puedo usar algo como esto

try { 
    Statement s = connection.createStatement(); 
    String sql = "query";     
    try {      
     ResultSet rs = s.executeQuery(sql);         
     try { 
      while (rs.next()) {       
       String group_code = rs.getString(1);             
       authenticated = true;        
      } //end of while() 

      if (autherntcated == true) { 
       sql = "query2(update status)"; 
       rs = s.executeQuery(sql); 

       while (rs.next()) { 
        //dos tuff 
       } 

       sql = "anotherQuery"; 
       rs = s.executeQuery(sql); 
       while (rs.next()) { 
        //do stuff 
       } 

      } 

     } finally {      
      rs.close();      
     }      
    } finally { 
     s.close();     
    }     
} catch(SQLException e) { 
    //System.out.println("Could not login from dataabse:" + e.getMessage()); 
} finally {    
    dataManager.putConnection(connection);       
} 

significa usar misma conexión, misma instrucción y la misma conjunto de resultados ejecutar otras consultas o se trata de un enfoque equivocado?

Gracias.

Editar ------------------------------------------- -------------------

if (connection != null) { 
    try { 
     String sql = "query"; 
     PreparedStatement prepStatement = connection.prepareStatement(sql); 
     try { 
      ResultSet rs = prepStatement.executeQuery(sql);     
      try { 
       while (rs.next()) { 
        String group_code = rs.getString(1); 
        authenticated = true; 
       } //end of while() 
      } finally {      
       rs.close();      
      } 
     } finally { 
      prepStatement.close();     
     } 

     /// Addition 
     if (authenticated == true) { 
      updateUser(connection, userName); 
     } 
    } catch(SQLException e) { 
     //System.out.println("Could not login from dataabse:" + e.getMessage()); 
    } finally { 
     dataManager.putConnection(connection); 
    } 
} //end of if (connection != null) 

método de actualización:

private static void updateUser(Connection connection, String userName) { 

    try { 
     String sql = "UPDATE users SET status_code = 'A' WHERE login_id = '" + userName + "'";  
     PreparedStatement prepStatement = connection.prepareStatement(sql); 
     try { 
      int numberOfRowsUpdated = prepStatement.executeUpdate(sql);     
     } finally { 
      prepStatement.close();     
     } 

     maintainHistory(connection); 

    } catch(SQLException e) { 
    //System.out.println("Could not login from dataabse:" + e.getMessage()); 
    } 

} //end of updateUser() 

maintainHistory:

private static void maintainHistory(Connection connection) { 

    try { 
     String sql = "INSERT INTO auditlog_user_logins(user_code,logintime,prstid) VALUES();"; 
     PreparedStatement prepStatement = connection.prepareStatement(sql);   
     try {    
      int numberOfRowsUpdated = prepStatement.executeUpdate(sql);     

     } finally { 

     prepStatement.close();     

     } 

    } catch(SQLException e) { 

     //System.out.println("Could not login from dataabse:" + e.getMessage()); 

    } 

} //end of maintainHistory() 

Respuesta

1

que sugeriría la reutilización conexión porque establ cada vez que intentas consultar tu base de datos puede ser una sobrecarga de rendimiento.

En cuanto a las declaraciones, sugiero cambiar a PreparedStatement. No solo están en la memoria caché, sino que son una buena forma de protegerse de las inyecciones de SQL. Así que construya su consulta de antemano, ejecútelos y finalmente ciérrelos cuando haya terminado. Reutilizar PreparedStatement significaría que está sustituyendo los valores de los parámetros por el mismo PreparedStatement y está ejecutando el mismo.

Así por ejemplo, si usted tiene un PreparedStatement como:

PreparedStatement preparedStatement = connection.prepareStatement("SELECT [col_names] from [table_name] where [col_1_value] = ? and [col_2_value] = ?") 

En este caso, se puede reutilizar los mismos PreparedStatement varias veces por simplemente sustituyendo los nuevos valores de los parámetros. En general, para su caso tendrá múltiples estados preparados. Dado que estas declaraciones se almacenan en caché, no obtendrían un gran impacto en el rendimiento cuando ejecutas el mismo.

Aquí hay un buen tutorial para presentarle PreparedStatement en caso de que usted está en necesidad de una: "Using Prepared Statements"

ResultSets - así que no veo cómo se puede volver a utilizarlo. Ciérralo cuando hayas terminado con ellos. Como por el Javadoc:

Un objeto ResultSet se cierra automáticamente cuando el objeto Statement que la generó está cerrado, vuelve a ejecutar, o se utiliza para recuperar el siguiente resultado de una secuencia de varios resultados.

Sin embargo, asegúrese de cerrar su conexión una vez que haya terminado de usarlo. La reutilización es algo bueno, pero la mala administración de los recursos no es

+0

Quiere decir que puedo cerrar Statement y ResultSet. Me refiero a que una vez que cierre el Statement y el ResultSet, use la actualización y otra consulta de la misma manera y luego cierre la conexión de la base de datos 'dataManager.putConnection (connection); '. ¿Lo es? – Basit

+0

@Basit: actualicé mi respuesta para incluir más información. Lo ideal sería reutilizar su objeto * connection *. ResultSet no tiene sentido y como he especificado, sugiero pasar de * Statement * a * PreparedStatement * – Sujay

+0

Al igual que cuando creo Statement 'Statement s = connection.createStatement();' entonces tengo que cerrarlo. ¿También necesito cerrar el Estado Preparado de la misma manera que lo estoy haciendo con el Estado de Cuenta? Primero estoy creando Statement using connection, luego obtengo 'ResultSet' utilizando' s.executeQuery (query) ', y luego recorro el conjunto de resultados. ¿Cómo puedo reemplazarlo con PreparedStatement? – Basit

4

puedo usar misma conexión JDBC, declaración

Sí. Puede reutilizarlos antes del cierre.

y de resultados

No. La pregunta no tiene sentido. El conjunto de resultados es el resultado de ejecutar una consulta o actualización. No hay duda de volver a usarlo. Imagino que debe cerrar el conjunto de resultados anterior antes de ejecutar la siguiente consulta o actualización.

+0

edito mi código, ¿lo hice en la derecha? manera? – Basit

+0

Parece correcto, pero no está reutilizando ningún 'Statement' o' PreparedStatement' allí, no es que aparentemente lo necesite. – EJP

0

Respondido diferente Caso de prueba con la misma pregunta.

¿Puedo usar misma JDBC de conexión, Statement y ResultSet para ejecutar dos consultas en JDBC

No podemos reutilizar la conexión, Statement y ResultSet en paralelo o concurrente de la siguiente manera:

Connection con = databaseConnector.getConnection(); 
PreparedStatement stmt1=con.prepareStatement("select * from emp"); 
ResultSet rs1=stmt.executeQuery(); 
while(rs1.next()){ // get SQLException in second iteration 
System.out.println(rs1.getInt(1)+" "+rs1.getString(2)); 
    //As soon as you execute the following query, the previous Statement and ResultSet are implicitly closed. 
    // to resolve we the problem, we should not use the above used Connection. We have to use new Connection. 
    PreparedStatement stmt2=con.prepareStatement("select * from address"); 
    ResultSet rs2=stmt2.executeQuery(); 
    System.out.println(rs2.getString(1)+" "+rs2.getString(2)); 

} 
  • Cerrando un Connection cierra un Statement, cuando Statement cerrado cierra implícitamente ResultSet también.
  • Cerrando un Statement cierra un ResultSet pero no la conexión.
  • Cerrando un ReultSet solo se cierra solo, no Statement.
  • De forma predeterminada, solo un ResultSet por Statement se puede abrir al mismo tiempo.

Mejor Práctica:

  • Las conexiones no es seguro para subprocesos, por lo compartirlos a través de peticiones no es una buena idea.
  • Abrir una conexión de base de datos es un costoso, debe utilizar un ConnectionPool para compartir conexiones.
  • Cierre ResultSet tan pronto como termine de trabajar con ResultSet.
Cuestiones relacionadas