连接字符串中,有Pooling关键字,默认情况下其值为true,即支持连接池技术。如果不想支持连接池技术,可以显式地将其赋值为false。
另外Max Pool Size, Min Pool Size为池允许的最大和最小连接数。
连接池就是一个容器,它存放了一定数量的与数据库服务器的物理连接。因此,当我们需要连接数据库服务器的时候,只需去池(容器)中取出一条空闲的连接,而不是新建一条连接。
比如:对Connection调用Close或Dispose时,连接被释放回池中,而跟数据库的物理连接并没有断掉。连接池一旦创建,直到活动进程终止时才会被毁坏。 所以sqlConnection.Closle()和sqlConnection.Dispose()并不会关掉数据库的物理连接。
连接池标识
连接池是由进程、应用程序域、连接字符串以及windows标识(在使用集成的安全性时)共同组成签名来标识区分的。但对于同一应用程序域来说,一般只由连接字符串来标识区分。
当打开一条连接时,如果该条连接的类型签名与现有的连接池类型不匹配,则创建一个新的连接池。反之,则不创建新的连接池。
举例说明,如下:
//构造连接字符串
SqlConnectionStringBuilder connStr = new SqlConnectionStringBuilder();
connStr.DataSource = "192.168.1.20";
connStr.InitialCatalog = "rzerp_zjsy";
connStr.UserID = "developer";
connStr.Password = "developer";
//创建连接对象1
using (SqlConnection conn1 = new SqlConnection(connStr.ConnectionString))
{
conn1.Open();
if (conn1.State == ConnectionState.Open)
{
Console.WriteLine("\nDatabase is linked.");
Console.WriteLine("\nDataSource:{0}", conn1.DataSource);
Console.WriteLine("\nDatabase:{0}", conn1.Database);
}
}
//创建连接对象2
connStr.InitialCatalog = "master";
using (SqlConnection conn2 = new SqlConnection(connStr.ConnectionString))
{
conn2.Open();
if (conn2.State == ConnectionState.Open)
{
Console.WriteLine("\nDatabase is linked.");
Console.WriteLine("\nDataSource:{0}", conn2.DataSource);
Console.WriteLine("\nDatabase:{0}", conn2.Database);
}
}
//创建连接对象3
connStr.InitialCatalog = "rzerp_zjsy";
using (SqlConnection conn3 = new SqlConnection(connStr.ConnectionString))
{
conn3.Open();
if (conn3.State == ConnectionState.Open)
{
Console.WriteLine("\nDatabase is linked.");
Console.WriteLine("\nDataSource:{0}", conn3.DataSource);
Console.WriteLine("\nDatabase:{0}", conn3.Database);
}
}
SQL Server端连接数与客户端连接池关系
1,准备
SQL Server 服务端的并发连接数可以设置:如下所示:
exec sp_configure 'user option' ,0
reconfigure
查看数据库设置的最大连接数,run_value=0(为0默认最大值32767)
2,客户端测试程式,其代码如下:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;
using System.Data.SqlClient;
namespace connPools
{
class Program
{
static void Main(string[] args)
{
int maxCount = 40000;
//构建连接字符串
SqlConnectionStringBuilder connStr = new SqlConnectionStringBuilder();
connStr.DataSource = "192.168.1.20";
connStr.InitialCatalog = "rzerp_zjsy";
connStr.UserID = "developer";
connStr.Password = "developer";
connStr.Pooling = true;
connStr.MaxPoolSize = 40000;
connStr.MinPoolSize = 1;
connStr.ConnectTimeout = 15;
string connstring = connStr.ConnectionString;
List<SqlConnection> collection = new List<SqlConnection>();
for (int i = 0; i < maxCount; i++)
{
try
{
var sqlConn = new SqlConnection(connstring);
sqlConn.Open();
collection.Add(sqlConn); //保存连接对象
Console.WriteLine(string.Format("已创建连接对象{0}", i));
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
}
}
}
}
为了验证关系,我们配置个测试用例,设置max poolsize = 100,即连接池100,数据库3000 (语法:exce SP_)
查询客户端连接到数据库的信息:
SELECT [program_name] ,[spid] FROM [sys].[sysprocesses] WHERE[spid]>50
用例安排:
测试用例一:设置max poolsize=40000,即连接池40000,数据库32767
测试用例二:设置max poolsize=3000,即连接池3000,数据库32767
测试用例三:设置max poolsize=40000,即连接池40000,数据库3000
观察结果如下: