有一個簡單的表,用於存儲IIS日誌。查詢優化大約需要一分鐘的時間執行
表架構如下:
CREATE TABLE [dbo].[TBL_iisLog](
[cdate] [varchar](50) NULL,
[ctime] [varchar](50) NULL,
[serverip] [varchar](50) NULL,
[uri] [varchar](255) NULL,
[port] [varchar](50) NULL,
[username] [varchar](50) NULL,
[clientip] [varchar](50) NULL,
[useragent] [nvarchar](max) NULL
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
請注意,我已經添加在以下領域這三個指標:
username
clientip
- 的(
cdate
和ctime
組合)
的表,下面的查詢大約需要50 - 60秒,執行:
SELECT TOP 10
username Usename,
(SELECT COUNT(DISTINCT SUBSTRING(useragent, PATINDEX('%SIG:+%',useragent) + 5, 36))
FROM tbl_iislog AS SoftwareSignatureCountTempTable
WHERE (PATINDEX('%SIG:+%',useragent) > 0)
AND SoftwareSignatureCountTempTable.username = MainTBL.username
) AS SoftwareSignatureCount
,
(SELECT COUNT(DISTINCT
LEFT(useragent, IIF((PATINDEX('%VDB%',useragent) -1) > 0, PATINDEX('%VDB%',useragent) -1, 0))
+
RIGHT(useragent, IIF((PATINDEX('%BPC%',useragent) -1) > 0, PATINDEX('%BPC%',useragent) -1, 0))
)
FROM TBL_iislog UseragentTempTable
WHERE UseragentTempTable.username = MainTBL.username
) AS UserAgentCount
,
(SELECT COUNT(DISTINCT clientip)
FROM tbl_iislog AS IPTempTable
WHERE IPTempTable.username = MainTBL.username
) AS IPCount
,
(SELECT COUNT(clientip)
FROM tbl_iislog ConnectionsTempTable
WHERE ConnectionsTempTable.uri = '/version_checker.ver'
AND ConnectionsTempTable.username = MainTBL.username
) AS Connections
FROM TBL_iisLog AS MainTBL
WHERE (username LIKE 'softgsg-%') OR (username LIKE 'sg-%')
GROUP BY username HAVING COUNT(clientip) > 0
ORDER BY SoftwareSignatureCount DESC, Connections DESC
我會感謝任何意見幫我優化我的查詢。
你可以發佈執行計劃嗎? –
我認爲你可以大大簡化這一點。看起來你所有的計數都來自同一個表('TBL_iislog'),但你多次旋轉。嘗試並用case語句替換所有那些時髦的子查詢,這樣你只能擊中表格一次。 – Andrew
我正在看看可以做些什麼......你是否爲clientip和username創建了單獨的索引,並且它們是非聚簇索引嗎?你能提供你創建的索引腳本嗎? – PCG