L'implementazione di un oggetto DataAdapter (SqlDataAdapter oppure OleDbDataAdapter) consente di aprire e chiudere un oggetto Connection (SqlConnection oppure OleDbConnection), se non è già aperto. L'operazione è utile per un'applicazione in cui è necessario chiamare il metodo Fill per due o più oggetti DataAdapter. Se l'oggetto Connection è già aperto, sarà necessario chiamare esplicitamente il metodo Close o Dispose per chiuderlo.
A riprova di questo discorso, anche è possibile facilmente verificare che nel metodo Fill vengono eseguiti questi due metodi privati della classe base DbDataAdapter:
private static void QuietOpen(IDbConnection connection, out ConnectionState originalState)
{
originalState = connection.State;
if (originalState == ConnectionState.Closed)
{
connection.Open();
}
}
private static void QuietClose(IDbConnection connection, ConnectionState originalState)
{
if ((connection != null) && (originalState == ConnectionState.Closed))
{
connection.Close();
}
}
originalState è lo stato della connessione quando viene richiamato il metodo Fill. Se lo stato iniziale della connessione è ConnectionState.Closed (connessione chiusa), il DataAdapter la apre implicitamente... Quindi quando il metodo Fill ha finito, richiude la connessione se questa è stata aperta implicitamente (lo stato iniziale era ConnectionState.Closed) e se esiste ancora l'istanza.
Se invece quando viene lanciato il metodo Fill la connessione è aperta, originalState vale ConnectionState.Open e la connessione non viene creata visto che c'è già! All'atto di chiusura pertanto la connessione deve continuare a rimanere aperta perchè non è stata creata implicitamente nell'ambito del metodo Fill.
Da questo si capisce che, se la connessione viene aperta prima di lanciare il metodo Fill, deve essere anche chiusa in seguito. Se invece non viene aperta prima, il DataAdapter lo fa da solo e pensa anche alla chiusura in modo totalmente automatico.
Massimomm in un post sul forum mi dice: La connessione è chiusa!, ma se vado a verificare nel database lo stato delle connessioni, questa risulta ancora aperta nel DB!!! ma dopo qualche minuto pero' si disconnette....
A rigor di logica, dipende dal fatto che viene usato un pool di connessioni. Un oggetto Connection viene rimosso dal pool se è scaduto il suo ciclo di vita oppure se si viene a verificare una anomalia. In ogni caso il pooler ispeziona periodicamente i vari pool e rimuove qullo che c'è da rimuovere (ovvero le connessioni scadute o non valide).
Nel caso di connessioni OLEDB è il componente OLEDB service a gestire il pooling. Il lancio del metodo Close o Dispose per una connessione OLEDB esegue il metodo Marshal.ReleaseComObject: questo sta a testimoniare il legame tra l'ambiente managed di ADO.NET e l'ambiente unamanaged sottostante.
Uno spunto di riflessione: l'implementazione di SqlConnection.Close è diversa rispetto a quella di OleDbConnection.Close. Infatti nel caso di SqlConnection vengono usate classi interne (ambiente managed).
Per inserire un commento, devi avere un account.
Fai il login e torna a questa pagina, oppure registrati alla nostra community.
- I design pattern di .NET, il 13 luglio 2005 alle 12:02
- Transazioni con Data Access Application Block: non mi convince!, il 10 gennaio 2005 alle 21:10
- SSL e il degrado di prestazioni nei WS, il 23 novembre 2004 alle 22:40
- Concatenazione dei costruttori di una classe, il 7 settembre 2004 alle 16:07
- .NET e COM: l'unione fa la forza!, il 27 agosto 2004 alle 15:42