最近做了一個(gè)搜索接口的優(yōu)化,反復(fù)壓測了四次吼和,終于達(dá)到要求了涨薪,記錄一下,晚上加個(gè)雞腿??
業(yè)務(wù)邏輯
從OpenSearch中檢索出數(shù)據(jù)炫乓,然后各種填充組裝數(shù)據(jù)刚夺,最后返回
邏輯看似很簡單,當(dāng)初我也是這樣認(rèn)為的末捣,于是預(yù)估5天完成侠姑,最后前前后后開發(fā)、聯(lián)調(diào)箩做、改bug直到上線差不多花了10天(當(dāng)然這10天并不是只做這一件事情)
復(fù)雜在于影響返回結(jié)構(gòu)的因素很多莽红,排除問題需要檢查配置、檢查數(shù)據(jù)庫邦邦、檢查緩存安吁、檢查OpenSearch、檢查代碼
言歸正傳燃辖,不管邏輯有多復(fù)雜鬼店,都不是你逃避問題的接口,更不是你不去優(yōu)化的理由郭赐,這不是本文的重點(diǎn)薪韩,優(yōu)化過程才是
要求,給APP提供的接口一般要求響應(yīng)時(shí)間在100ms以內(nèi)
第一次壓測
慘不忍睹捌锭,平均響應(yīng)時(shí)間150ms俘陷,而且在這次壓測過程中還發(fā)現(xiàn)其它的問題,后臺報(bào)錯(cuò)观谦,經(jīng)查是OpenSearch每秒查詢次數(shù)限制
優(yōu)化代碼與配置
1拉盾、修改OpenSearch配置,并且將壓測環(huán)境中的OpenSearch連接地址改為內(nèi)網(wǎng)地址
2豁状、將代碼中循環(huán)查詢緩存的地方改為一次性批量查詢返回
3捉偏、和相關(guān)同學(xué)確認(rèn)后去掉項(xiàng)目中無用的代碼
第二次壓測
雖然優(yōu)化了代碼倒得,修改了配置,但是情況更糟糕了夭禽,而且還改出了新的問題
當(dāng)時(shí)霞掺,反復(fù)檢查了代碼,確定查詢緩存的次數(shù)已經(jīng)是最少了讹躯,而且連接線程池相關(guān)參數(shù)也調(diào)到一個(gè)相對較大且合理的值了
如果菩彬,再壓測還是無法達(dá)到要求的話,只有出最后一招了:緩存結(jié)果集
即潮梯,以用戶ID和用戶搜索的關(guān)鍵詞為key骗灶,查詢的結(jié)果為value,緩存5分鐘
第三次壓測
總算符合要求了秉馏,并發(fā)60的時(shí)候響應(yīng)時(shí)間達(dá)到32ms耙旦,而我又發(fā)現(xiàn)了新的優(yōu)化點(diǎn)
接口中居然還有查數(shù)據(jù)庫的操作,這可不能忍萝究,排查之后去掉了一些不必要的依賴
成長
學(xué)會(huì)了使用RedisTemplate的executePipelined進(jìn)行redis批量查詢
針對本次優(yōu)化的總結(jié)
1免都、一定要絕對避免循環(huán)查數(shù)據(jù)庫和緩存(PS:循環(huán)里面就不能有查詢緩存,更不能有查詢數(shù)據(jù)庫的操作帆竹,因?yàn)檠h(huán)的次數(shù)沒法控制)
2琴昆、對于API接口的話,一般都是直接查緩存的馆揉,沒有查數(shù)據(jù)庫的
3、多用批量查詢抖拦,少用單條查詢升酣,盡量一次查出來
4、對于使用阿里云态罪,要留意一下相應(yīng)產(chǎn)品的配置噩茄,該花的錢還是得花,同時(shí)复颈,千萬要記得正式環(huán)境中使用相應(yīng)產(chǎn)品的內(nèi)網(wǎng)地址
5绩聘、注意連接池大小(包括數(shù)據(jù)庫連接池耗啦、Redis緩存連接池凿菩、線程池)
6、壓測的機(jī)器上不要部署其它的服務(wù)帜讲,只跑待壓測的服務(wù)衅谷,避免受其它項(xiàng)目影響;對于線上環(huán)境似将,最好一臺機(jī)器上只部署一個(gè)重要的服務(wù)
7获黔、沒有用的以及被注釋掉的代碼蚀苛,沒有用的依賴最好及時(shí)清理掉
8、集群自不用說
9玷氏、一些監(jiān)控類的工具工具可以幫助我們更好的定位問題堵未,比如鏈路跟蹤,這次項(xiàng)目中使用了PinPoint
10盏触、如果技術(shù)上優(yōu)化的空間已經(jīng)非常小了渗蟹,可以試著從業(yè)務(wù)上著手,用實(shí)際的數(shù)據(jù)說話耻陕,可以從日常的訪問量拙徽,歷史訪問量數(shù)據(jù)來說服測試
11、每一次代碼改動(dòng)都有可能引入新的問題诗宣,因此膘怕,每次修改代碼后都要回歸測試一下(PS:每次修改完以后,我都會(huì)用幾組不同的關(guān)鍵詞搜索召庞,然后比對修改前和修改后返回的數(shù)據(jù)是否一致岛心,這個(gè)時(shí)候postman,以及Beyond compare就派上用場了)
12篮灼、關(guān)鍵的地方一定要多加點(diǎn)兒日志忘古,方便以后排除問題,因?yàn)榕挪榫€上問題最主要還是靠日志
歡迎工作一到五年的Java工程師朋友們加入Java程序員開發(fā): 721575865
群內(nèi)提供免費(fèi)的Java架構(gòu)學(xué)習(xí)資料(里面有高可用诅诱、高并發(fā)髓堪、高性能及分布式、Jvm性能調(diào)優(yōu)娘荡、Spring源碼干旁,MyBatis,Netty,Redis,Kafka,Mysql,Zookeeper,Tomcat,Docker,Dubbo,Nginx等多個(gè)知識點(diǎn)的架構(gòu)資料)合理利用自己每一分每一秒的時(shí)間來學(xué)習(xí)提升自己炮沐,不要再用"沒有時(shí)間“來掩飾自己思想上的懶惰!趁年輕大年,使勁拼换薄,給未來的自己一個(gè)交代!