登入頁用來判斷能否使用通行金鑰的兩個零權限 WebAuthn 檢測,也會透露裝置類型、作業系統版本下限與瀏覽器引擎——微弱卻耐人尋味的指紋訊號。
2026 年 8 月,Google 的 Android Developers 官方部落格介紹了WhatsApp 如何為 10 億使用者升級到通行金鑰登入——證明通行金鑰(passkey)已經從早期嘗鮮功能,走向主流的預設選項。WhatsApp 是原生 Android App,但同樣的轉變也正在網頁上發生:登入頁面在提供通行金鑰選項之前,得先問瀏覽器一句「這台裝置能用通行金鑰嗎?」。本文要談的,就是這個問題的答案會透露什麼——不只透露給提問的網站,也透露給同一頁面上執行的任何其他指令碼。
核心要點
- 決定是否顯示通行金鑰介面的兩個能力檢測,都不需要任何權限。
PublicKeyCredential.isUserVerifyingPlatformAuthenticatorAvailable()與isConditionalMediationAvailable()都是回傳 Promise 的檢測,沒有權限提示、不需要使用者操作,也不會顯示任何介面——參見 WebAuthn Level 3 規範 與 MDN 的參考文件。 - 這個 true/false 答案與裝置類型、作業系統版本下限和瀏覽器引擎相關。 平台認證器指的是內建的使用者驗證機制——Face ID、Touch ID、Windows Hello 或 Android 螢幕鎖定——並與特定的作業系統版本和引擎掛鉤,因此單一個布林值區分訪客的能力,比你想像的更強。
- 老實說,它的資訊熵很低。 即使加上較新的
getClientCapabilities()能力清單,這些答案大多仍與 User-Agent 已透露的資訊重疊,單獨使用時幾乎無法進一步縮小範圍。 - 它真正的價值在於矛盾檢測,而非身分識別。 User-Agent 自稱是新款旗艦手機,卻沒有可用的平台認證器——這才是值得注意的情況,也是反偵測瀏覽器或模擬器的典型特徵。
- 這項檢測只透露能力。 它無法讓指令碼得知你在這個網站或任何網站上是否有通行金鑰,也無法得知你是誰——那需要一次明確、經使用者驗證、且限定於單一依賴方(relying party)的憑證流程。
每個「使用通行金鑰?」按鈕背後的兩個檢測
登入頁面若想提供通行金鑰選項,得先確認裝置能不能產生通行金鑰。WebAuthn 為此在 PublicKeyCredential 上提供了兩個靜態方法,均定義於 W3C 維護的 WebAuthn Level 3 規範:
isUserVerifyingPlatformAuthenticatorAvailable()只回答一個問題:這個瀏覽器在這台裝置上,能否使用可驗證使用者身分的內建認證器——Face ID 或 Touch ID、Windows Hello(臉部、指紋或 PIN),或 Android 裝置的生物辨識或螢幕鎖定驗證?MDN 文件將它描述為回傳Promise<boolean>的靜態方法。isConditionalMediationAvailable()回答的是一個範圍更窄、但相關的問題:這個瀏覽器能否在一般的使用者名稱欄位中,以自動填入的方式提供通行金鑰選項,而不必跳出對話框打斷頁面?
較新的瀏覽器還多了第三個、範圍更廣的方法:PublicKeyCredential.getClientCapabilities(),一次呼叫就回傳一整組布林值——包括條件式登入與建立、混合式(跨裝置)傳輸、通行金鑰平台認證器支援、Related Origin Requests、較新的「signal」系列方法,以及支援的擴充功能。和前兩個檢測一樣,它只要求安全(HTTPS)環境。
這幾個方法都具備與本文相關的三個特性:不需要權限提示、不需要使用者操作,本身也不會產生任何可見介面。頁面一載入就能呼叫,幾毫秒內取得答案,訪客完全察覺不到。這是刻意的設計——登入頁面本來就該悄悄判斷「使用通行金鑰登入」值不值得顯示。但也正因為如此安靜,頁面上的任何指令碼都能讀到這個答案,而不只是需要它的登入程式碼。
一組 true/false 究竟和什麼相關
單一個布林值聽起來幾乎沒什麼——就一個位元。但這個位元並不是獨立的雜訊,而是由真實的硬體與軟體條件決定,因此它區分訪客的精細程度,遠高於位元數給人的印象:
- 裝置類型。 平台認證器通常建立在硬體支援的金鑰儲存之上——安全隔離區(secure enclave)、TPM 或 Android 的硬體金鑰庫。較舊的桌機、許多虛擬機器與部分 Linux 環境無法提供;在手機上,答案還取決於使用者是否真的設定了螢幕鎖定。
- 作業系統版本下限。 各作業系統都是從某個特定版本起支援平台認證器;回傳
true代表裝置版本已達到或高於這個下限,精確度勝過大多數被動訊號。 - 瀏覽器引擎。 各引擎實作這個 API 的方式與時間不盡相同,因此答案也能框出目前使用的是哪個算繪引擎——以及大致的版本。
- 在某些設定下,是否受管理或虛擬化。 缺乏硬體安全儲存的裝置——部分虛擬機器、部分高度鎖定的企業管理映像——即使回報的作業系統與瀏覽器理應支援,也可能回傳
false。
把這些綜合起來,一對布林值的作用就不像兩個位元,而更像一個針對裝置世代、作業系統版本下限與引擎的粗略分類器——這些訊號背後的原理,請參考我們的瀏覽器指紋識別指南。但它終究只是分類器,而不是查詢表。這種相關性是真實且有用的,但不能當成關於某台特定裝置的證據。
誠實面對資訊熵:幾個位元,而非識別碼
這很容易被誇大,但不應該。單獨來看,isUserVerifyingPlatformAuthenticatorAvailable() 只回傳一個位元,isConditionalMediationAvailable() 最多再多一個。getClientCapabilities() 回傳的欄位較多,但彼此並不獨立:大多數欄位會隨瀏覽器品牌與版本一起翻轉,因為各廠商都是整批推出這些功能。對想把它當成獨立識別碼的人來說更不利的是,這些資訊幾乎都和 User-Agent 字串早已透露的作業系統與瀏覽器版本相關。加進既有的指紋之後,它能額外縮小的範圍非常有限。
它真正發揮作用的地方在別處:作為矛盾檢測,而不是識別碼。偵測方並不是單獨問「這裡回傳了什麼值」,而是問這個值是否與頁面已知的其他資訊一致。User-Agent 自稱是當前的旗艦手機,isUserVerifyingPlatformAuthenticatorAvailable() 卻回傳 false,這就是值得標記的矛盾:真正的旗艦手機都內建平台認證器,而且幾乎都設定了螢幕鎖定。同樣地,自稱是新版 Chrome 或 Safari 的 UA,卻完全沒有 getClientCapabilities() 方法,也說不過去。這種矛盾模式正是反偵測瀏覽器設定檔與偽裝的自動化程式的特徵:一項宣稱的屬性(新式 UA 字串)和另一項屬性(沒有平台認證器、沒有 TPM、沒有安全隔離區)對不上,因為這個設定檔是東拼西湊出來的,而不是從真實裝置上測得的。
這和媒體裝置指紋識別以及其他零權限硬體檢測的思路相同:沒有任何單一檢測能辨識出你,但每一項都是偽造設定檔必須自圓其說的地方,而前後一致遠比任何單一數值更難偽造。
諷刺之處:為隱私而生,自己卻成了小訊號
這一點值得細想。通行金鑰的設計目的,是用限定於單一網站、無法跨站關聯的金鑰對,取代密碼這種容易被釣魚、又常被多個網站重複使用的秘密。然而,提供這項改進的 API 本身,光是存在並回答 true 或 false,就洩漏了一個微小的被動訊號。
有兩點但書能讓這個結論保持持平,而不是危言聳聽。第一,有供測試用的軟體與虛擬認證器——瀏覽器開發人員工具與 CI 環境可以註冊一個虛擬平台認證器,即使機器上完全沒有真正的生物辨識硬體,也會回傳 true,所以這項檢測並非在所有情境下都能保證硬體存在。第二,這項檢測無法區分「沒有認證器」和「認證器尚未設定」。一支有指紋感應器卻沒設定螢幕鎖定的手機,或一台從未註冊 Windows Hello 的電腦,在這個 API 看來,可能和從來沒有這類硬體的裝置毫無二致。這兩點都指向同一個結論:把它當成微弱的輔助訊號,而不是強訊號——矛盾檢測的價值在於執行成本低,而不是單憑它就能下定論。
這項檢測不會透露什麼
這一節值得說得精確,因為誇大其詞最容易在這裡損害讀者的信任:
- 它不會透露你在這個網站或任何網站上是否有通行金鑰。「能力」(這台裝置能不能使用通行金鑰)和「註冊狀態」(某個依賴方是否已有特定憑證)是兩個完全獨立的問題,這個 API 只回答前者。
- 它不會透露你的身分。 WebAuthn 憑證在設計上就限定於單一依賴方——為某個網站建立的通行金鑰,無法被其他網站讀取、列舉或關聯,而且每個網站都會拿到各自的金鑰對,而不是像第三方 Cookie 那樣的共用識別碼。
- 要實際使用真正的憑證,必須經過明確的使用者驗證步驟。 能力檢測是無聲的,但真正用通行金鑰登入時,使用者仍須完成生物辨識或 PIN 驗證。能力檢測本身並不會讓人離這一步更近。
這種範圍限定是刻意的設計,而且比大多數被動指紋訊號的隱私邊界更強:可以和裝置認證比較——裝置認證針對特定裝置提出經密碼學簽章、強得多的宣告,而不是一個軟性、低熵的能力位元。通行金鑰能力檢測和匿名憑證在這個光譜上比較接近——兩者都是為了證明某個有限的屬性而不暴露身分——裝置認證則是本質上更強、也更具識別性的宣告。如果你關心的是網站如何推斷你登入了哪些帳號,而不是你的硬體能做什麼,那是完全不同的機制——請參考跨站登入偵測。
結語
通行金鑰能力檢測,是貫穿本部落格的「一致性檢查」概念的典型例子:單獨來看都很微弱的訊號,彼此交叉比對後,能抓出的問題比任何單一強訊號都多。它本身不構成指紋,也不像追蹤 Cookie 或認證權杖那樣帶來隱私風險——但它又是一個讓「你聲稱自己是什麼」和「你的裝置實際能做什麼」接受檢驗的地方:兩者不是吻合,就是不吻合。
我們的工具目前還不會檢測通行金鑰支援,但會顯示通行金鑰檢測結果會拿來交叉比對的那些訊號:執行指紋檢測,查看你的瀏覽器所透露的 User-Agent、平台與硬體屬性;或試試機器人偵測,看看這些屬性之間的矛盾如何被標記出來。
常見問題
檢測通行金鑰支援需要我的授權嗎?
不需要。isUserVerifyingPlatformAuthenticatorAvailable()、isConditionalMediationAvailable() 與 getClientCapabilities() 都是無聲、以 Promise 為基礎的檢測——沒有權限提示、不需要使用者操作,頁面上也看不到任何變化。
網站能得知我是否儲存了通行金鑰嗎?
不能。這些檢測回報的是裝置的能力——是否存在平台認證器——而不是你是否已為該網站或任何網站註冊通行金鑰。憑證註冊狀態依依賴方各自隔離,這個 API 不會透露。
這項檢測回傳 false,一定有意義嗎?
單獨來看不一定。它可能代表裝置確實沒有平台認證器,也可能是有認證器但尚未設定(例如沒有設定螢幕鎖定,或未註冊 Windows Hello),或者——在測試環境中——只是還沒有註冊虛擬認證器。請把它當成一個微弱的輔助訊號,而不是確定的答案。
這和裝置認證有什麼不同?
強度差很多。這項能力檢測是一個軟性、低熵的布林值,與裝置類型及作業系統/瀏覽器版本相關。裝置認證則是針對特定裝置、經密碼學簽章且有硬體支撐的宣告——強度高得多,也更具識別性。
推薦閱讀:


