Les connexions Oracle de ne pas fermer
Nous avons ASP.NET application qui se connecte à la base de données oracle avec odp.net.
Dernièrement, nous avons commencé à connu quelques problèmes de performances. Il semble que les connexions Oracle ne fermez pas et finit par s'accumuler jusqu'à ce qu'il crash de notre site web.
Comme une première étape, nous avons fait une revue de code et nous avons fait en sorte qu'on ferme toutes les connexions ouvertes après l'exécution.
OracleConnection cn = Helpers.ConnectToDB();
try
{
cn.Open();
//do somtehing
}
catch (Exception ex)
{
//log error
}
finally
{
cn.Close();
cn.Dispose();
}
mais cela n'a pas aidé, toutes les quelques heures, les connexions s'accumulent dans le crash de notre site web.
Voici les connexions journal d'hier:
TO_CHAR(DATE_TIME,'DD/MM/YYYY MACHINE STATUS CONNECTIONS
19/01/2012 14:40:03 WORKGROUP\OTH-IIS-1 ACTIVE 1
19/01/2012 14:38:00 WORKGROUP\OTH-IIS-1 ACTIVE 2
19/01/2012 14:35:57 WORKGROUP\OTH-IIS-1 ACTIVE 2
19/01/2012 14:34:55 WORKGROUP\OTH-IIS-1 ACTIVE 28
19/01/2012 14:33:54 WORKGROUP\OTH-IIS-1 ACTIVE 26
19/01/2012 14:31:51 WORKGROUP\OTH-IIS-1 ACTIVE 34
19/01/2012 14:30:49 WORKGROUP\OTH-IIS-1 ACTIVE 96
19/01/2012 14:29:47 WORKGROUP\OTH-IIS-1 ACTIVE 73
19/01/2012 14:28:46 WORKGROUP\OTH-IIS-1 ACTIVE 119
19/01/2012 14:27:44 WORKGROUP\OTH-IIS-1 ACTIVE 161
19/01/2012 14:26:43 WORKGROUP\OTH-IIS-1 ACTIVE 152
19/01/2012 14:25:41 WORKGROUP\OTH-IIS-1 ACTIVE 109
19/01/2012 14:24:40 WORKGROUP\OTH-IIS-1 ACTIVE 74
19/01/2012 14:23:38 WORKGROUP\OTH-IIS-1 ACTIVE 26
19/01/2012 14:22:36 WORKGROUP\OTH-IIS-1 ACTIVE 2
19/01/2012 14:21:35 WORKGROUP\OTH-IIS-1 ACTIVE 2
Crash point eu lieu à 14:27:44 et après le redémarrage de l'application des connexions commencé à tomber.
la chaîne de connexion à utiliser est:
<add name="OracleRead" connectionString="Data Source=xxx;User Id=yyy;Password=zzz;Max Pool Size=250;Connection Timeout=160;" providerName="Oracle.DataAccess"/>
Alors quel est le problème ici?
Faire nous avons besoin de définir ou de modifier l'une de ces propriétés:
Connection Lifetime, Decr Pool Size, Max Pool Size, Min Pool Size?
Qu'est-ce que les paramètres recommandés dans cette situation?
Mise en commun=True (valeur par défaut)
Avez-vous réussi à résoudre ce problème?
Viens avec un mi-chemin de la solution, fondamentalement, efface les autres séances, voir ma réponse.
OriginalL'auteur baba-dev | 2012-01-20
Vous devez vous connecter pour publier un commentaire.
Vous devez explicitement supprimer tous les Oracle.DataAccess objets, y compris les Connexions, les Commandes et les Paramètres.
Voir l'exemple de code dans les commentaires ici:
https://nhibernate.jira.com/browse/NH-278
Quelques autres remarques:
OriginalL'auteur Martin Suchanek
Je sais que cette question est assez vieux, mais j'ai trouvé une solution qui semble fonctionner pour moi.
Ma solution est d'appeler un ASHX gestionnaire qui renvoie alors une image, en moyenne, ce service est appelé entre 10 à 14 fois par la page de chargement de certaines pages.
Je suis en utilisant le ODP.NET Oracle.DataAccess.Espace de noms du Client V4.112.3.60 pour la version 64 bits.
J'ai tout mon code en utilisant des déclarations (l'obscurcissement):
J'ai essayé beaucoup de choses:
Mais quand il est venu à pas à pas dans le code que j'ai trouvé que, parfois, le code ne serait pas atteint à la fin de l'utilisation de bloc et de la prochaine demande de venir dans le gestionnaire avant de pouvoir atteindre la fin (je devine quelque chose à faire avec max les demandes de gestionnaire?) ainsi, des séances d'être laissé ouvert dans V$SESSION que j'ai eu à fermer manuellement.
Je suis tombé sur ce morceau de code:
Et essayé de courir, mais les séances sont laissées en suspens par le gestionnaire, au moins ce serait fermée par le présent code, actuellement, il s'exécute à la fin de l'utilisation de bloc pour la OracleConnection (donc à chaque fois que le service est appelé, il efface les piscines, c'est en espérant que le gestionnaire gère pour l'exécution de cette mesure!).
Donc, en utilisant la ClearAllPools méthode semble fonctionner, mais je sais que c'est pas la solution idéale.
J'ai eu le même problème. Lorsque j'appelle le PS à oracle, il crée 40+ processus lors de la rentrée de la Session du navigateur. Il n'est pas clair, même après l'utilisation de "l'aide" ou "oracleConnection.close() et dispose()". Donc, temporairement, j'ai eu à utiliser OracleConnection.ClearPool(oraConn). Merci pour votre code. Pendant ce temps, avez-vous trouvé une autre solution ou le problème?
Non, ce qui m'a pris si longtemps pour en arriver au fait que j'ai un peu manqué de temps pour trouver un moyen d'améliorer cela. Je me demande ce que le coût de la ressource est d'appeler ClearAllPools() sur le OracleCOnnection objet chaque fois que nous faisons un db appel... j'aurais presque tendance à penser que c'était quelque chose dans mon code, mais il semblait assez serré, la seule raison pour laquelle je dirais que c'est parce que je n'ai pas trouvé quelqu'un d'autre avec le même problème.
dans mon cas, nous avons compris le problème. Il n'était pas avec le code c# ou les procédures stockées. Lorsque la base de données a été actualisé avec les nouvelles données, les Administrateurs de bases de données ont donner quelques indices comme index en parallèle dans les tableaux qui manquait. Après leur avoir donné, le processus a redcued et n'a pris que 1.,
soupir j'ai quitté le lieu de travail, où cette question est originaire, mais quand j'ai parlé aux Administrateurs de bases de données ils ont juste blâmé sur le code. Moi étant un newbie de l'équipe, ils ne voulaient pas prendre quoi que ce soit d'autre.
OriginalL'auteur Robbie
Assurez-vous d'envelopper toutes les connexions dans un try/finally bloc. Il ne suffit pas d'appel .Close() pour chaque .Open(). Vous devez placer le .Appel Close() dans le bloc finally. La façon la plus simple de faire cela est de créer des connexions avec l'aide du bloc.
Ce n'est pas encore clair pour moi que vous l'avez fait à droite. Votre commentaire donne l'impression que le try/catch/finally se produire que après de l'exécution de votre requête, et couvre la
.Close()
appel. L'exécution de la requête être à l'intérieur de latry
bloc, et le.Close()
appeler être à l'intérieur de l'correspondantfinally
bloc. Si c'est le cas, assurez-vous que c'est clairement en train de modifier dans votre question initiale. Je pense que vous n'avez probablement que la droite, mais j'ai besoin d'être certain avant que nous puissions commencer à regarder d'autres questions. Si cela est faux, même dans un endroit, il est presque certainement le coupable.Joel - voir mon edit.
OriginalL'auteur Joel Coehoorn
Essayer d'emballage de votre utilisation de
OracleConnection
à l'intérieur d'un bloc using (si vous êtes à l'aide de C#):Qui sera assurez-vous qu'il est correctement réglé lorsque vous avez terminé de l'utiliser.
OracleConnection
etOracleDataReader
(autre exemple) de mettre en œuvreIDisposable
, et doit donc être utilisé à l'intérieur d'unusing
déclaration.OriginalL'auteur GriffeyDog