當使用連接服務器(Linked Servers)時,最昂貴的代價就是網絡帶寬間大量數據的傳輸。在正確的服務器書寫正確的代碼是很是重要的,由於每個錯誤都會致使在網絡帶寬上付出很是昂貴的代價。 下面是使用連接服務器(Linked Servers)時的幾個常見錯誤:mysql
1:使用推送方式而不是拉方式取數sql
出人意料以外的是,使用連接服務器推送數據比拉取數據慢得多。Linchi Shea寫了一篇很好的博客討論這個。數據庫
Linchi Shea 使用openquery來講明二者間的差別,可是這個也會發生在使用連接服務器的SQL語句中(這裏很差翻譯,其實就是查詢中使用Linked Server須要用到 LinkServer.DatabaseName.dbo.TableName)安全
2: 使用JOIN服務器
跨服務器查詢時,爲了在兩臺服務器之間的數據集之間執行JOIN操做,SQL Server須要將數據從一臺服務器傳送到另一臺服務器。若是傳送的數據是一個很是大的表,這個過程可能會很是痛苦。一般來講,數據會從遠程服務器傳送到本地服務器。爲了防止大量數據在服務器之間大傳送,你能夠經過在查詢條件中過濾數據,經過一個遠程存儲過程只取回相關數據來達到目的,萬一你須要使用INNER JOIN關聯兩個不一樣服務器之間的數據集,並且本地表的數據量遠小於遠程服務器的那個表。你可使用REMOTE JOIN HINT, 這樣就會將數據從本地服務器將數據傳送到遠程服務器,從而提升性能網絡
3:使用UNIONapp
正如JOIN操做,UNIION不一樣服務器之間的兩個數據集一定致使從遠程服務器傳送數據到本地服務器。即便你執行遠程查詢合併(UNION)同一個遠程服務器的兩個數據集,仍是會先將兩個數據集傳送到本地服務器,而後UNION兩個數據集,能夠經過遠程存儲過程,函數或視圖先UNION數據庫來阻止這個函數
4:書寫太複雜的查詢語句性能
優化器不能老是能明白你須要作什麼,尤爲是你的SQL語句中使用了連接服務器(Linked Server)時,例如, 我遇到過一個相似以下SQL語句,執行了10分鐘測試
1: SELECT *
2: FROM LocalTable
3: WHERE SomeColumn <
4: (SELECT COUNT(*)
5: FROM RemoteServer.SomeDB.dbo.SomeTable
6: WHERE SomeColumn > 100)
我像這樣修改了查詢語句
1: DECLARE @Count INT
2: SELECT @Count = COUNT(*)
3: FROM RemoteServer.SomeDB.dbo.SomeTable
4: WHERE SomeColumn > 100
5:
6: SELECT *
7: FROM LocalTable
8: WHERE SomeColumn < @Count
這樣重寫SQL後,查詢語句只跑了一秒就查詢出結果了,保持SQL腳本簡單。
5:當數據庫位於同一個實例時使用連接服務器(Linked Server)
這種場景的性能損耗可能不像其它場景那樣明顯,可是這種方式比使用數據庫前綴(Database.dbo.TableName)要慢
若是你想區別這兩種情形,能夠在測試數據庫測試、對比這兩種方法的性能,而後決定性能的提高是否值得在生產環境修改代碼。在某些狀況下,它是會提高性能的。
主要問題:一、性能問題 二、安全問題