In addition to Weibo, there is also WeChat
Please pay attention
WeChat public account
Shulou
2025-04-03 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >
Share
Shulou(Shulou.com)06/02 Report--
This article mainly explains "how to close the ADO.NET connection pool". The content in the article is simple and clear, and it is easy to learn and understand. Please follow the editor's train of thought to study and learn how to close the ADO.NET connection pool.
You are no stranger to ADO.NET connection pooling. However, .NET programmers who have used ADO.NET connection pooling many times do not necessarily understand it in depth. The specific reasons are:
Connection pooling is provided in ADO.NET, and most developers rarely set it because it is the default.
The interface settings are as follows:
It is also easy to turn off connection pooling, as shown in the connection string:
Data Source= (local); Initial Catalog=AdventureWorks;Integrated Security=SSPI;Pooling=False
But what is the nature of connection pooling?
With Reflector, open the setting value of the ConnectionString property of System.Data.SqlClient.SqlConnection as follows:
Private void ConnectionString_Set (string value) {DbConnectionOptions userConnectionOptions = null; DbConnectionPoolGroup group = this.ConnectionFactory.GetConnectionPoolGroup (value, null, ref userConnectionOptions); DbConnectionInternal innerConnection = this.InnerConnection; bool allowSetConnectionString= innerConnection.AllowSetConnectionString; if (allowSetConnectionString) {allowSetConnectionString= this.SetInnerConnectionFrom (DbConnectionClosedBusy.SingletonInstance, innerConnection); if (allowSetConnectionString) {this._userConnectionOptions = userConnectionOptions; this._poolGroup = group This._innerConnection = DbConnectionClosedNeverOpened.SingletonInstance;}} if (! allowSetConnectionString) {throw ADP.OpenConnectionPropertySet ("ConnectionString", innerConnection.State);} if (Bid.TraceOn) {string str = (userConnectionOptions! = null)? UserConnectionOptions.UsersConnectionStringForTrace (): "; Bid.Trace ("% dumped,'% ls'\ n ", this.ObjectID, str);}}
Then connect to the red GetConnectionPoolGroup method, as follows
Internal DbConnectionPoolGroup GetConnectionPoolGroup (string connectionString, DbConnectionPoolGroupOptions poolOptions, ref DbConnectionOptions userConnectionOptions) {DbConnectionPoolGroup group; if (ADP.IsEmpty (connectionString)) {return null;} if (! this._connectionPoolGroups.TryGetValue (connectionString, out group) | | (group.IsDisabled & & (group.PoolGroupOptions! = null) {DbConnectionOptions options = this.CreateConnectionOptions (connectionString, userConnectionOptions) If (options = null) {throw ADP.InternalConnectionError (ADP.ConnectionError.ConnectionOptionsMissing);} string str = connectionString; if (userConnectionOptions = = null) {userConnectionOptions = options; str = options.Expand () If (str! = connectionString) {return this.GetConnectionPoolGroup (str, null, ref userConnectionOptions);}} if ((poolOptions = = null) & & ADP.IsWindowsNT) {if (group! = null) {poolOptions = group.PoolGroupOptions } else {poolOptions = this.CreateConnectionPoolGroupOptions (options);}} DbConnectionPoolGroup group2 = new DbConnectionPoolGroup (options, poolOptions) {ProviderInfo = this.CreateConnectionPoolGroupProviderInfo (options)}; lock (this) {Dictionary dictionary = this._connectionPoolGroups If (! dictionary.TryGetValue (str, out group)) {Dictionary dictionary2 = new Dictionary (1 + dictionary.Count); foreach (KeyValuePair pair in dictionary) {dictionary2.Add (pair.Key, pair.Value);} dictionary2.Add (str, group2); this.PerformanceCounters.NumberOfActiveConnectionPoolGroups.Increment () Group = group2; this._connectionPoolGroups = dictionary2;} return group;}} if (userConnectionOptions = = null) {userConnectionOptions = group.ConnectionOptions;} return group;}
TryGetValue is to determine whether there is a connection whose connection string is connectionString. If it is returned to group, if it does not exist, call CreateConnectionOptions to create a DbConnectionOptions,***
Lock (this) {Dictionary dictionary = this._connectionPoolGroups; if (! dictionary.TryGetValue (str, out group)) {Dictionary dictionary2 = new Dictionary (1 + dictionary.Count); foreach (KeyValuePair pair in dictionary) {dictionary2.Add (pair.Key, pair.Value) } dictionary2.Add (str, group2); this.PerformanceCounters.NumberOfActiveConnectionPoolGroups.Increment (); group = group2; this._connectionPoolGroups = dictionary2;} return group;}
This code is put into the connection pool, and here, as you might see, the connection pool for ado.NET is essentially a collection of Dictionary generics.
The so-called connection pool is a collection related to the connection object Connection, which is not just a simple collection, but has a certain mechanism inside. When we do development, we may establish the Connection connection object, close the connection object, and sometimes call Dispose to release the connection. The next time you use it, re-instantiate a connection. However, connections in the pool are not released with the Close or Dispose of the connection object. If the connection is re-established the next time and the connection string is exactly the same as the previous one, the connection pool will assign the last available connection object to the connection for use. If the two connection strings are a little different, even if there is an extra space in a certain place, the connection pool will not think of it as the same connection, which Microsoft may only compare the two strings directly internally instead of comparing the key values of the connection database strings to match each other.
The advantage of connection pooling is that it retains the connection object, preventing it from instantiating a connection object from scratch next time.
String constr1 = "Data Source= (local); Initial Catalog=AdventureWorks;Integrated Security=SSPI;"; string constr2 = "Data Source= (local); Initial Catalog=Pubs;Integrated Security=SSPI;"; string AssMark = "System.Data,Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"; Assembly ass = Assembly.Load (AssMark); Type SqlConType = null; foreach (Type conType in ass.GetExportedTypes ()) {Console.WriteLine (conType. ToString ()) If ("System.Data.SqlClient.SqlConnection" = = conType.ToString ()) {SqlConType = conType;}} if (SqlConType! = null) {Type [] types1 = new Type [0]; ConstructorInfo constructorInfoObj1 = SqlConType.GetConstructor (BindingFlags.Instance | BindingFlags.Public, null, CallingConventions.HasThis, types1, null); SqlConnection con1 = (SqlConnection) constructorInfoObj1.Invoke (null); con1.ConnectionString = constr1 SqlConnection con2 = (SqlConnection) constructorInfoObj1.Invoke (null); con2.ConnectionString = constr2; PropertyInfo PI = SqlConType.GetProperty ("PoolGroup", BindingFlags.Instance | BindingFlags.NonPublic); object poolGroup1 = PI.GetValue (con1, null); object poolGroup2 = PI.GetValue (con2, null);}
(explanation: it may be very simple to find the result, but it takes a lot of effort, almost 5 hours, to find the result, so give a brief account of the process of finding the result:
At first, I use Reflector to find that there is a property of PoolGroup in SqlConnection, so I want to compare this property of two SqlConnection objects at run time, but because the access modifier of this property is internal, it cannot be accessed directly, only with reflection. The code (optimized) is as follows:
Then set a breakpoint on the reciprocal * * line to compare the difference between poolGroup1 and poolGroup2. It is found that when the connection string is the same, the _ objectID of the two objects is the same, and the string will be a little different. This indicates that the connection pool is compared by the string itself, not by the key-value pairs in the string. It is also found that when the ConnectionString of con1 and con2 is not assigned, these two objects are both null, which shows that the key is the ConnectionString assignment, so we started to use Reflector to view the assignment method of this property, and there is the above code.
Thank you for reading, the above is the content of "how to close the ADO.NET connection pool". After the study of this article, I believe you have a deeper understanding of how to close the ADO.NET connection pool, and the specific use needs to be verified in practice. Here is, the editor will push for you more related knowledge points of the article, welcome to follow!
Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.
Views: 210
*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.
Continue with the installation of the previous hadoop.First, install zookooper1. Decompress zookoope
"Every 5-10 years, there's a rare product, a really special, very unusual product that's the most un
© 2024 shulou.com SLNews company. All rights reserved.