2008-12-30 98 views
4

我可以在postgresql日誌中看到某些簡單的查詢(無連接並僅使用匹配使用索引的條件)需要1到3秒的時間才能執行。我記錄的查詢花費的時間超過一秒鐘,因此有類似的查詢在一秒鐘內執行,而且不會被報告。PostgreSQL性能問題

當我使用EXPLAIN ANALYZE嘗試相同的查詢時,需要幾毫秒。

該表包含大約800萬條記錄並被廣泛地寫入和查詢。 我已經啓用了自動真空,甚至最近(幾個小時前)在該表上運行了一個VACUUM ANALYZE。

示例查詢日誌條目: Dec 30 10:14:57 db01 postgres [7400]:[20-1] LOG:duration:3857.322 ms語句:SELECT * FROM「responses」WHERE(「responses」.contest_id = 17469)AND(user_id不是 Dec 30 10:14:57 db01 postgres [7400]:[20-2] null)ORDER BY updated_on desc LIMIT 5

contest_id和user_id被編入索引。 updated_on未被編入索引。如果我將其編入索引,則查詢計劃程序將忽略contest_id索引並使用updated_on,而這會進一步降低查詢速度。上述查詢中沒有LIMIT的最大條目數不會超過1000.

任何幫助將不勝感激。

回答

0

這似乎是由於交換而發生的。

3

根據您是否可以提供更多細節,這裏可能會有所幫助。最有用的將是您的EXPLAIN ANALYZE的實際輸出,以便我們可以看到它在完成查詢時的作用。被查詢的表格的定義也可能與索引一起有用。越多越好的信息。我現在只能猜測發生了什麼,這裏有幾個盲目的刺:

  • 很多其他選擇同時發生在這個數據庫上,並定期的數據和/或結果即將到期在某處緩存中。
  • 有別的東西,定期鎖定此表爲3-4秒再次向上釋放它之前,在此期間,該查詢被卡住
  • 此表將被寫入這樣廣泛,該表統計結束了近從不反映實際情況,因此查詢分析器會對是否使用索引執行查詢做出決定。

其他人可能有其他的想法,但是。有關正在發生的更多信息可能會有用。

+0

如果問題是#1(很多其他SELECT ...),我可以做些什麼來提高性能? 我剛剛運行了解釋分析,耗時約4秒。當我用不同的ID再次運行它時,花了幾毫秒。 因此我懷疑它與從緩存中取出數據有關。 – 2008-12-30 05:44:12

+0

@Nikhil:運行它還不夠,你還必須閱讀它。如果您希望其他人幫助您瞭解您的績效問題,我們也必須閱讀它。 – Dustin 2008-12-30 06:34:48

0

pgsql-performance是一個很好的郵件列表來提出這些問題。

好像你這裏有兩個問題:

1)你想成爲能夠索引updated_on,但如果這樣做,PostgreSQL的選擇錯誤的計劃。

我的第一個猜測是PostgreSQL高估了匹配謂詞「(responses.contest_id = 17469) AND (user_id is not null)」的元組的數量。如果postgres首先使用該謂詞,則必須稍後對值進行排序才能實現ORDER BY。你說它匹配1000個元組;如果postgresql認爲它匹配100000,也許它認爲使用updated_on索引進行掃描將會更便宜。另一個因素可能是你的配置:如果work_mem設置爲低,它可能認爲排序比它更昂貴。

您確實需要顯示緩慢查詢的EXPLAIN ANALYZE輸出,以便我們可以看到爲什麼它可能選擇updated_on的索引掃描。

2)即使它沒有編入索引,有時需要一段時間才能執行,但你不知道爲什麼,因爲如果你手動運行它,它可以正常工作。

使用auto_explain contrib模塊,新增8.4。它允許您記錄需要花費很長時間的查詢的輸出EXPLAIN ANALYZE。只要記錄查詢,就可以完全解決現在的問題:每次運行查詢都很快。

0

如果完全相同的查詢在解釋分析中需要毫秒,並且日誌中有3秒(即,我認爲它恰好需要3秒,並非每次調用都需要那麼長時間) - 比它絕對意味着它鎖定問題。

0
  • 鎖定
  • 交換
  • CLUSTER /真空cron作業
  • 飽和網絡FULL
  • 飽和IO

檢查的iostat,vmstat的,iptraf ...