iT邦幫忙

tag不存在或已被下架!

2026 iThome 鐵人賽

DAY 14
0

💡 今日學習目標:掌握 SEI (Software Engineering Institute) 後五大安全程式碼法則,理解最小權限原則與縱深防禦 (Defense in Depth) 的實務貫徹。


📌 前言:構建多層次的程式碼防禦網

昨天我們介紹了 SEI Top 10 Secure Coding Practices 的前五條法則(輸入驗證、重視警告、安全架構、KISS 保持簡潔與預設拒絕)。

今天,我們繼續探討後五條法則(法則 6 ~ 10)。這五條法則專注於**「權限控制、邊界清洗、多層防護與品質標準」**,是讓程式碼從「能跑」跨越到「堅不可摧」的關鍵!


🔍 SEI 後五大法則深度拆解

SEI CERT 安全程式碼十大實務法則,今天談的是後五條


法則 6:最小權限原則 (Adhere to Principle of Least Privilege)

  • 通則邏輯:任何進程、函數或資料庫連線,都只應該具備執行其特定任務所必需的最低限度權限
  • 反面案例:Web 應用程式直接用資料庫最高管理者(如 rootsa)權限連線資料庫!一旦發生 SQL 注入,駭客就能控制整台資料庫主機。
// ❌ 壞習慣:用超級管理員帳號連線 DB
Database.Connect(user="root", password="...")

// ✅ 最小權限實踐:為應用程式建立限制權限的專用帳號
Database.Connect(user="app_read_write", password="...") // 只擁有特定 Table 的 SELECT/INSERT/UPDATE 權限,禁止 DROP / ALTER

💡 最小權限不是只有資料庫帳號。同一個原則,在你的系統裡至少還有四個地方適用:

  • API Token / 金鑰:發給第三方的權杖,只給它真正需要的那幾個 scope,不要一律發全權。
  • 雲端 IAM 角色:這台主機真的需要「讀取整個 S3 bucket」嗎?還是只要讀某一個路徑?
  • 容器與服務帳號:容器裡不要用 root 跑你的應用程式,這是免費就能拿到的一層防護。
  • 檔案系統權限:程式需要「讀」設定檔,那就別給它「寫」的權限。

法則 7:淨化傳送給其他系統的資料 (Sanitize Data Sent to Other Systems)

  • 通則邏輯:當資料準備傳遞給第三方系統、Shell 命令行、外接 API 或前端瀏覽器時,必須根據目標系統的語法語境(Context)做清洗與轉義。
  • 防禦範疇
    • 送給 SQL DB ➔ 使用參數化。
    • 送給 Command Shell ➔ 做轉義(Escaping)或禁止呼叫 Shell。
    • 送給 HTML 瀏覽器 ➔ 做 HTML Entity Encode(防範 XSS)。

法則 8:實踐縱深防禦 (Practice Defense in Depth)

  • 通則邏輯:假設你的第一道防線一定會被攻破!系統必須具備多重獨立的防禦機制,而且每一層都要能單獨擋下攻擊,不能互相依賴。

縱深防禦六層模型:前端驗證不算防線,真正的防線全部在伺服器端

⚠️ 先破除一個超級常見的誤解:前端驗證不是防線

很多人畫縱深防禦時,第一層會寫「前端表單驗證」。這是錯的。

前端驗證只是使用者體驗:它讓使用者在按下送出前就知道格式不對,省得白跑一趟。但攻擊者根本不會用你的網頁:他直接對 API 發一個 curl 請求,你的 JavaScript 完全沒有機會被執行。

🛡️ 一句話記住前端驗證是給使用者的體貼,不是給攻擊者的防線。
你可以做,而且應該做,但絕對不能把它算進防禦層數裡

那真正的縱深長什麼樣?

上圖那六層的關鍵在於:它們彼此獨立,任何一層失守,下一層都還能單獨擋住

舉個具體的例子。假設攻擊者送進一段 SQL 注入字串:

  • 第 1 層漏了(輸入驗證的正規表達式寫得太寬鬆)
  • 第 2 層漏了(這支 API 忘了檢查資源擁有者)
  • 第 3 層漏了(商業邏輯沒有防呆)
  • 但第 4 層擋住了:參數化查詢讓那段字串永遠只是「資料」,不會變成指令。
  • 就算第 4 層也漏了,第 5 層還在:那個資料庫帳號根本沒有 DROP 權限。
  • 就算資料真的被撈走,第 6 層還在:欄位是加密儲存的,撈到的是一堆密文。

這就是縱深防禦的價值:它讓「一個疏忽」不等於「一場災難」。


法則 9:採用有效的品質保證技術 (Use Effective QA Techniques)

  • 通則邏輯:資安不能靠感覺,要靠多種互補的驗證手段,因為每一種都有它抓不到的東西。
手段 擅長抓什麼 我們在哪一天做過
SAST 靜態掃描 已知的危險寫法、硬編碼機密 Day 09 - 11
DAST 動態測試 執行時期才會現形的組態與行為問題
Fuzzing 模糊測試 沒人想過的畸形輸入造成的崩潰
人工 Code Review 商業邏輯與權限判斷的錯誤 Day 06
  • 重點:這四種抓到的東西幾乎不重疊。只做其中一種,就等於默認放棄了另外三類問題。

法則 10:採用安全程式碼標準 (Adopt a Secure Coding Standard)

📌 去找 SEI 的資料時,有件事要先知道。 十幾年來這些規則原始的網址是 wiki.sei.cmu.edu,網路上絕大多數教學、簡報甚至論文引用的都是那個網址。但那個站現在已經連不上了,請改從 SEI 官網進去。

這剛好又是 Day 08 那個教訓的翻版:資料會搬家,引用它的文章不會跟著搬。 遇到連結打不開時,先去官網找現在的入口,而不是以為自己記錯了。

💡 給小團隊與個人開發者的務實版本
「訂立標準」聽起來像大公司才做的事,但其實你在 Day 08 裝上 SonarQube for IDE 的那一刻,就已經在執行一套安全編碼標準了,它內建的那幾千條規則,正是別人幫你整理好的標準。

你要做的只有兩件事:不要把跳出來的規則隨手關掉,以及在 Day 28 把它接進 CI,讓標準從「個人自律」變成「系統強制」。


🎯 今日重點小結與防守心法

  • 🔹 心法 1:權限給得越少,風險越低。資料庫連線絕不用 root / sa,而且這個原則同樣適用於 Token、IAM 角色與容器帳號。
  • 🔹 心法 2:前端驗證不算防線。它是給使用者的體貼,不是給攻擊者的障礙。真正的防線,每一層都必須在伺服器端。
  • 🔹 心法 3:讓「一個疏忽」不等於「一場災難」。縱深防禦的價值不在於哪一層特別強,而在於沒有任何一層是唯一的那一層

💬 明日預告:【Day 15】OWASP Top 10 縱覽:2021 到 2025 的排名大洗牌
明天我們將進入業界最知名的資安榜單,看看四年之間,攻擊者的主戰場搬到哪裡去了!


上一篇
【Day 13】SEI 10 大安全程式碼法則 (上):輸入驗證 (Validate Input) 與預設拒絕
系列文
槍林彈雨下的資安防守:從品質觀念切入,帶開發者從零動手作資安 30 天14
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言