Azure SQL Database 連線加密(Connection Encryption)預設也是強制開啟的

公司的政策, 資料庫要連線加密, 並給我 sql server command:

-- 確認您已設定好網路加密並有成功啟用,請執行下列 Transact-SQL 查詢:
USE [master]
GO
SELECT DISTINCT (encrypt_option)
FROM sys.dm_exec_connections;
GO

事實上,Azure SQL 為了確保雲端資料傳輸的安全,在網路層級有非常嚴格的加密規範。不論你在連線字串裡有沒有設定,所有進出 Azure SQL 的流量都必須經過 TLS (Transport Layer Security) 加密。

你執行的這段指令完全正確,它能幫你檢查目前所有對資料庫的連線是否有進行加密。

1. 執行結果分析

當你在 Azure SQL 執行上述指令後,你預期會看到唯一一個結果:

encrypt_option
TRUE
  • TRUE:代表該連線目前正透過 TLS/SSL 進行加密傳輸。
  • 如果你在地端(On-Premises)自建的 SQL Server 執行,可能會看到 FALSE,但在 Azure SQL 上,你只會看到 TRUE

2. Azure SQL 的連線加密機制

Azure SQL 在連線安全上有以下幾個鐵律:

  • 強制加密 (Force Encryption):Azure SQL 伺服器端強制要求所有連線必須加密。即使客戶端(你的程式或 SSMS)在連線字串中寫了 Encrypt=False,Azure 依然會拒絕該未加密的連線請求。
  • TLS 版本要求:目前 Azure SQL 預設要求 TLS 1.2 或以上。較舊、有安全性漏洞的 TLS 1.0 和 1.1 預設是被停用的(你也可以在 Azure Portal 中手動將最低要求提高到 TLS 1.2)。

3. 客戶端(你的程式或工具)該如何設定?

雖然 Azure 端強制加密,但為了防止 「中間人攻擊 (Man-in-the-Middle)」,最佳實踐是在你的應用程式連線字串(Connection String)中明確加上以下參數:

Plaintext

Server=tcp:yourserver.database.windows.net,1433;Database=yourdb;Encrypt=True;TrustServerCertificate=False;
  • Encrypt=True:明確告知客戶端要啟用加密(與 Azure 端的強制政策呼應)。
  • TrustServerCertificate=False這點非常重要! 設定為 False 代表客戶端會嚴格驗證 Azure SQL 伺服器的 SSL 憑證是否合法(由信任的憑證頒發機構簽署)。如果設為 True,雖然會加密,但客戶端會盲目信任伺服器憑證,容易遭受中間人攔截。

總結

你的 TDE(靜態資料加密)和連線加密(傳輸中資料加密)在 Azure SQL 中都是預設啟動且強制執行的,這符合現代雲端資安的「預設安全 (Secure by Default)」原則!


SQL command:

SELECT DISTINCT (encrypt_option)
FROM sys.dm_exec_connections;

先回傳 False, 第回一列 True.

你在執行結果中同時看到了 FALSETRUE,這代表目前連線到你這台 Azure SQL 伺服器的連線中,有部分連線沒有啟用加密(FALSE)

這通常會讓原本預期「Azure SQL 會強制加密」的人感到驚訝。以下為你說明為什麼會出現 FALSE,以及如何調整:

1. 為什麼會出現 FALSE

Azure SQL Managed Instance (MI) 或是某些特定設定的 Azure SQL Database 環境中,如果客戶端是透過內部虛擬網路 (VNet / Private Endpoint) 進行連線,且伺服器端的「高度安全連線重定向 (Redirect)」機制在舊版驅動程式下運作時,有些系統內部的路由連線或舊版工具可能會被判定為 FALSE

另外,如果你使用的是地端 SQL Server (VM 或實體機),預設確實是允許 FALSE(未加密)連線的。

2. 這是資安風險嗎?該如何稽核?

是的,出現 FALSE 代表有資料正在以明文(Plaintext)在網路間傳輸,這在生產環境(Production)或合規性要求高的環境中是不被允許的。

你可以執行以下進階指令,揪出到底是「誰」或「哪台機器」在使用未加密的連線:

SQL

SELECT 
    c.session_id,
    c.encrypt_option,
    s.login_name,
    c.client_net_address,
    s.program_name,
    s.host_name
FROM sys.dm_exec_connections c
JOIN sys.dm_exec_sessions s ON c.session_id = s.session_id;

透過這個語法,你可以對照 encrypt_option = 'FALSE' 的那一列,查看:

  • client_net_address:是哪台 IP 連進來的?
  • program_name:是用什麼應用程式(例如:舊版 .NET 程式、舊版 SSMS、或是某個背景服務)?
  • login_name:是用哪個帳號登入的?

3. 如何強制所有人必須使用加密連線?

為了確保安全,你應該強制隔離那些未加密的連線。

方案 A:從 Azure Portal 修改(最推薦)

  1. 登入 Azure Portal,找到你的 SQL Server (邏輯伺服器) 或 Managed Instance。
  2. 在左側選單點選 「安全性 (Security)」 > 「網路 (Networking)」
  3. 檢查是否有 「最低 TLS 版本 (Minimum TLS Version)」 的設定,將其強制設定為 TLS 1.2。這會直接阻斷不支援現代加密協議的舊式未加密連線。

方案 B:修正應用程式連線字串(Connection String)

檢查程式碼中連線到該資料庫的字串,務必確保加上以下兩個參數:

  • Encrypt=True(強制加密傳輸)
  • TrustServerCertificate=False(嚴格驗證憑證,防止中間人攻擊)

只要客戶端正確啟動這兩個參數,再次執行你的 SQL 指令,FALSE 的項目就會消失,全部變成 TRUE 了!


看到這份清單,你可以完全放心了!這是一個非常健康的狀態,你的資料庫完全沒有外部的安全漏洞。

那些顯示為 FALSE 的連線,全部都有一個共同的特徵:它們是 Azure SQL 內部的「系統維護服務」,而不是來自外部或你的應用程式。

以下為你詳細拆解這份清單的結構:

1. 外部與應用程式連線:全部都是 TRUE (安全)

看這幾筆最關鍵的資料:

  • 你的 Go 語言應用程式 (go-mssqldb):來自 IP 20.48.25.146,狀態全部是 TRUE。這代表從 Kubernetes 叢集(ca-pr-backend-stg-...)連過來的業務流量都有經過 TLS 加密。

2. 為什麼那幾筆會是 FALSE

那些顯示為 FALSE 的連線,你可以注意到它們的特徵:

  • client_net_address 欄位顯示為 <named pipe>。這代表它們不是透過網路(TCP/IP)連進來的,而是「這台資料庫伺服器本機內部的行程(Processes)」在互相通訊。
  • program_name 是:
    • BackupService(微軟自動備份服務)
    • MetricsDownloaderDmvCollector(微軟收集效能指標與 DMV 監控資料的服務)
    • AutomaticTuningAgent(微軟的自動索引與效能最佳化顧問)
  • login_name 格式為 DB000001\WF-...。這是 Azure 後台自動指派給這台虛擬機器內部使用的本機服務帳號。

💡 結論:

因為這些服務與 SQL Server 根本就在「同一台主機的記憶體內」通訊(透過 Named Pipe,非網路),資料完全不會流出這台機器之外,所以 Azure 為了追求最佳效能,內部通訊預設不經過網路加密層(TLS)。這在架構上是安全且極為常見的設計。

結論

你的稽核可以順利過關了!

  1. 靜態資料 (Data at Rest):已透過 TDE 100% 加密。
  2. 傳輸中資料 (Data in Transit):所有來自外部、應用程式、非本機的網路連線,全部都已強制使用 TLS 加密 (TRUE)

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *