天天看點

PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析

postgresql 的gui用戶端比較多,有開源的,也有商業的。

用得比較多的可能是pgadmin了,有些人可能會用edb的pem。

但實際上這兩個gui都有一個小問題,在傳回較大的結果集時,會非常的慢。

例如 :

資料庫端建立一個表,插入約30mb資料。

使用edb的pem或者pgadmin連接配接到資料庫 :

在gui中執行 :

耗時20秒。

換個執行語句:

3秒傳回。

copy與select * 查詢的資料量一樣多,而且都是全表掃描,但是時間卻相差10幾秒。

原因排查

在pgadmin用戶端的機器上,觀察到一個現象 :

執行select * from test;時,網絡使用率不高,持續時間長。

網絡傳輸結束後,cpu馬上飙高,估計pgadmin在處理資料,很長一段時間後,才開始展示結果。

PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析
PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析

而更換為

後,執行非常迅速,而且展示也非常快,可以看到網絡使用率很高,出現了一個尖峰。

PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析

将gui用戶端更換為heidisql後,執行 select * from test; 執行速度很快,與copy相當。

從網絡使用率來看,也出現了一個尖峰,資料很快就傳完了。

PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析

使用 postgresql 用戶端 psql 指令執行select * from test,速度也和heidisql一樣,很快。

對比以上幾種情況,說明pgadmin和pem在處理 select 時,效果并不理想,如果要傳回大量的結果集,請慎用。

如果使用pem或者pgadmin要傳回大量結果集,建議使用遊标來傳回:

例子:

網絡流量對比圖 :

PostgreSQL IDE pgadmin , edb postgres enterprise manager 查詢慢的問題分析

從左往右數

第1個尖峰,heidisql中執行select * from test;

第2個尖峰,pgadmin中執行copy (select * from test) to stdout;

第3個尖峰,pgadmin中執行copy test to stdout;

第4個尖峰,psql中執行select * from test;

說明 select * from test 的網絡傳輸流量确實比copy的更大一些。

heidisql不支援 copy指令.

如果你用的是windows平台,并且遇到了與之類似的問題,建議排查一下用戶端程式的代碼,從程式層面來解決這個問題。

這個問題我也會回報給pgadmin和edb,看看他們怎麼解決。

最後要給應用開發人員的一個小建議 :

查詢大結果集,給使用者展示資料的sql,建議修改為用遊标打開,一次fetch少量資料, 拿到資料馬上就可以向使用者展示,背景可以根據政策選擇是否再繼續fetch剩餘的資料。

這樣做的好處是使用者體驗更好,同時有可能可以大大減少資料庫的網絡開銷和cpu開銷(因為使用者并不一定要查詢所有資料)如果使用者關閉視窗,可以不再fetch其他資料。

大多數類似的應用場景,都是這樣來設計的。