不用命令列的 PGP 加密

PGP 的名聲是強大與難用並存,這正是如今許多人把金鑰貼上進 AI 聊天裡操作的原因——而私鑰恰恰是最不該去的地方。本指南用瀏覽器本機運行的 PGP 套件,走完涵蓋幾乎所有真實用途的四個操作:產生金鑰對、加密、解密、簽章與驗證——再加上決定這一切是否經得起考驗的金鑰衛生。

不要再把私鑰貼上進聊天機器人

這件事發生在一個可預料的時刻。金鑰匯不進去、訊息解不開、指紋對不上,看起來最快的辦法就是把整段內容——連私鑰一起——貼上進 AI 聊天,問它哪裡出了問題。不要這樣做。私鑰一旦進入聊天,就脫離了你的控制:它可能留在對話記錄裡、日誌裡、你日後分享的截圖裡,留在一台並不是你以為的那台裝置上。你無法撤回一次貼上。任何被複製進你不控制的系統的金鑰,都必須視為已外洩,這意味著撤銷它、重新來過——恰恰是那次貼上本想省掉的工作。

還有第二個問題,比第一個更安靜:答案可能是錯的。語言模型會拒絕某些金鑰處理請求,會截斷過長的裝甲文字塊,也可能在看錯中間內容之後,以十足的把握報出一個指紋或金鑰 ID。密碼學不原諒這種差一點。替代方案不是為了命令列而命令列,而是把工作放在本機完成,讓金鑰材料從不離開本機。這正是本站 PGP 套件 的用途:金鑰產生、加密、解密、簽章與驗證都在瀏覽器分頁中運行,什麼都不上傳。

PGP 到底給了你什麼

PGP——以其現代形態而言,即由 GnuPG 等工具實作的 OpenPGP 標準——是在一對金鑰之上建構的兩個操作。公鑰可以與任何人分享,可以列印、寄電子郵件或公開發布。私鑰則保密保存,由口令保護。任何用公鑰加密的內容,只能用配套的私鑰解密。這就是全部的保密機制:無需事先交換共享秘密,也無需在你正試圖保護的同一個渠道裡商定密碼。

簽章走的是反方向。你用私鑰簽章,任何持有你公鑰的人都可以驗證:簽章確實來自該私鑰的持有者,且被簽內容自此未被更改。兩者合起來,加密回答誰能讀這個?,簽章回答是誰寫的,它完整嗎?。而兩者都不回答誰在旁邊看著?——這個限制下文還會回到,因為它決定了 PGP 到底是不是合適的工具。

產生一對金鑰,然後用別人的公鑰加密

在一台你信任的機器上產生金鑰對,並從第一分鐘起區別對待兩個半部。公鑰那一半是名片:匯出它,給任何可能給你寫信的人,放在通訊對象能找到的地方。私鑰那一半是通往所有曾加密給你的訊息的主鑰匙,它屬於離線環境——放在做解密的那台機器上,並在獨立媒體上備一份加密備份,不要放雲端筆記、不要放信箱、不要放聊天裡。產生時,選一個不在任何地方重用的口令;本站的密碼產生器可以在本機產生一個長口令片語,這比在壓力之下臨時編一個要好。

加密是人們想像中的那一步,也是最簡單的一步。你取來收件者的公鑰——以你信任的方式取得,理由見下文——寫好訊息或附上檔案,然後用那把公鑰加密。輸出是一個裝甲文字塊,可以走普通電子郵件,因為它的內容只有配套私鑰的持有者能讀。這裡有一個值得直說的後果:如果你沒有同時加密給你自己的公鑰,你將無法重讀自己發出的內容。這個決定要有意地做,而不是出於意外。

注意是哪把金鑰做了這項工作。你用的是對方的公鑰,不是你自己的。當別人給你寫信、以及你簽章時,起作用的是你的金鑰對;當你給別人寫信時,起作用的是對方的。初學者的大部分困惑——以及大多數第一次嘗試的失敗——都是這個方向弄反了,結果是一條誰也打不開的訊息,偶爾連本該收到它的人也打不開。

解密收到的內容,簽章發出的內容,驗證收到的簽章

解密正是私鑰那些儲存規則掙得其地位的地方。有人寄給你一個裝甲文字塊或一個加密檔案;你用私鑰打開它,輸入口令,在本機讀到內容。這一步不需要網路、不需要伺服器、不需要帳戶,也不應有其中任何一樣。如果某個流程要求你把加密訊息和私鑰一起上傳到某個網站、讓它替你解密,那麼這個流程本身就是威脅——關掉那個分頁。

簽章與驗證是一對,而驗證是人們跳過的那一半。你做出的簽章告訴收件者:這來自這把金鑰的持有者,未經更改。你驗證的簽章則告訴你同樣的事,關於到達你手裡的內容——但前提是你真的去查,而且查的是你確信屬於寄件者的公鑰。驗證失敗不是一個可以點過去的警告。它只意味著三件事之一:內容在簽章後被改動了,簽章損壞了,或者簽章的金鑰不是你預期的那把。三者的結局相同:不要根據該內容行事,並透過另一個渠道詢問寄件者發生了什麼。

大多數日子裡,金鑰衛生就是安全本身

現實世界中的 PGP 失敗,很少是數學被攻破。它們是:一把沒有備份的私鑰隨著筆記型電腦一起遺失;一個從論壇帳戶重用來的口令;一把在對話中途過期的金鑰,於是通訊對象悄悄退回到明文。設定一個你真的會維護的過期時間——一到兩年是常見而合理的選擇——並在產生金鑰的當天就把續期日期寫進行事曆,而不是在它失效的那一週。

在產生金鑰的同時、趁你還不需要時,就產生撤銷憑證,並把它與備份放在一起。撤銷憑證是你向世界宣告一把金鑰已退役或已外洩的方式;產生它需要私鑰,而這恰恰是你在倒楣那天可能沒有的東西。口令、備份和撤銷憑證都不起眼,而它們正是一次事件與一個死胡同之間的區別。

最後是指紋。金鑰 ID 很短,不證明任何事;指紋是公鑰的長雜湊,比對它才是你確認自己手裡的金鑰就是通訊對象手裡那把的方式。用帶外方式比對——在通話中讀出來,對照一張對方給你的名片或一個由對方控制的頁面——不要在送來金鑰的同個郵件討論串裡比對。一把透過電子郵件到達、指紋也在同一封郵件裡的金鑰,等於自己驗證了自己,也就是說,它根本沒有被驗證。

誠實的限制,以及何時該用別的工具

PGP 加密的是內容。它不隱藏中繼資料:在電子郵件中,寄件者、收件者、時間和通常還有主旨行,對承載訊息的伺服器仍然可見,加密檔案的大小也說明問題。它還背著三十年的可用性歷史——金鑰管理困惑了一整代使用者,工具也從未像現代訊息應用那樣變得無形。這並不使它無用。這使它具體而明確:非同步的、面向檔案與訊息的加密,發生在能管理金鑰的人之間,沒有中央帳戶,也沒有居中的廠商。

日常對話用 Signal 是更好的工具:金鑰替你管理,中繼資料處理更強,也沒人需要在晚餐前比對指紋。為儲存或傳輸加密一個檔案,age 比 PGP 更簡單,也更難誤用。當你需要的只是一個簽章——簽署一個發布版本或一份文件——minisign 更小、更清晰。PGP 剩下的陣地是真實的:必須多年後仍可讀的電子郵件、既有基礎設施內部的簽章、跨工具跨數十年的互通性——而在這塊陣地上,這裡的 PGP 套件 把命令列從這項工作中拿掉,但不拿掉這項工作所要求的審慎。

常見問題

以瀏覽器為基礎的 PGP 安全嗎?

金鑰材料從不離開分頁:產生、加密、解密和簽章都在瀏覽器中本機運行,頁面不上傳也不儲存任何東西。但話說回來,瀏覽器只和運行它的裝置與瀏覽器本身一樣可信——擴充功能、惡意軟體和借來的機器都在它之下。對日常金鑰來說,這個權衡是合理的。對最高風險的金鑰——那把保護著發布版本、保險庫或他人資料的金鑰——請用一台離線機器,瀏覽器工具留給圖方便的工作。

我弄丟了私鑰或它的口令——有人能復原我的訊息嗎?

不能,這正是要點所在。沒有密碼重設,沒有客服台,沒有後門:一封加密給某個金鑰的訊息,如果其私鑰半部已遺失、或口令被遺忘,就會一直保持加密狀態。任何能替你復原它的人,也能替別人復原它。這正是衛生一節中備份與撤銷憑證存在的原因——備份讓你在遺失裝置後活下來,撤銷憑證讓你退役一把你再也用不了或再也不信任的金鑰。

我怎麼知道一把公鑰真的屬於那個人?

透過第二個渠道比對指紋:在通話中大聲讀出來,對照對方遞給你的名片,或對照一個由對方控制的頁面。指紋是公鑰的完整雜湊;如果兩邊一致,你拿到的就是對方持有的那把金鑰。金鑰伺服器什麼都不證明——任何人都可以上傳一把聲稱是任何姓名和電子郵件的金鑰,上架不等於驗證。從任何地方下載一把金鑰,再在另一個地方用指紋確認它,是應當瞄準的標準。