Newsgroup: it.comp.java
Titolo: Consiglio su connessioni al db....

Consiglio su connessioni al db....  Inviato:29-ott-2006 12.17
  Rispondi
Salve ragazzi,
vorrei chiedervi un consiglio,più che un aiuto pratico.
Ho realizzato un'applicazione jsf con connessioni al database tramite
datasource di Tomcat 5.5.
La mia domanda è questa.
Sono inesperto in materia e un vostro aiuto potrebbe aiutarmi tanto.
Questo è una mia classe generica,che serve solo per aggiungere un
elemento ad una lista o per rimuoverlo.
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import javax.faces.application.FacesMessage;
import javax.faces.context.FacesContext;
import javax.faces.event.ActionEvent;
import javax.sql.DataSource;
public class Organism extends BaseBean{
private String organismName;
public String getOrganismName(){
return organismName;
}
public void setOrganismName(String organismName){
this.organismName=organismName;
}
public String newOrganism() {
Statement stmt = null;
PreparedStatement pst = null;
ResultSet rs = null;
Connection conn=null;
try {
DataSource dataSource = Singleton.getInstance().getDataSource();
conn = dataSource.getConnection();
if (conn != null) {
stmt = conn.createStatement();
String query = "SELECT * FROM organismo "
+ "WHERE NomeOrganismo = '" + organismName + "' ";
rs = stmt.executeQuery(query);
...........
catch (Exception z) {
z.printStackTrace();
} finally {
try {
if (rs != null)
rs.close();
} catch (SQLException z) {
}
;
try {
if (conn != null)
conn.close();
} catch (SQLException z) {
}
;
try {
if (stmt != null)
stmt.close();
} catch (SQLException z) {
}
;
}
Questa è la mia classe Singleton per la connessione al db
import javax.naming.Context;
import javax.naming.InitialContext;
public class Singleton {
private static Singleton singleton = null;
private static javax.sql.DataSource ds = null;
static {
try {
Context ctx = new InitialContext();
if (ctx == null) {
throw new Exception("No Context");
}
ds = (javax.sql.DataSource) ctx.lookup("java:comp/env/MysqlJNDI");
} catch (Exception e) {
e.printStackTrace();
}
}
public static Singleton getInstance() {
if (singleton == null) {
singleton = new Singleton();
}
return singleton;
}
public javax.sql.DataSource getDataSource() {
return ds;
}
}
DOMANDA
Conviene creare una connessione prima di ogni operazione o crearne una
nella sessione e usare sempre la stessa per ogni utente?
Io ho optato per creare una connessione per ogni operazione,so che è
dispendioso ma ho settato un timeout con tomcat per cui una connessione
inattiva per esempio per 60 s viene chiusa e riciclata....è una scelta
giusta?
Mi aiutate a capire con semplice codice,se devo apportare modifiche?
Grazie mille per la vostra disponibilità e professionalità.

>nella sessione e usare sempre la stessa per ogni utente?
Più che conviene, si deve fare così. Infatti le specifiche impongono che 
ogni connessione utilizzata in una richiesta di servizio ad una servlet, 
venga chiusa prima che l'invocazione della servlet termini. Da qui l'utilità 
dei pool di connessioni, che rendo praticamente nullo l'overhead per la 
creazione di nuove connessioni.
Scorpio. 

Scorpio ha scritto:

Ciao scusa, non si capisce la risposta, il tuo "Più che conviene, si 
deve fare così" si riferisce alla prima parte o alla seconda parte della 
frase di gbattine? Conviene creare una connessione per ogni operazione?
Grazie, ciao
Cor

 Grazie, ciao
Hai ragione, scusa... intendevo: per ogni operazione occorre creare una 
connessione, e poi rilasciarla al pool. Intendiamoci , perň, sul. termine 
operazione: con "operazione" intendo una chiamata a metodo, non importa 
quanto complessa. Per esempio un singolo metodo potrebbe usare una ed una 
sola connessione per eseguire una select, un'update ed una insert:
Connection conn = pool.getConnection();
eseguiQuery(conn);
eseguiUpdate(conn);
eseguiInsert(conn);
conn.close();
e non:
Connection conn = pool.getConnection();
eseguiQuery(conn);
conn.close();
conn = pool.getConnection();
eseguiUpdate(conn);
conn.close();
conn = pool.getConnection();
eseguiInsert(conn);
conn.close();
In questo caso intendo come "operazione" una "transazione locale" su un 
database, che puo' coinvolgere n operazioni sulla base dati.
Scorpio 

 conn.close();
NO :D !
Solitamente:
   Connection conn = pool.getConnection();
   try {
     eseguiQuery(conn);
     eseguiQuery(conn);
     eseguiQuery(conn);
   } catch {
     ...
   } finally {
     conn.close();
   }
E' buona cosa chiudere le risorse con un finally, cosi' da evitare che 
restino aperte in caso di exception. Lo stesso puo' valere per 
PreparedStatements e ResultSets.
-- 
Giambo - Occhio al filtro antispam _e_ alla whitelist !


Verissimo !! ... ma quel che mi premeva era spiegare cosa intendevo per 
"singola operazione", tralasciando il "dettaglio" (che tale non è) del 
garantire il rilascio delle risorse (connessioni e compagnia bella) :-)
Ciao,
    Scorpio.