2010-09-05 6 views
12

ho trovato questo pezzo di codice in una sola applicazioneC# DbConnection cast SqlConnection

Database database = DatabaseFactory.CreateDatabase("connection string"); 
DbConnection connection = database.CreateConnection(); 
connection.Open(); 
SqlConnection sqlConnection = (SqlConnection)connection; 

E 'sicuro, derieve SqlConnection da DbConnection. Il database proviene da Microsoft.Practices.EnterpriseLibrary.Data. Secondo la documentazione, CreteDatabase restituisce DbConnection.

risposta

11

No, non è sicuro, la fusione non è mai al sicuro e può saltare in qualsiasi momento mentre l'applicazione è in esecuzione. Mentre SqlConnection deriva effettivamente da DbConnection non è garantito che database.CreateConnection() restituirà un valore SqlConnection in quanto potrebbe essere parametrizzato nel file di configurazione. Inoltre, perché devi trasmettere a SqlConnection? È sempre meglio lavorare con classi che sono più in alto nella gerarchia per evitare di accoppiare il codice con un'implementazione specifica che renderà il tuo codice impossibile da testare da solo.

Mentre EnterpriseLibrary fa un lavoro decentemente buono nel mantenere le cose astratte, stai uccidendo tutto con questo cast. Inoltre, è necessario assicurarsi che le risorse disponibili siano sempre smaltite correttamente. Che ne dite di questo, invece:

Database database = DatabaseFactory.CreateDatabase("connection string"); 
using (var conn = database.CreateConnection()) 
using (var cmd = conn.CreateCommand()) 
{ 
    conn.Open(); 
    cmd.CommandText = "SELECT id FROM foo"; 
    using (var reader = cmd.ExecuteReader()) 
    { 
     while (reader.Read()) 
     { 
      // TODO: work with the results here 
     } 
    } 
} 

In questo modo il codice è meno fragile di modifiche del database nel file di configurazione. Beh, certo, hai ancora questo codice SQL hardcoded e ci sono ORM che si prenderanno cura di questa situazione. Ti consentiranno inoltre di concentrarti sul vero dominio della tua applicazione invece di perdere tempo scrivendo query SQL e trasmettendo da un provider di database a un altro. Ma per una semplice applicazione questo è OK.

+0

Esiste un metodo utilizzato in questo codice che richiede SqlConnection come parametro – Darqer

7

Deve essere sicuro fino a quando non si modifica la stringa di connessione per connettersi a un database diverso da SQL Server. Se questo è sempre una possibilità, allora si dovrebbe aggiungere un po 'più logica per rendere le cose sicure:

Database database = DatabaseFactory.CreateDatabase("conn string"); 

using(DbConnection conn = database.CreateConnection()) 
{  
    if(conn is SqlConnection) 
    { 
     var sqlConn = conn as SqlConnection; 
    } 
} 
+0

Non una grande differenza, usare 'come' senza 'è' e quindi verificare il null è più efficiente. –

4

Dipende dai database che si utilizzano nella propria applicazione. Dal codice che hai scritto sembra che venga utilizzato solo SQL Server. Se è così, allora puoi trasmettere DbConnection a SqlConnection in modo sicuro. Infatti, DbConnection è una classe base per qualsiasi altra connessione al database. Nel tuo caso è SqlConnection (che è usato per lavorare con il database SQL Server), ci sono anche diversi database come Oracle, Mysql, ecc. Ei loro provider di solito hanno classi proprie per le connessioni. Quindi, se la tua app utilizza un altro database o potrebbe essere utilizzata in futuro, non è sicuro avere tale cast.

+2

, non solo dipende dal database utilizzato ma, più direttamente, dipende dal tipo che la fabbrica restituisce in base al database in uso. Se avessero mai deciso di creare una nuova classe di connessione che funzionasse con SQL server, il codice poteva fallire –