2017年4月19日 星期三

[SQL Server][SSMS] 透過建立Code snippet提升工作效率

前言
每個DBA 或者 DB Developer經常都會有許多自己撰寫的花式Script,透過這些語法去查詢DMV或者metadata來幫助我們在緊急狀況的時候做trouble shooting,或者是Load test的時候輔助我們找出bottleneck
但這些語法通常都不太好直接背起來,就算即時自己兜出來的script,其包含資訊也不是那麼完整。最後就會散落在各處(onenotetxt...等等),如果找不到或忘記又得去網路上google
每個同事也都會自己私藏一些好用的獨門秘方,卻沒有一個方便的共享平台。

這個問題困擾了我許久,後來我找到了在SSMS 2012之後推出的新功能 : Code snippet manager


What is Code snippet manager?

Code snippet manager是一個讓我們能用熱鍵自動帶出我們常用script的工具,如果有使用過Visual studio的朋友應該不太陌生。

我們可以透過CTRL + K + X 快速的呼叫出來,其實原先SSMS就有內建了許多讓我們建置tablestored procedure的方便語法。
如下圖所示:



那要如何建置我們自己客製用的script?
我們可以到下面位置找到SSMS原先提供的一些Snippet當作範本參考:
C:\Program Files (x86)\Microsoft SQL Server\130\Tools\Binn\ManagementStudio\SQL\Snippets

Step 1. 建立Folder並列入版控
首先我們建立一個Folder當作我們等等Code snippet manager 要指向的目錄,並將其commit svn或者其他版控軟體,方便整個team能隨時透過SVN UPDATE取得,也能共同編輯,將Sciprt寫得更加完整。



Step 2.撰寫Snippet
其實Snippet就是一個簡單的XML,根據微軟定義的tag我們可以定義其Title跟我們常用的Script,也可以達到帶參數進去的效果。
我們來看看一個簡單範例,這是一段方便我們查看某個table上面的Index使用狀況,透過查看其在Production 上面update , seek, Scan的次數得知是否有建了之後根本沒被採用的Index

<?xml version="1.0" encoding="utf-8" ?>
<CodeSnippets xmlns="http://schemas.microsoft.com/VisualStudio/2005/CodeSnippet">
<_locDefinition xmlns="urn:locstudio">
    <_locDefault _loc="locNone" />
    <_locTag _loc="locData">Title</_locTag>
    <_locTag _loc="locData">Description</_locTag>
    <_locTag _loc="locData">Author</_locTag>
    <_locTag _loc="locData">ToolTip</_locTag>
</_locDefinition>
<CodeSnippet Format="1.0.0">
<Header>
<Title>Check index usag</Title>
        <Shortcut></Shortcut>
<Description>Check index usage</Description>
<Author>Max Weng</Author>
<SnippetTypes>
<SnippetType>Expansion</SnippetType>
</SnippetTypes>
</Header>
<Snippet>
<Declarations>
<Literal>
<ID>YOURTABLENAME</ID>
<ToolTip>YOURTABLENAME</ToolTip>
<Default>YOURTABLENAME</Default>
</Literal>
</Declarations>
<Code Language="SQL">
<![CDATA[With IND_USG (DBNAME,SCHEMANAME, OBJNAME, TYPE, name, seeks, scans, lookups, updates)
AS
(SELECT DB_NAME(Database_ID) DBName,
SCHEMA_NAME(schema_id) AS SchemaName,
OBJECT_NAME(ius.OBJECT_ID) ObjName,
i.type_desc, i.name,
user_seeks, user_scans,
user_lookups, user_updates
FROM sys.dm_db_index_usage_stats ius
INNER JOIN sys.indexes i
ON i.index_id = ius.index_id
AND ius.OBJECT_ID = i.OBJECT_ID
INNER JOIN sys.tables t ON t.OBJECT_ID = i.OBJECT_ID)
select * from IND_USG
WHERE OBJNAME in ('$YOURTABLENAME$')
GO]]>
</Code>
</Snippet>
</CodeSnippet>
</CodeSnippets>

上述有幾個地方要進行修改:
1 . <Title> </Title>: 填入明確定義的Title方便在Code snippet中查找

2 .<SnippetType></SnippetType> : 這邊有兩種選擇
Expansion : 直接在你箭頭處塞入你要的Script
SurroundsWith : 在你選取的範圍前後加上你要的字串

3.
<Declarations>
<Literal>
<ID>YOURTABLENAME</ID>
<ToolTip>YOURTABLENAME</ToolTip>
<Default>YOURTABLENAME</Default>
</Literal>
</Declarations>

我們可以在其中宣告參數,提醒我們哪些地方在呼叫出來之後是要手動修改的。

4.
<Code Language="SQL">
<![CDATA[With IND_USG (DBNAME,SCHEMANAME, OBJNAME, TYPE, name, seeks, scans, lookups, updates)
AS
(SELECT DB_NAME(Database_ID) DBName,
SCHEMA_NAME(schema_id) AS SchemaName,
OBJECT_NAME(ius.OBJECT_ID) ObjName,
i.type_desc, i.name,
user_seeks, user_scans,
user_lookups, user_updates
FROM sys.dm_db_index_usage_stats ius
INNER JOIN sys.indexes i
ON i.index_id = ius.index_id
AND ius.OBJECT_ID = i.OBJECT_ID
INNER JOIN sys.tables t ON t.OBJECT_ID = i.OBJECT_ID)
select * from IND_USG
WHERE OBJNAME in ('$YOURTABLENAME$')
GO]]>
</Code>

這段就是重點部分,在CDATA之後帶入我們常用的 Script,要注意上面如果要使用參數的話,在這段使用時要在前後加上 $ 字號。

Step 3.SSMSImport我們剛剛所建立的snippet
接下來開啟我們的SSMS來將我們剛剛撰寫的scriptimport進來。

上面工作列 Tools Code snippet manager (CTRL + K , CTRL + B)




點選ADD →選取剛剛建立的FolderOK



此時我們透過CTRL + K + X就能快速帶出我們引以為豪的花式Script :)
 
雖然透過SSMS雖然也能點出Snippet,但還是建議大家背一下熱鍵,日後會很有幫助。

後記
大學時期一直很佩服教授能用Ultra edit寫出教務系統,快速的打字速度配上舊式鍵盤那清澈的聲音真是相當過癮阿!
 
但出社會後發現自己的記憶力實在沒那麼好,沒能背起大量的語法且很熟練的刻出漂亮的查詢語句。
尤其在Production support時,User要你在一個小時內查出原因並hotfix上去,如果突然忘記自己常用的monitor script且上網又查不到的話,真的會很無奈。

後來發現Code snippet幫我解決了這麻煩, 而且能透過版控在team中達到知識分享的效果,藉此互相討論更加進步。


不過在底層環境開發且沒那麼緊急時,其實多花點時間手刻,不熟的DMV就去查詢MSDN了解每個Column的定義,自己的能力是可以大幅提升的,Code snippet雖然好用但別寵壞就是。

沒有留言:

張貼留言