1. <strong id="7actg"></strong>
    2. <table id="7actg"></table>

    3. <address id="7actg"></address>
      <address id="7actg"></address>
      1. <object id="7actg"><tt id="7actg"></tt></object>

        如何主動(dòng)清空.NET數(shù)據(jù)庫(kù)連接池?

        共 8008字,需瀏覽 17分鐘

         ·

        2021-08-16 12:36


              一般我們的項(xiàng)目中會(huì)使用1到2個(gè)數(shù)據(jù)庫(kù)連接配置,同程藝龍的數(shù)據(jù)庫(kù)連接配置被收攏到統(tǒng)一的配置中心,由DBA統(tǒng)一維護(hù),業(yè)務(wù)方通過(guò)某個(gè)配置字符串拿到的是開(kāi)箱即用的Connection對(duì)象。

             DBA能在對(duì)業(yè)務(wù)方無(wú)侵入的情況下,給業(yè)務(wù)方切換備份數(shù)據(jù)庫(kù),之后DBA要求舊連接池必須立即被清空。

        那么問(wèn)題來(lái)了: 不能立即清空.NET連接池?注意我用得是清空,而不是釋放連接。

        如果有同學(xué)不知道DBA做這個(gè)要求的目的,那我啰嗦一下:


        應(yīng)用程序不再使用舊連接時(shí),理論上你的連接池要被完全清空,因?yàn)閱渭兊尼尫胚B接,只會(huì)讓連接池中的Connection處于Sleep狀態(tài),依舊維持了短時(shí)間的物理連接,這個(gè)短時(shí)間其實(shí)是不必要的占用,影響了舊連接數(shù)據(jù)庫(kù)的吞吐量。


        連接池知識(shí)背景



        回答這個(gè)問(wèn)題之前, 我們還是先研究一下.NET數(shù)據(jù)庫(kù)連接池。

        1. .NET數(shù)據(jù)庫(kù)連接池的背景

        數(shù)據(jù)庫(kù)連接是一個(gè)耗時(shí)的行為,大多數(shù)應(yīng)用程序只使用1到幾種數(shù)據(jù)庫(kù)連接,為了最小化打開(kāi)連接的成本,ado.net使用了一種稱(chēng)為連接池的優(yōu)化技術(shù)。

        2. .NET 數(shù)據(jù)庫(kù)連接池的表現(xiàn)

        數(shù)據(jù)庫(kù)連接池減少了必須打開(kāi)新連接的次數(shù),池程序維護(hù)了數(shù)據(jù)庫(kù)物理連接。

        通過(guò)為每個(gè)特定的連接配置保持一組活動(dòng)的連接對(duì)象來(lái)管理連接。

        每當(dāng)應(yīng)用程序嘗試Open連接,池程序就會(huì)在池中找到可用的連接,如果有則返回給調(diào)用者;
        應(yīng)用程序Close連接對(duì)象時(shí),池程序?qū)⑦B接對(duì)象返回到池中(Sleep), 這個(gè)連接可以在下一次Open調(diào)用中重用。

        看黑板,下面是這次的重點(diǎn):

        3. .NET是如何形成數(shù)據(jù)庫(kù)連接池的?

        只有相同的連接配置才能被池化,.NET為不同的配置維護(hù)了不同的連接池。

        相同的配置限制為:
        進(jìn)程相同、
        連接字符串相同、
        連接字符串關(guān)鍵key順序相同。

        (連接字符串提供的關(guān)鍵字順序不同也將被分到不同的池)。

        連接池中的可用連接的數(shù)量由連接字符串Max Pool Size決定。

        在一個(gè)應(yīng)用程序中,有如下代碼:

        using (SqlConnection connection = new SqlConnection(  
          "Integrated Security=SSPI;Initial Catalog=Northwind"))  
            {  
                connection.Open();
                // Pool A is created.  
            }  
          
        using (SqlConnection connection = new SqlConnection(  
          "Integrated Security=SSPI;Initial Catalog=pubs"))  
            {  
                connection.Open();
                // Pool B is created because the connection strings differ.  
            }  
          
        using (SqlConnection connection = new SqlConnection(  
          "Integrated Security=SSPI;Initial Catalog=Northwind"))  
            {  
                connection.Open();
                // The connection string matches pool A.  
            }  

        上面創(chuàng)建了三個(gè)Connection對(duì)象,但是只形成了兩個(gè)數(shù)據(jù)庫(kù)連接池

        還是以上代碼,如果有兩個(gè)相同的應(yīng)用程序,理論上就形成了四個(gè)數(shù)據(jù)庫(kù)連接池。

        4. 連接池中的連接什么時(shí)候被移除?

        連接池中的連接空閑4-8 分鐘,池程序會(huì)移除這個(gè)連接。

        應(yīng)用程序下線,連接池直接被清空。



        如何主動(dòng)清空.NET連接池



        有了以上知識(shí)背景,我們?cè)賮?lái)回顧一下DBA的要求,切換數(shù)據(jù)庫(kù)連接配置的時(shí)候,清空原連接池。

         .NET提供了 ClearAllPools、ClearPool靜態(tài)方法用于清空連接池。

        ClearAllPools:      清空與這個(gè)DBProvider相關(guān)的所有連接池? ClearPool(DBConnection conn)      清空與這個(gè)連接對(duì)象相關(guān)的連接池

        很明顯,我們這次要使用ClearPool(DBConnection conn) 方法。

        光說(shuō)不練不驗(yàn)證,不是我的風(fēng)格。

        天錘壓測(cè)/queryapi 產(chǎn)生一個(gè)包含大量連接對(duì)象的連接池;

        適當(dāng)?shù)臅r(shí)候,調(diào)用/clearpoolapi清空連接池。

         public class MySqlController : Controller
            {
                // GET: MySql
                [Route("query")]
                public string Index()
                {
                    var s = "User ID=teinfra_neo_netreplay;Password=123456;DataBase=teinfra_neo_netreplay;Server=10.100.41.196;Port=3980;Min Pool Size=1;Max Pool Size=28;CharSet=utf8;";
                    using (var conn = new MySqlConnection(s))
                    {
                        var comm = conn.CreateCommand();
                        comm.CommandText = "select count(*) from usertest;";
                        conn.Open();
                        var ret = comm.ExecuteScalar();

                        comm.CommandText = "select count(*) from information_schema.PROCESSLIST WHERE HOST like  '10.22.12.245%';";
                        var len = comm.ExecuteScalar();
                        return $"查詢(xún)結(jié)果:{ret} ,順便查一下當(dāng)前連接池的連接對(duì)象個(gè)數(shù): {len}";
                    };
                }

                [Route("clearpool")]
                public string Switch()
                {
                    var s = "User ID=teinfra_neo_netreplay;Password=123456;DataBase=teinfra_neo_netreplay;Server=10.100.41.196;Port=3980;Min Pool Size=1;Max Pool Size=28;CharSet=utf8;";
                    using (var conn = new MySqlConnection(s))
                    {
                        conn.Open();
                        MySqlConnection.ClearPool(conn);
                    };

                    using (var conn = new MySqlConnection(s))
                    {
                        conn.Open();
                        var comm = conn.CreateCommand();
                        comm.CommandText = "select count(*) from information_schema.PROCESSLIST WHERE HOST like  '10.22.12.245%';";
                        var len = comm.ExecuteScalar();
                        return $"之前已經(jīng)清空連接池, 此次查詢(xún)連接池有 {v1}  個(gè)連接對(duì)象";
                    }

                }
            }

        1.壓測(cè)產(chǎn)生大量連接對(duì)象


        2. mysql數(shù)據(jù)庫(kù)對(duì)比

        mysql的連接數(shù)查詢(xún)命令: (host是web服務(wù)器IP):
        select * from information_schema.PROCESSLIST WHERE HOST like '10.22.12.245%';

          3.  調(diào)用/clearpoolapi,清空連接池

        bingo,清空連接池的理論得到驗(yàn)證。


        旁白


        這是我在同程藝龍最近爬的比較深的坑位, 在本次實(shí)踐中我們了解到:

        ?.NET 數(shù)據(jù)庫(kù)連接池屬編程語(yǔ)言范疇,連接池維護(hù)了物理連接?.NET數(shù)據(jù)庫(kù)連接池的定義方式:(同一進(jìn)程、同一連接字符串、同一連接字符串關(guān)鍵key順序一致) 被劃到一個(gè)池?DB客戶(hù)端查詢(xún)當(dāng)前連接數(shù)的方式

        根據(jù)這個(gè)思路改造祖?zhèn)鞔a,.NET數(shù)據(jù)獲取組件SDK 已經(jīng)滿(mǎn)足了DBA的要求。

        希望本文設(shè)計(jì)考量、理論+論證的行文思路對(duì)讀者有所幫助, 距離上次發(fā)文一月有余,再次感謝5000+讀者不離不棄。

        引用鏈接

        [1] sql連接池(ado.net): https://docs.microsoft.com/en-us/dotnet/framework/data/adonet/sql-server-connection-pooling

        btw 成都同程藝龍常年招收資深golang開(kāi)發(fā)者,有機(jī)會(huì)參與企業(yè)級(jí)服務(wù)治理實(shí)踐。


        往期精彩回顧




        【推薦】.NET Core開(kāi)發(fā)實(shí)戰(zhàn)視頻課程 ★★★

        .NET Core實(shí)戰(zhàn)項(xiàng)目之CMS 第一章 入門(mén)篇-開(kāi)篇及總體規(guī)劃

        【.NET Core微服務(wù)實(shí)戰(zhàn)-統(tǒng)一身份認(rèn)證】開(kāi)篇及目錄索引

        Redis基本使用及百億數(shù)據(jù)量中的使用技巧分享(附視頻地址及觀看指南)

        .NET Core中的一個(gè)接口多種實(shí)現(xiàn)的依賴(lài)注入與動(dòng)態(tài)選擇看這篇就夠了

        10個(gè)小技巧助您寫(xiě)出高性能的ASP.NET Core代碼

        用abp vNext快速開(kāi)發(fā)Quartz.NET定時(shí)任務(wù)管理界面

        在ASP.NET Core中創(chuàng)建基于Quartz.NET托管服務(wù)輕松實(shí)現(xiàn)作業(yè)調(diào)度

        現(xiàn)身說(shuō)法:實(shí)際業(yè)務(wù)出發(fā)分析百億數(shù)據(jù)量下的多表查詢(xún)優(yōu)化

        關(guān)于C#異步編程你應(yīng)該了解的幾點(diǎn)建議

        C#異步編程看這篇就夠了


        瀏覽 53
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        評(píng)論
        圖片
        表情
        推薦
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        1. <strong id="7actg"></strong>
        2. <table id="7actg"></table>

        3. <address id="7actg"></address>
          <address id="7actg"></address>
          1. <object id="7actg"><tt id="7actg"></tt></object>
            黑鸡巴视频 | 超碰人人爱人人 | 北条麻妃影音先锋 | 散兵被到爽高潮痉挛 | 特级西西444www大胆高清图片 | 99日韩精品视频 | 中文字幕在线无码 | 男人的天堂在线 | 在线欧美网址 | 国产精品a久久久久久 |