07 生產(chǎn)經(jīng)驗(yàn):如何對生產(chǎn)環(huán)境中的數(shù)據(jù)庫進(jìn)行360度無死角壓測?

生產(chǎn)經(jīng)驗(yàn):如何對生產(chǎn)環(huán)境中的數(shù)據(jù)庫進(jìn)行360度無死角壓測?
1、昨日思考題解答
先給大家分析昨天的第一個(gè)小思考題:給你一臺(tái)4核8G的機(jī)器,他可以抗到每秒幾千甚至每秒幾萬的并發(fā)請求嗎?
其實(shí)這個(gè)是不一定的,因?yàn)橐慌_(tái)機(jī)器到底每秒鐘可以抗下多少并發(fā)請求,跟CPU、內(nèi)存、磁盤IO、網(wǎng)絡(luò)帶寬,都是有關(guān)系的。
舉個(gè)例子,之前在我們的一個(gè)項(xiàng)目的生產(chǎn)環(huán)境中,據(jù)我們觀察,一臺(tái)4核8G的機(jī)器如果每秒抗下500+的請求,那么他的CPU負(fù)載就已經(jīng)很高了,基本上最多可能也就是去抗下每秒1000+的請求,而且那個(gè)時(shí)候CPU負(fù)載基本會(huì)打滿,機(jī)器有掛掉的風(fēng)險(xiǎn)。
另外如果你的系統(tǒng)的業(yè)務(wù)邏輯特別的吃內(nèi)存,也許你一臺(tái)4核8G的機(jī)器跑到每秒幾百的請求,內(nèi)存使用率就很高了,而且JVM GC頻率可能會(huì)非常的高,所以此時(shí)也很難繼續(xù)提升并發(fā)請求了。
所以其實(shí)你一臺(tái)機(jī)器是不可能無限制的讓他增加可以抗下的并發(fā)請求的。
再來看下一個(gè)思考題:關(guān)于QPS和TPS的。我上次問大家了,如果一個(gè)交易系統(tǒng)拆分為了很多服務(wù),那么每個(gè)服務(wù)每秒接收的并發(fā)請求是QPS還是TPS呢?
這個(gè)明顯是QPS,因?yàn)槊總€(gè)服務(wù)就負(fù)責(zé)干自己的一些事兒,其實(shí)對他來說,每秒并發(fā)請求數(shù)量就是QPS。
那么對于多個(gè)服務(wù)組成的一個(gè)大的交易系統(tǒng)而言,這個(gè)交易系統(tǒng)每秒可以完成多少筆交易,這是QPS還是TPS呢?
其實(shí)這個(gè)你可以認(rèn)為是TPS的概念,因?yàn)橐还P交易需要調(diào)用多個(gè)服務(wù)來完成,所以一筆交易的完成其實(shí)就類似數(shù)據(jù)庫里的一個(gè)事務(wù),他涵蓋了很多服務(wù)的請求調(diào)用,所以每秒完成多少筆交易,你可以用TPS來形容。
比如你說交易系統(tǒng)的TPS是300,就是說每秒可以完成300筆交易。那么比如交易系統(tǒng)中的服務(wù)A的QPS是500,就是交易系統(tǒng)中的一個(gè)服務(wù)A每秒可以處理500個(gè)請求。
2、一款非常好用的數(shù)據(jù)庫壓測工具
上一篇文章給大家講解了我們在壓測的過程中要關(guān)注哪些東西,這一篇文章就來帶著大家一步一步的利用一個(gè)工具進(jìn)行數(shù)據(jù)庫壓測。
先給大家介紹一個(gè)非常好用的數(shù)據(jù)庫壓測工具,就是sysbench,這個(gè)工具可以自動(dòng)幫你在數(shù)據(jù)庫里構(gòu)造出來大量的數(shù)據(jù),你想要多少數(shù)據(jù),他就自動(dòng)給你構(gòu)造出來多少條數(shù)據(jù)。
然后這個(gè)工具接著可以模擬幾千個(gè)線程并發(fā)的訪問你的數(shù)據(jù)庫,模擬使用各種各樣的SQL語句來訪問你的數(shù)據(jù)庫,包括模擬出來各種事務(wù)提交到你的數(shù)據(jù)庫里去,甚至可以模擬出幾十萬的TPS去壓測你的數(shù)據(jù)庫。
所以一般來說,如果你要進(jìn)行數(shù)據(jù)庫的壓測,就是直接使用sysbench工具就可以了,這一篇文章我來帶著大家學(xué)習(xí)一下這個(gè)壓測工具的使用,大家學(xué)習(xí)完這一講,完全可以自己本地裝一個(gè)MySQL數(shù)據(jù)庫,然后自己壓測一下試一試。
3、在linux上安裝sysbench工具
首先你需要有一臺(tái)linux機(jī)器,如果你只有一個(gè)windows筆記本電腦,可以在里面裝一個(gè)linux的虛擬機(jī),然后你可以用如下的命令設(shè)置一下yum repo倉庫,接著基于yum來安裝sysbench就可以了,安裝完成以后驗(yàn)證一下是否成功。
curl -s https://packagecloud.io/install/repositories/akopytov/sysbench/script.rpm.sh | sudo bash
sudo yum -y install sysbench
sysbench --version
如果上面可以看到sysbench的版本號(hào),就說明安裝成功了。
4、數(shù)據(jù)庫壓測的測試用例
接著我們需要在自己的數(shù)據(jù)庫里創(chuàng)建好一個(gè)測試庫,我們可以取個(gè)名字叫做test_db,同時(shí)創(chuàng)建好對應(yīng)的測試賬號(hào),可以叫做test_user,密碼也是test_user,讓這個(gè)用戶有權(quán)限可以訪問test_db。
然后我們將要基于sysbench構(gòu)建20個(gè)測試表,每個(gè)表里有100萬條數(shù)據(jù),接著使用10個(gè)并發(fā)線程去對這個(gè)數(shù)據(jù)庫發(fā)起訪問,連續(xù)訪問5分鐘,也就是300秒,然后對其進(jìn)行壓力測試。
5、基于sysbench構(gòu)造測試表和測試數(shù)據(jù)
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_read_write --db-ps-mode=disable prepare
上面我們構(gòu)造了一個(gè)sysbench命令,給他加入了很多的參數(shù),現(xiàn)在我們來 解釋一下這些參數(shù),相信很多參數(shù)大家自己看到也就大致明白什么意思了:
--db-driver=mysql:這個(gè)很簡單,就是說他基于mysql的驅(qū)動(dòng)去連接mysql數(shù)據(jù)庫,你要是oracle,或者sqlserver,那自然就是其他的數(shù)據(jù)庫的驅(qū)動(dòng)了
--time=300:這個(gè)就是說連續(xù)訪問300秒
--threads=10:這個(gè)就是說用10個(gè)線程模擬并發(fā)訪問
--report-interval=1:這個(gè)就是說每隔1秒輸出一下壓測情況
--mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user:這一大串,就是說連接到哪臺(tái)機(jī)器的哪個(gè)端口上的MySQL庫,他的用戶名和密碼是什么
--mysql-db=test_db --tables=20 --table_size=1000000:這一串的意思,就是說在test_db這個(gè)庫里,構(gòu)造20個(gè)測試表,每個(gè)測試表里構(gòu)造100萬條測試數(shù)據(jù),測試表的名字會(huì)是類似于sbtest1,sbtest2這個(gè)樣子的
oltp_read_write:這個(gè)就是說,執(zhí)行oltp數(shù)據(jù)庫的讀寫測試
--db-ps-mode=disable:這個(gè)就是禁止ps模式
最后有一個(gè)prepare,意思是參照這個(gè)命令的設(shè)置去構(gòu)造出來我們需要的數(shù)據(jù)庫里的數(shù)據(jù),他會(huì)自動(dòng)創(chuàng)建20個(gè)測試表,每個(gè)表里創(chuàng)建100萬條測試數(shù)據(jù),所以這個(gè)工具是非常的方便的。
6、對數(shù)據(jù)庫進(jìn)行360度的全方位測試
測試數(shù)據(jù)庫的綜合讀寫TPS,使用的是oltp_read_write模式(大家看命令中最后不是prepare,是run了,就是運(yùn)行壓測):
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_read_write --db-ps-mode=disable run
測試數(shù)據(jù)庫的只讀性能,使用的是oltp_read_only模式(大家看命令中的oltp_read_write已經(jīng)變?yōu)閛ltp_read_only了):
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_read_only --db-ps-mode=disable run
測試數(shù)據(jù)庫的刪除性能,使用的是oltp_delete模式:
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_delete --db-ps-mode=disable run
測試數(shù)據(jù)庫的更新索引字段的性能,使用的是oltp_update_index模式:
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_update_index --db-ps-mode=disable run
測試數(shù)據(jù)庫的更新非索引字段的性能,使用的是oltp_update_non_index模式:
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_update_non_index --db-ps-mode=disable run
測試數(shù)據(jù)庫的插入性能,使用的是oltp_insert模式:
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_insert --db-ps-mode=disable run
測試數(shù)據(jù)庫的寫入性能,使用的是oltp_write_only模式:
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_write_only --db-ps-mode=disable run
使用上面的命令,sysbench工具會(huì)根據(jù)你的指令構(gòu)造出各種各樣的SQL語句去更新或者查詢你的20張測試表里的數(shù)據(jù),同時(shí)監(jiān)測出你的數(shù)據(jù)庫的壓測性能指標(biāo),最后完成壓測之后,可以執(zhí)行下面的cleanup命令,清理數(shù)據(jù)。
sysbench --db-driver=mysql --time=300 --threads=10 --report-interval=1 --mysql-host=127.0.0.1 --mysql-port=3306 --mysql-user=test_user --mysql-password=test_user --mysql-db=test_db --tables=20 --table_size=1000000 oltp_read_write --db-ps-mode=disable cleanup
7、壓測結(jié)果分析
按照我們上面的命令,我們是讓他每隔1秒都會(huì)輸出一次壓測報(bào)告的,此時(shí)他每隔一秒會(huì)輸出類似下面的一段東西:
[ 22s ] thds: 10 tps: 380.99 qps: 7312.66 (r/w/o: 5132.99/1155.86/1321.35) lat (ms, 95%): 21.33 err/s: 0.00 reconn/s: 0.00
我來給大家解釋一下這是什么意思,首先他說的這是第22s輸出的一段壓測統(tǒng)計(jì)報(bào)告,然后是其他的一些統(tǒng)計(jì)字段:
thds: 10,這個(gè)意思就是有10個(gè)線程在壓測
tps: 380.99,這個(gè)意思就是每秒執(zhí)行了380.99個(gè)事務(wù)
qps: 7610.20,這個(gè)意思就是每秒可以執(zhí)行7610.20個(gè)請求
(r/w/o: 5132.99/1155.86/1321.35),這個(gè)意思就是說,在每秒7610.20個(gè)請求中,有5132.99個(gè)請求是讀請求,1155.86個(gè)請求是寫請求,1321.35個(gè)請求是其他的請求,就是對QPS進(jìn)行了拆解
lat (ms, 95%): 21.33,這個(gè)意思就是說,95%的請求的延遲都在21.33毫秒以下
err/s: 0.00 reconn/s: 0.00,這兩個(gè)的意思就是說,每秒有0個(gè)請求是失敗的,發(fā)生了0次網(wǎng)絡(luò)重連
這個(gè)壓測結(jié)果會(huì)根據(jù)每個(gè)人的機(jī)器的性能不同有很大的差距,你要是機(jī)器性能特別高,那你可以開很多的并發(fā)線程去壓測,比如100個(gè)線程,此時(shí)可能會(huì)發(fā)現(xiàn)數(shù)據(jù)庫每秒的TPS有上千個(gè),如果你的機(jī)器性能很低,可能壓測出來你的TPS才二三十個(gè),QPS才幾百個(gè),這都是有可能的。
另外在完成壓測之后,最后會(huì)顯示一個(gè)總的壓測報(bào)告,我把解釋寫在下面了:
SQL statistics:
queries performed:
read: 1480084 // 這就是說在300s的壓測期間執(zhí)行了148萬多次的讀請求
write: 298457 // 這是說在壓測期間執(zhí)行了29萬多次的寫請求
other: 325436 // 這是說在壓測期間執(zhí)行了30萬多次的其他請求
total: 2103977 // 這是說一共執(zhí)行了210萬多次的請求
// 這是說一共執(zhí)行了10萬多個(gè)事務(wù),每秒執(zhí)行350多個(gè)事務(wù)
transactions: 105180( 350.6 per sec. )
// 這是說一共執(zhí)行了210萬多次的請求,每秒執(zhí)行7000+請求
queries: 2103977 ( 7013.26 per sec. )
ignored errors: 0 (0.00 per sec.)
reconnects: 0 (0.00 per sec.)
// 下面就是說,一共執(zhí)行了300s的壓測,執(zhí)行了10萬+的事務(wù)
General staticstics:
total time: 300.0052s
total number of events: 105180
Latency (ms):
min: 4.32 // 請求中延遲最小的是4.32ms
avg: 13.42 // 所有請求平均延遲是13.42ms
max: 45.56 // 延遲最大的請求是45.56ms
95th percentile: 21.33 // 95%的請求延遲都在21.33ms以內(nèi)
8、今日作業(yè)
今天希望大家可以完成一個(gè)作業(yè),自己準(zhǔn)備一臺(tái)linux機(jī)器或者虛擬機(jī),然后裝一個(gè)mysql數(shù)據(jù)庫,接著使用sysbench工具嘗試一下數(shù)據(jù)庫的壓測,自己分析一下壓測的報(bào)告和結(jié)果,感受一下你的數(shù)據(jù)庫到底能抗多高的并發(fā)。
同時(shí)接下來我們還會(huì)給大家講解在壓測的過程中,如何去觀察機(jī)器的其他重要的性能指標(biāo),比如說CPU、網(wǎng)絡(luò)、內(nèi)存、磁盤IO,等等。
End
專欄版權(quán)歸公眾號(hào)儒猿技術(shù)窩所有
未經(jīng)許可不得傳播,如有侵權(quán)將追究法律責(zé)任