2010-08-10 4 views
2

J'ai cette méthode:est une méthode statique en utilisant les mêmes variables pour les appels différents

public static IEnumerable<T> ExecuteReaderSp<T>(string sp, string cs, object parameters) where T : new() 
    { 
     using (var conn = new SqlConnection(cs)) 
     { 
      using (var cmd = conn.CreateCommand()) 
      { 
       cmd.CommandType = CommandType.StoredProcedure; 
       cmd.CommandText = sp; 
       cmd.InjectFrom<SetParamsValues>(parameters); 
       conn.Open(); 
       using (var dr = cmd.ExecuteReader()) 
        while (dr.Read()) 
        { 
         var o = new T(); 
         o.InjectFrom<ReaderInjection>(dr); 
         yield return o; 
        } 
      } 
     } 
    } 

J'ai eu la situation quand je l'ai appelé à l'époque (avec différents T et sp) dans un « champ d'opération »

et si je ne demande pas .ToArray() sur l'appel de poing que j'ai eu une erreur qui me dit que cette commande est déjà associé à un autre DataReader et que le premier devrait être fermé d'abord

Répondre

3

Comme il est dans un champ de transaction, je suis sûr que ADO.Net fournit la même connexion physique à la base de données, mais je pense que le texte cette commande est déjà associé est un faux - essayer en ajoutant MultipleActiveResultSets=True à votre chaîne de connexion. La situation que vous rencontrez ici est que les fonctions yield return ne sont pas complètement évaluées tant que les objets IEnumerable ne sont pas complètement utilisés - et que SqlConnections, par défaut, n'autorise qu'un seul DataReader à être actif contre eux à la fois.

Aussi, j'applaudis votre utilisation appropriée de l'utilisation des instructions - mais sachez que rien ne sera mis au rebut jusqu'à ce que vous marchiez le IEnumerable entier. (C'est ce que fait ToArray() pour que tout fonctionne.)

Questions connexes