2010-08-23 2 views
13

ExecuteNonQuery requiert une connexion ouverte et disponible. L'état actuel de la connexion est fermé.ExecuteNonQuery requiert une connexion ouverte et disponible. L'état actuel de la connexion est fermé.

Qu'est-ce que je fais mal ici? Je suppose que vous pouvez réutiliser la connexion?

Merci pour toute aide!

using (SqlConnection cn = new SqlConnection(ConfigurationManager.ConnectionStrings["LocalSqlServer"].ToString())) 
{ 
    cn.Open(); 

    // If we are reverting to an old type 
    if (pageAction == "revert") 
    { 
     debug.Text = "FLAG 1"; 

     // Get the revert ID 
     int revertingID = int.Parse(Request.QueryString["revID"]); 
     bool rowsReturned = false; 

     debug.Text = "FLAG 2 - " + revertingID.ToString(); 

     // Set all to 0 
     using (SqlCommand cmd = new SqlCommand("SELECT ID FROM tblSiteSettings WHERE ID = " + revertingID, cn)) 
     { 
      // If it exists 
      SqlDataReader rdr = cmd.ExecuteReader(CommandBehavior.CloseConnection); 
      if (rdr.Read()) 
      { 
       rowsReturned = true; 
      } 
      rdr.Close(); 
     } 

     debug.Text = "FLAG 3 - " + rowsReturned.ToString(); 

     // Set new active and reset others 
     if (rowsReturned == true) 
     { 
      using (SqlCommand cmd = new SqlCommand("UPDATE tblSiteSettings SET isActive = 1 WHERE ID = " + revertingID, cn)) 
      { 
       cmd.ExecuteNonQuery(); 
      } 
      using (SqlCommand cmd = new SqlCommand("UPDATE tblSiteSettings SET isActive = 0 WHERE ID <> " + revertingID, cn)) 
      { 
       cmd.ExecuteNonQuery(); 
      } 
     } 
     //debug.Text = "FLAG 4 - "; 
    } 

Répondre

16

Votre problème est:

SqlDataReader rdr = cmd.ExecuteReader(CommandBehavior.CloseConnection); 

Vous devez simplement appeler cmd.ExecuteReader()' si vous souhaitez utiliser la connexion à nouveau avant « se débarrasser "De cela. Si vous voulez comprendre ce que fait la partie CommandBehaviour.CloseConnection, alors la documentation pour SqlCommand.ExecuteReader est un bon pari. Il y a aussi une documentation pour vous dire quelles sont toutes les valeurs possibles du CommandBehaviour enumeration. Essentiellement, CommandBehaviour.CloseConnection effectue les opérations suivantes:

Lorsque la commande est exécutée, l'objet Connection associé est fermé lorsque l'objet DataReader associé est fermé.

Si vous n'avez pas besoin particulier de spécifier un CommandBehaviour, ensuite demander CommandBehaviour.Default, ou ne spécifiez pas du tout. CommandBehaviour.Default est:

La requête peut renvoyer plusieurs jeux de résultats. L'exécution de la requête peut affecter l'état de la base de données. La valeur par défaut ne définit aucun indicateur CommandBehavior. Par conséquent, l'appel de ExecuteReader (CommandBehavior.Default) équivaut fonctionnellement à l'appel de ExecuteReader().

+0

Est-ce que l'instruction Using() ses commandes sont encapsulées dans la fermeture de la connexion quand elle dispose de SqlCommand? – Tommy

+0

@Tommy, pas aussi loin que je sache - la documentation pour SqlCommand.Dispose ne l'appelle pas, donc je suppose que non (http://msdn.microsoft.com/fr-fr/library/system .data.sqlclient.sqlcommand.dispose.aspx) – Rob

+0

Bon appel, si la définition de connexion était enveloppée dans un bloc Using, alors ce serait le cas. http://stackoverflow.com/questions/410222/does-connection-close-when-command-is-disposed-and-the-connection-is-defined-dire – Tommy

5

vous fermez la connexion rdr.Close(); et ne jamais rouvrir avant d'appeler ExecuteNonQuery().

Vous n'avez pas besoin de le fermer du tout s'il est entouré d'un using car l'appel à Dispose() ferme automatiquement la connexion pour vous.

4

Il semble que vous faites une lecture avant de faire votre ExecuteNonQuery. Dans votre premier appel à SqlCommand (pour le SELECT), vous fermez la connexion une fois la lecture terminée. Supprimez le comportement de la commande, vous devriez être bon à aller, ou rouvrir la connexion dans votre prochaine instruction if.

Ce

SqlDataReader rdr = cmd.ExecuteReader(); 

Ou cette

if (rowsReturned == true){ 
    cn.open(); 
1

Ici, votre SqlDataReader fermera la connexion quand il complète:

// Set all to 0 
using (SqlCommand cmd = new SqlCommand("SELECT ID FROM tblSiteSettings WHERE ID = " + revertingID, cn)) 
{ 
    // If it exists 
    SqlDataReader rdr = cmd.ExecuteReader(CommandBehavior.CloseConnection); 
    if (rdr.Read()) 
    { 
     rowsReturned = true; 
    } 
    rdr.Close(); 
} 

Plus tard, la section « Régler nouvelle actif et remis à zéro les autres » échouera, car la connexion est fermée.

2

Ajoutez simplement cn.Open avant de le fermer ou ne le fermez pas.

Questions connexes