測量應用程序的方法之一是看性能。而性能的指標之一即是用戶體驗,通俗的說法就是「用戶是否須要等待更長的時間才能獲得他們想要的東西」。html
這個指標在不一樣的應用場合而有所改變。對於移動購物應用,響應時間不能超過幾秒鐘。對於員工的人力資源頁面,可能須要多花幾秒鐘的時間。mysql
有不少關於性能如何影響用戶行爲的研究:sql
不管採用何種標準,都必須保持良好的應用性能。不然,用戶會抱怨(或者更糟的是,轉到不一樣的應用程序)。影響應用程序性能的因素之一是數據庫性能。應用程序、網站和數據庫之間的交互對於創建應用程序性能的好壞相當重要。數據庫
這種交互的一個核心組件是應用程序如何查詢數據庫以及數據庫如何響應請求。不管如何,MySQL都是最受歡迎的數據庫管理系統之一。在生產環境中,愈來愈多的企業正在轉向使用MySQL(和其餘開源數據庫)做爲數據庫解決方案。json
有許多配置MySQL的方法能夠幫助確保數據庫對查詢做出快速響應,並使應用程序性能下降到最低限度。緩存
如下是幫助優化MySQL數據庫性能的一些基本技巧。性能優化
使用任何數據庫所作的兩個最重要的決定是設計應用程序實體之間的關係如何映射到表(數據庫模式),以及設計應用程序如何以所需的格式得到所需的數據(查詢)。服務器
複雜的應用程序能夠有複雜的模式和查詢。若是想獲得應用程序所須要的性能和擴展性,不能僅僅依靠直覺來理解如何執行查詢。併發
應該學習如何使用EXPLAIN命令,而不是隨意的猜想和想象。此命令展現瞭如何執行查詢,並讓您瞭解所指望的性能,以及查詢將如何隨着數據大小的變化而伸縮。分佈式
有許多工具–好比MySQLWorkbench–能夠可視化EXPLAIN輸出,但仍然須要理解基礎知識才能理解它。
EXPLAIN命令提供輸出的有兩種不一樣的格式:老式的表格式和更現代的結構化JSON文檔,它提供了更多的細節(以下所示):
mysql> explain format=json select avg(k) from sbtest1 where id between 1000 and 2000 \G *************************** 1. row *************************** EXPLAIN: { 「query_block」: { 「select_id」: 1, 「cost_info」: { 「query_cost」: 「762.40」 }, 「table」: { 「table_name」: 「sbtest1」, 「access_type」: 「range」, 「possible_keys」: [ 「PRIMARY」 ], 「key」: 「PRIMARY」, 「used_key_parts」: [ 「id」 ], 「key_length」: 「4」, 「rows_examined_per_scan」: 1874, 「rows_produced_per_join」: 1874, 「filtered」: 「100.00」, 「cost_info」: { 「read_cost」: 「387.60」, 「eval_cost」: 「374.80」, 「prefix_cost」: 「762.40」, 「data_read_per_join」: 「351K」 }, 「used_columns」: [ 「id」, 「k」 ], 「attached_condition」: 「(`sbtest`.`sbtest1`.`id` between 1000 and 2000)」 } } }
應該查看的一個組件是「query cost」。query cost是指MySQL根據查詢執行的總開銷來考慮這個特定查詢的代價,而且基於許多不一樣的因素。
簡單查詢的查詢開銷一般小於1,000。開銷在1,000到100,000之間的查詢被認爲是中等開銷的查詢,並且若是每秒只運行數百個這樣的查詢(而不是數萬個),一般會比較快。
開銷超過100,000的查詢能夠看成是昂貴的。一般,當您是系統上的單個用戶時,這些查詢仍會快速運行,但您應該仔細考慮在交互式應用程序中使用此類查詢的頻率(尤爲是隨着用戶數量的增加)。
固然,這些數字只是性能的一個大概的體現,但它們展現了通常原則。您的系統可能更好地處理查詢工做負載,也可能更糟,這取決於其體系結構和配置。
決定查詢開銷的主要因素是查詢是否正確使用索引。EXPLAIN 命令能夠告訴您查詢是否使用索引(一般是由於索引是如何在數據庫中建立的,或者查詢自己是如何設計的)。這就是爲何學會使用 EXPLAIN 是如此重要。
索引經過減小查詢必須掃描的數據庫中的數據量來提升查詢效率。MySQL中的索引用於加速數據庫中的訪問,並幫助執行數據庫約束(如 UNIQUE和FOREIGN KEY )。
數據庫索引很像圖書索引。它們被保存在本身的位置,而且包含主數據庫中已經存在的信息。它們是指向數據所在位置的參考方法或映射。索引不會更改數據庫中的任何數據。它們只是指向數據的位置。
沒有徹底適用於任何工做負載的索引。而應該始終在系統運行的查詢上下文中查看索引。
索引良好的數據庫不只運行得更快,並且即便缺乏一個索引也會使數據庫慢如蝸牛。使用EXPLAIN(如前所述)查找缺乏的索引並添加它們。可是要當心:不要添加你不須要的索引!沒必要要的索引會下降數據庫的速度
源碼下載地址:http://www.jinhusns.com/Products/Download
與任何軟件同樣,MySQL有許多可配置的設置,可用於修改行爲(以及最終的性能)。與任何軟件同樣,管理員忽略了許多這些可配置的設置,最終在默認模式下使用。
要從MySQL中得到最佳性能,瞭解可配置的的MySQL設置是很是重要的,更重要的是將它們設置爲最適合您的數據庫環境。
默認狀況下,MySQL用於小規模的開發安裝,而不是生產規模。您一般但願配置MySQL以使用全部可用的內存資源,並容許應用程序須要的鏈接數量。
下面是三個MySQL性能優化設置,您應該始終仔細檢查:
innodb_ buffer_ pool_size:緩衝池用於存放緩存數據和索引。這是使用具備大容量RAM的系統做爲數據庫服務器的主要緣由。若是隻運行InnoDB存儲引擎,一般會將80%的內存分配給緩衝池。若是您正在運行很是複雜的查詢,或者有大量的併發數據庫鏈接,或大量的表,可能須要將此值下降一個檔次,以便爲其餘操做分配更多的內存。
在設置InnoDB緩衝池大小時,須要確保不要設置得太大,不然會致使交換。這絕對會影響數據庫性能。一種簡單的檢查方法是查看Percona Monitoring and Management中的系統概述圖中的交換活動:
如圖所示,有時進行一些交換是能夠的。可是,若是看到持續每秒1MB或更多的交換活動,則須要減小緩衝池大小(或其餘內存使用)。
若是在第一次訪問時沒有正確地得到innodb_ Buffer_ pool_ size的值,不用擔憂。從MySQL5.7開始,即可以動態更改InnoDB緩衝池的大小,而無需從新啓動數據庫服務器。
innodb_ log_ file_ size:這是單個InnoDB日誌文件的大小。默認狀況下,InnoDB使用兩個值,這樣您就能夠將這個數字加倍,從而得到InnoDB用於確保事務持久的循環重作日誌空間的大小。這也優化了將更改應用到數據庫。設置innodb_ log_ file_ size是一個權衡的問題。分配的重作空間越大,對於寫密集型工做負載而言,性能就越好,可是若是系統斷電或出現其餘問題,崩潰恢復的時間就越長。
如何知道MySQL的性能是否受到當前InnoDB日誌文件大小的限制?能夠經過查看實際使用了多少可用的重作日誌空間來判斷。最簡單的方法是查看Percona Monitor and Management InnoDB Metrics儀表板。在下圖中,InnoDB日誌文件的大小不夠大,由於使用的空間很是接近可用的重作日誌空間(由紅線表示)。日誌文件的大小應該至少比保持系統最佳運行所用的空間大20%。
MAX_ Connections:大型應用程序鏈接數一般需高於默認值。不一樣於其它變量,若是沒有正確設置它,就不會有性能問題(自己)。相反,若是鏈接的數量不足以知足您的應用程序的須要,那麼您的應用程序將沒法鏈接到數據庫(在您的用戶看來,這就像是停機時間)。因此正確處理這個變量很重要。
若是在多個服務器上運行多個組件的複雜應用程序,很難知道須要多少鏈接。幸運的是,MySQL能夠很容易地看到在峯值操做時使用了多少鏈接。一般,您但願確保應用程序使用的最大鏈接數與可用的最大鏈接數之間至少有30%的差距。查看這些數字的一種簡單方法是在Percona監控和管理的MySQL概述儀表板中使用MySQL鏈接圖。下圖顯示了一個健全的系統,其中有大量的附加鏈接可用。
須要記住的一點是,若是數據庫運行緩慢,應用程序一般會建立過多的鏈接。在這種狀況下,您應該處理數據庫的性能問題,而不是簡單地容許更多的鏈接。更多的鏈接會使底層的性能問題變得更糟。
(注意:當將max_Connections變量設置爲明顯高於默認值時,一般須要考慮增長其餘參數,如表緩存的大小和打開的MySQL文件的數量。可是,這不屬於本文討論的範疇。)
近年來,咱們看到了向固態磁盤(SSD)的過渡。儘管SSD比旋轉硬盤快得多,但它們仍然沒法與RAM中的數據相比。這種差別不只來自存儲性能自己,還來自數據庫在從磁盤或SSD存儲中檢索數據時必須作的額外工做。
隨着最新硬件的改進,不管是在雲端運行仍是管理本身的硬件,都愈來愈有可能將數據庫存儲在內存中。
更好的消息是,您不須要將全部數據庫都放入內存中,就能夠得到內存中的大部分性能優點。您只需將工做數據(最頻繁訪問的數據)集存入內存中。
你可能已經看到一些文章提供了一些具體的數字,說明應該將數據庫的哪一個部分保存在內存中,從10%到33%不等。事實上,沒有「一刀切」的數字。適合內存的最佳性能優點的數據量與工做負載相關。與其尋找一個特定的「萬能」數字,不如檢查一下數據庫在其穩定狀態下運行的I/O(一般在啓動後幾個小時)。看看READ,由於若是數據庫在內存中,則能夠徹底消除READ。寫老是須要發生的,無論你有多少內存可用。
下面,您能夠在Percona監控和管理的InnoDBMetrics儀表板中的 InnoDB I/O圖中看到 I/O。
在上面的圖表中,您能夠看到高達每秒2,000個I/O操做的峯值,這代表(至少對於工做負載的某些部分)數據庫工做集不適合內存。
若是您的數據庫不適合內存(即便不適合),您仍然須要快速存儲來處理寫操做,並在數據庫升溫時(從新啓動後)避免性能問題。現在,SSD便是快速存儲的代名詞。
出於成本或可靠性的緣由,一些「專家」仍然主張使用旋轉磁盤(機械磁盤)。坦率地說,當涉及到操做數據庫時,這些論點每每已通過時或徹底錯誤。今天,SSD以較高的價格提供着可觀的性能和可靠性。
然而,並不是全部SSD都是適用的。對於數據庫服務器,您應該使用爲服務器工做負載設計的SSD,這種SSD會對數據起到保護做用(例如,在斷電期間)。避免使用爲臺式計算機和筆記本電腦設計的商用SSD。
經過NVMe或Intel OpTan技術鏈接的SSD可提供最佳性能。即便做爲SAN、NAS或cloud block設備遠程鏈接,與旋轉磁盤相比,SSD仍然具備更優越的性能。
即便是高性能的服務器也有其侷限性。有兩種擴展方式:up和out。縱向擴展意味着購買更多的硬件。這可能很昂貴,並且硬件很快就會過期。橫向擴展以處理更多的負載有幾個好處:
1.能夠利用較小且成本較低的系統。
2.經過橫向擴展,進行線性擴展更快更容易。
3.由於數據庫分佈在多臺物理機器上,因此數據庫不會受到單個硬件故障點的影響。
雖然橫向擴展是有好處的,但也有必定的侷限性。擴展須要複製,例如基本的MySQL複製或Percona XtraDB Cluster,以實現數據同步。可是做爲回報,能夠得到額外的性能和高可用性。若是您須要更大的擴展,請使用MySQL分片。
您還須要確保鏈接到集羣體系結構的應用程序可以找到所需的數據–一般經過一些代理服務器和負載平衡器(如ProxySQL或HAProxy)。
在計劃橫向擴展時,避免過早地擴展。使用分佈式數據庫每每更復雜。現代硬件和MySQL服務器只使用一臺服務器就能夠獲得良好的體驗。最近發佈的MySQL 8候選版本代表,它可以在單個系統上處理200多萬個簡單查詢。
設計最好的系統時要考慮到可觀察性-MySQL也不例外.。
一旦您啓動、運行並正確調整了MySQL環境,就不能僅僅設置而不進行管理。數據庫環境會受到系統或工做負載更改的影響。準備好應對諸如流量高峯、應用程序錯誤和MySQL故障等意外。這些事情可以並且將會發生。
當發生問題時,你須要迅速而有效地解決它們。這樣作的惟一方法是設置某種監視解決方案並對其進行適當的初始化。這使您可以在數據庫環境在生產中運行時看到它正在發生的狀況,並在出現問題時分析服務器數據。理想狀況下,系統容許您在問題發生以前或在問題發展到用戶能夠看到其影響以前進行預防。
監控工具備諸如MySQL Enterprise Monitor、Monyog和 Percona Monitoring and Management (PMM),後者具備免費和開源的額外優點。這些工具爲監視和故障排除提供了很好的可操做性。
隨着愈來愈多的公司轉向開源數據庫(特別是MySQL),以便在大規模生產環境中管理和服務其業務數據,他們將須要集中精力保持這些數據庫的優化和最佳運行效率。與全部對您的業務目標相當重要的事情同樣,您的數據庫性能可能會致使或破壞你的業務目標或成果。MySQL是一個能夠爲應用程序和網站提供優質的數據庫解決方案,但須要進行調整以知足您的須要,並進行監視以發現和防止瓶頸和性能問題。