mysql性能調優與架構設計筆記

 

一、mysql基本介紹mysql

    mysql支持多線程高併發的關係型數據庫;web

    數據庫存儲引擎InnoDB、MyISAM;sql

    mysql快速崛起的緣由就是他是開源的;數據庫

    性能一直是mysql自豪的一大特色;後端

 

二、mysql架構組成緩存

    麻雀雖小五臟俱全,mysql雖然簡單但其內部結構並不簡單;安全

    mysql物理文件組成之日誌文件:性能優化

    錯誤日誌error log這裏記錄mysql運行時嚴重的警告和錯誤,以及mysql啓動和關閉的日誌信息服務器

    二進制日誌 binary log 記錄mysql運行時全部的query和query執行的時間保存爲二進制信息網絡

    查詢日誌 query log 記錄全部query 包括select語句 體積較大開啓後對性能有所影響

    慢查詢日誌 slow query log 記錄慢查詢的日誌信息

 

    mysql物理文件組成之數據文件:

    每個數據庫都會在定義好的數據目錄下存在一個以數據庫名字命名的文件夾,用來存放某個數據庫各個表的數據信息;

    不一樣的數據存儲引擎有着不一樣的數據文件;

    .frm拓展名的文件:不管是存儲引擎,每一個表都會有一個以表名.frm的文件,存放的是表結構的定義

    .MYD拓展名的文件:MyISAM存儲引擎專用,存放表數據,每個表都會存在一個以表名.MYD的文件

    .MYI拓展名的文件:MyISAM存儲引擎專用,存放表索引數據,每一個表都會存在一個以表名.MYI的文件

    .ibd、.ibdata文件:InnoDB存儲引擎專用,存放表數據和表索引,區別在於.ibd是獨立存儲每一個表信息,每一個表都有一個表名.idb文件這點和MyISAM同樣,而ibdata文件是共享表空間存儲數據信息;

 

    mysql server系統架構之邏輯模塊組成:

    mysql能夠當作是二層架構,第一層是sql layer,在mysql數據庫系統處理底層數據以前的全部工做都在這一層完成,包括權限判斷、sql解析、執行計劃優化、query cache等工做,第二層是存儲引擎層也就是數據存儲實現的部份,有多種存儲引擎組成;

    雖然只有兩個層可是每一個層都有不少模塊組成,也是至關的複雜;

    sql layer層包含:(optimizer 優化程序)

    初始化、核心Api、網絡交互、client & server交互協議、用戶模塊、訪問控制模塊、

    鏈接管理鏈接線程管理、query解析和轉化、query cache、query優化器、表變動管理、

    表維護、系統狀態管理、表管理、日誌記錄、複製、存儲引擎接口管理

 

    mysql自帶工具使用介紹:

    mysql提供大量的客戶端工具程序mysql、mysqladmin、mysqldump...

 

三、mysql存儲引擎

    mysql存儲引擎概述:

    MyISAM儲存引擎是mysql默認的存儲引擎;

    Innodb存儲引擎是第三方插件式存儲引擎,是innobase公司開發,其最大特色是提供事務控制等功能;

 

    MyISMA儲存引擎簡介:

    MyISMA存儲引擎的表在數據庫中每個表都被存放到三個以表名命名的物理文件中,分別是存放表結構定義的表名.frm文件、表數據表名.MYD文件、表索引表名.MYI文件;

    MyISAM索引類型有三種:B-Tree、R-Tree、full-text,經常使用B-Tree類型索引;

    MyISAM存儲引擎有靜態固定長度存儲FIXED、動態可變長度存儲DYNAMIC、壓縮存儲COMPRESS;

    MyISAM儲存引擎中某個表數據文件出錯後不會影響到其餘表或其餘數據信息;

 

    Innodb存儲引擎簡介:

    mysql中除了MyISAM存儲引擎以外適用做普遍就是Innodb存儲引擎,他和MyISAM同樣遵循開源license協議;

    Innodb的優勢就是提供了事務控制功能;

    Innodb提高了MyISAM鎖的機制,實現了行鎖功能;

    Innodb的數據存儲和MyISAM也不同,雖然也有表結構定義信息表名.frm文件,表數據和表索引是在一個文件裏面存儲.ibd單獨的存儲、.ibdata共享存儲;

 

    Innodb的物理結構能夠分紅兩大類:

    數據文件(存放表數據和表索引數據).ibd單獨的存儲、.ibdata共享存儲兩種類型;

    日誌文件:請不要所有刪除Innodb的日誌文件這樣會讓數據庫crash(崩潰),或提示數據丟失;

 

    Memory存儲引擎:

    Memory存儲引擎就是把數據存儲在內存裏面的一種引擎;

    Memory存儲引擎不會把數據存儲在磁盤,存入磁盤的只是表名.frm結構,所以若是數據庫crash或者宕機都會致使數據丟失;

 

    小結:多存儲引擎是mysql有別於其餘數據庫的一大特性;後續對經常使用的存儲引擎會進行詳情介紹;

 

四、mysql安全管理

    對企業來講數據庫保存的數據的安全性是很是重要的;

    數據失去了安全性就等於失去了一切;

    

    數據庫系統安全相關因素:

    外圍網絡安全:mysql是基於網路環境的,而網絡自己就存在一種入侵的威脅;要從最外層預防;

                儘可能讓mysql存在有保護的局域網環境中;

 

    主機防護:外圍網絡預防獲得了保護,那麼仍是會存在入侵的可能,那就是局域網入侵;

        主要是阻止沒有受權的設備鏈接mysql;

        入侵數據庫危害盜取數據、刪除數據、製造漏洞;

 

    數據庫防護:經過第二道防線咱們能夠預防一部分威脅,但是容許使用主機登陸的設備是否

                徹底擁有權限呢?是不是可信任的對象呢?

                數據庫防線是mysql自身系統的訪問控制受權模塊,這道防線是mysql入侵的最後一道防線了;

                設置登陸用戶名和密碼和端口號並並設置權限;

 

    代碼防護:sql語句相關安全因素、sql注入攻擊、程序代碼相關安全因素

 

    DDL、DML、DCL

    數據庫定義語言(CREATE ALTER DROP TRUNCATE)

    數據庫操做語言(SELECT INSERT UPDATE DELETE EXPLAN)

    數據庫控制語言(COMMIT ROLLBACK)

 

    mysql訪問控制實現原理:

    mysql訪問控制其實有2部分組成:一是用戶模塊管理、一是訪問控制模塊管理(權限);

        用戶模塊決定是否能進入,訪問控制模塊(權限)決定能有哪些操做;

        例如:客戶端請求(提供host,用戶名,密碼)-->用戶模塊驗證(經過mysql.user表驗證)-->

        客戶端請求query(DML、DDL)-->解析query執行權限-->權限匹配查找(grant tables中查找)

        -->發日後端繼續執行

 

    mysql訪問受權策略:

    不是每一個用戶的權限都同樣無限大;

    每一個用戶的權限作到越小越好,知足使用就好;

    首先了解來訪主機、瞭解用戶需求、最後爲工做分類,這樣確保絕對必要擁有者擁有grant(准許)權限;

 

    備註:安全無小事,數據是一個企業的財富;

 

五、mysql數據的備份與恢復

    數據庫備份使用的場景:

    數據丟失應用場景:人爲誤操做、軟件bug、硬件故障、安全漏洞

    非數據丟失場景:特殊場景下數據恢復、開發測試數據庫搭建、數據庫或數據遷移

    備註:數據庫數據備份解決問題不是萬能的;

 

六、影響mysql server性能的相關因素

    大多都認爲數據庫應用系統的性能瓶頸是數據庫管理軟件和數據庫主機自身形成的,其實否則;

    下面以mysql數據庫web場景爲例來分析影響性能的瓶頸;

    商業需求對性能的影響:

        不是全部功能都能實現,有些不合理的功能反而最後成了累贅,消耗資源;

        不合理的需求形成資源投入產出比太低;

        無用功能堆積使系統過分複雜影響總體性能;(無用的功能大多不會下線,由於考慮風險,因此係統愈來愈龐大複雜,不只維護困難,系統性能也愈來愈差)

 

    系統架構及實現對性能的影響:

        一個web應用天然離不開應用程序(web application)和web應用程序服務器(web server),web server咱們控制調優的很少都是很成熟的產品,web application咱們能夠優化不少方面;

        如下幾類數據不適合存放到數據庫中:

            二進制多媒體數據(消耗內存、消耗cpu);

            流水隊列數據(不斷的進行insert update delete由於每次操做都會寫入日誌文件影響性能);

            超大文本數據(佔用空間浪費資源)

 

        是否合理利用應用層cache機制:mysql memory存儲引擎

            經過cache機制成功的案例不少不少,但是失敗的案例也不少;

            下面整理哪些可使用cache機制:

                系統各類配置和規則的數據;

                活躍用戶的基本信息(緩存用戶的基本信息能夠大大提高性能);

                時間段的統計數據;

                訪問平凡更新較少的數據;

 

        過分依賴數據庫sql語句的功能形成數據庫操做效率低下:

            儘可能不要在循環中屢次執行sql,有時可使用2個sql,這樣不佔用IO和解析資源;

            若是一條sql查詢的列不是所有使用時請拆分紅2個sql,減小不適用列的查詢;

            避免重複執行相同的sql浪費資源(這裏可能和上面兩條像違背,分不一樣邏輯考慮取捨)

 

        架構設計不當帶來性能問題和資源浪費問題:

            cache命中率低,增長數據庫的訪問壓力,浪費cache資源利用率;

            過分依賴面向對象,對可拓展性的過分追求;

            對數據庫的過分依賴,一些不符合存入數據庫的應該存入文件系統中;

            過分的在意用戶體驗,好比不用實時更新的數據實時更新了浪費資源;

 

        query語句對性能的影響:

            當mysql的鏈接線程接收到client請求的sql時,會通過解析和分析,而後經過執行計劃調用存儲過程接口,最後把數據返回給client顯示;

            執行sql主要是IO消耗和cpu消耗(這裏能夠經過explain進行測試);

            備註:有時間測試下兩個表先鏈接查詢和先查詢一個表信息在和另外一個錶鏈接分析哪一個好?

 

        schema(方案)的設計對系統性能的影響:

            數據庫設計對性能的提高;

            適當的使用好範式是對設計最大的調優;

 

        硬件環境對性能的影響:

            考慮併發訪問比較頻繁的時候要考慮服務器IO和CPU處理能力;

 

七、mysql數據庫鎖定機制

    爲了保證數據的完整性任何一種數據庫都有鎖定的機制;

    一個數據庫鎖定技術的優劣直接影響數據庫高併發處理和性能;

    mysql經常使用存儲引擎Innodb、MyISAM

 

    mysql鎖定機制簡介:

        行級鎖定:

            行級鎖定最大的特色就是對象的顆粒度很小,是最經常使用的一種形式;

            因爲鎖定顆粒下取鎖和鎖定處理的事情比較多,耗內存,也最容易發生死鎖;

 

        表級鎖定:

            表級鎖定與行級鎖定的特色正好相反,是鎖定mysql存儲引擎中最大的顆粒;

            表鎖定邏輯簡單、處理快、耗能小、不容易死鎖;

 

        頁級鎖定:

            頁級鎖定是mysql一個比較獨特的鎖定機制,鎖定介於行鎖和表鎖之間;

            頁級鎖定和行級鎖定同樣,很容易被死鎖;

 

        備註:行級鎖定不是mysql本身的鎖定機制,而是第三方Innodb存儲引擎的鎖定機制;

            Innodb若是產生死鎖時會經過檢測死鎖機制來判斷要回滾那個事務sql,這裏會根據影響數據的大小來判斷,讓影響數據大的事務sql執行成功,回滾影響小的事務sql;或者經過死鎖機制過時時間來回滾事務sql;

 

        Innodb行級鎖的優勢:

            在不少線程請求不一樣記錄時減小衝突;

            事務回滾時減小改變的數據;

            使長時間對單獨的一行記錄加鎖成爲可能;

        Innodb行鎖的缺點:

            比表級別鎖和頁級別鎖消耗更多的內存;

 

    合理的利用鎖機制優化mysql:

        MyISAM的表鎖優化建議:

            MyISAM的表鎖比行鎖和頁鎖減少了資源,可是必定程度上影響了併發的性能,

            所以優化表鎖的建議就是如何提升併發的性能;

            

            縮短鎖定時間;

                惟一的辦法讓sql執行時間儘量的短;

                龐大複雜的sql建議分紅多個小sql分佈式執行;

                儘量的創建高效的索引和字段類型限制;

 

            分離能並行的操做;

 

            合理利用讀寫優先級;

 

        Innodb行鎖的優化建議:

            Innodb的行鎖機制雖然比MyISAM的表鎖機制消耗很大的資源可是高併發卻遠遠超於後者;

            Innodb的行鎖也有瓶頸的一面:

                查詢儘可能使用索引提升查詢速度;

                合理的設計索引;

                查詢的範圍不該過大;

 

        系統鎖定狀況查詢:

            表鎖定狀況查詢:

                SHOW STATUS LIKE '%table%';

                Table_locks_immediate 表鎖定的次數

 

                Table_locks_waited    表鎖定等待的次數

                Table_locks_waited若是數值變大了說明表爭用比較嚴重,須要優化;

 

            Innodb行鎖的狀況查詢:

                SHOW STATUS LIKE '%innodb_row_lock%';

                Innodb_row_lock_current_waits   //當前正在等待鎖定的數量

                Innodb_row_lock_time    //從系統啓動到如今鎖定總時間長度

                Innodb_row_lock_time_avg    //每次等待所花費的平均時間

                Innodb_row_lock_time_max    //某次等待最長的時間

                Innodb_row_lock_waits   //從系統啓動到如今請求的次數

                上述分析:重要的是1 3 5這幾個值

 

    Innodb存儲引擎的總體性能要高於MyISAM存儲引擎

 

八、mysql數據庫中query的優化

    mysql query optimizer:

        mysql query optimizer 是query查詢優化器模塊,提供最優的執行計劃;

 

    query語句優化的思路和原則:

        優化更須要優化的query;

        定位優化對象的性能瓶頸;//是IO仍是CPU仍是內存

        明確的優化目標;

        多使用show profiles;

        從explain sql入手; //由於它能夠展現執行計劃詳細信息

        最可能的在索引中排序;

        只取出本身須要的columns;

        使用最有效的過濾條件;

        儘量避免複雜的join和子查詢;

 

    優化更須要優化的query:

        兩個query每小時執行的IO數是同樣的,一個是每小時執行10000次每次消耗20個IO,

        一個是每小時執行10次每次消耗20000個IO那麼試問該優化哪一個query呢?

        解答:第一個query把IO從20降到18就減小了2個,那麼就2*10000 = 20000個IO

            第二個query若是能減小20000個IO那麼20000/10 = 2000個IO那麼每次需減小2000個IO

            所以咱們以爲那個更好優化呢,哪一個能減小更少的IO呢,第一個query;

 

        執行高併發的query比執行低併發的危險性要高的多,高併發的query很容易讓系統crash掉,

        等咱們從新啓動後系統負荷就會直線飆升接近crash,讓咱們都不能查詢問題出如今哪裏,

        而低併發的query雖然也產生負荷至少還在可控範圍內;

 

    join時的原則就是‘小結果集驅動大結果集的’:

    A表1000數據,B表10萬條數據 SELECT A.*, B.name FROM A LEFT JOIN B ON A.id=B.a_id

    //這裏就是以A表做爲驅動表循環鏈接B表信息;減小了循環次數;B表示被驅動表;

 

 

    explain sql語句詳細分析:

        注意key_len的值,越小越好;

        //也就是說每每一個where條件能夠查詢到的就不要再用第二個沒有意義的條件了哦,由於消耗內存;

 

    mysql中索引的限制:

        MyISAM存儲引擎的索引鍵值長度總和不能超過1000字節;

        mysql目前不支持函數索引;

        mysql查詢條件!= 、<>的時候不能使用索引;

        使用like查詢 like'%abc'這樣沒法使用索引;

 

    join的原理和優化思路:

        SELECT A.*

        FROM USER_GROUP A LEFT JOIN GROUP_MESSAGE B ON A.group_id = B.group_id

        LEFT JOIN GROUP_MESSAGE_CONTENT C ON B.id = C.message_id

        WHERE A.user_id = 1;

        //這裏是把USER_GROUP表做爲驅動表, 先A表經過索引查詢出group_id集合做爲驅動表,

        //對GROUP_MESSAGE表進行循環查詢出id,最後在經過索引message_id查詢出最終結果集合;

        

 

        儘量的減小join語句的循環次數;

        鏈接的字段必須建索引;

        GROUP BY/ ORDER BY儘可能使用索引;

 

九、mysql數據庫schema(圖標)的設計和調優 

    高效的模型設計:

        首先考慮符合第一第二第三範式;

        適當沉餘讓query儘可能減小join;

            舉例:user表,message表中能夠添加個author_name字段;

        大字段垂直分隔;

            blog表中有個content字段text類型能夠分隔成blog_detail表;

        統計表準實時更新;

            統計的數據不建議實時更新,這裏就是商業需求影響性能,可使用定時實時更新;

 

    合適的數據類型:

        儘可能使用小的數據類型來減小磁盤的空間;

        經過合適的數據類型進行數值比較;

 

    規範的對象命名:

        數據庫和表命名應儘量的和所屬產品描述相符合;

        字段名也應和該列信息描述相符合;

        索引名稱儘可能包含字段名稱或字段縮寫;

 

    備註:數據庫性能的提高不是優化出來的而是設計出來的;

 

十、mysql性能優化

    mysql安裝優化:

        安裝適合的數據庫版本;

 

    mysql日誌性能優化:

        錯誤日誌(error log);

        更新日誌(update log);

        二進制日誌(binlog);

        查詢日誌(query log);

        慢查詢日誌(slow query sql);

 

    mysql query cache的優化:

        mysql query cache產生可讓mysql性能產生質的飛越;

 

    mysql server的其餘優化:

        網絡容許的最大鏈接數;max_connections處理併發能力

        用戶容許的組大鏈接數;max_user_connextions針對於單個用戶的鏈接限制;

        網絡包傳輸中,傳輸信息以前net_buffer的初始化大小;net_buffer_length;

        網絡傳輸中一次傳輸信息的最大值;max_allowed_packet;

        mysql鏈接等待中的最大數量;back_log;

 

十一、經常使用存儲引擎優化

    mysql中MyISAM存儲引擎優化;

    mysql中Innodb存儲引擎優化;

 

十二、mysql可拓展設計的基本原則

1三、可拓展性設計之mysql replication(複製)

1四、可拓展性設計之數據切分

    何爲數據切割:

        按照不一樣的表來切分到不一樣的數據庫上這個是垂直(縱向)切割模式;

        把同一個表按照某種邏輯關係分別拆分存放到不一樣的數據庫上這個是水平切割模式;

 

        備註:垂直分隔的特色就是簡單,低耦合的表能夠進行垂直分隔;

        若是咱們作了垂直分隔後還任然不能提升性能時咱們還的進行水平分隔;

 

    數據的垂直分隔:

        數據庫中的表都是有多個功能模塊組成,每一個功能模塊以前的耦合度越小越容易進行垂直分隔;

 

    垂直分隔優勢:

        數據庫拆分簡單明瞭,拆分規則明確;

        應用程序模塊清晰明確,整合容易;

        數據維護方便容易定位;

    垂直分隔缺點:

        部分表關聯沒法在數據庫中完成;

        切分紅必定程度以後拓展性下降;

 

    數據水平分隔:

        數據的水平分隔是高併發查詢的表經過某個字段的規則吧數據分別存放不一樣的表中進行查詢,

        這樣每張表的數據集合就沒有以前一張表大,從而來提示查詢速度,常見的方案是經過userid

        對5取模而後分別存放到5個表中,顯示查詢則經過userid對5取模,餘數就知道此userid存在哪裏;

 

    備註:經過數據分隔技術將一個大的數據mysql server分隔成多個小數據的mysql server,這樣提升了

        查詢和寫入性能, 最佳方案是先進行垂直分隔再進行水平分隔;

 

1五、可拓展性設置cache和search的利用

    分佈式緩存cache解決方案memcached;

    利用search實現高效的全文索引;

    備註:數據庫只是存儲數據的工具,他的特色就是持久化,除了數據庫咱們還有不少其餘方式的數據存儲;

 

1六、mysql cluster(集羣)

    mysql cluster是一個基於NDB cluster存儲引擎的完整的分佈式數據庫系統;

相關文章
相關標籤/搜索