把檔案上傳到一個基於伺服器的轉換器,三件事會發生。你的檔案透過網路傳輸到你無法控制的某個 IP 位址。伺服器上的某個行程解碼它。然後,取決於網站的保留政策,檔案會留在磁碟上——短則幾分鐘,長則永久。
同樣的事情在瀏覽器分頁裡做,檔案不會離開你機器的記憶體。解碼器執行在瀏覽器引擎強制執行的 WebAssembly 沙箱內。網路從未被觸及。
這不僅是政策差異,更是架構差異。基於伺服器的轉換器可以承諾刪除你的檔案;瀏覽器端的轉換器無法洩漏你的檔案,因為它從一開始就從未收到過它們。
架構
用戶端轉換由四個層次組成:
第 1 層:檔案存取
當你拖放一個檔案到瀏覽器分頁時,DragEvent 或 <input type="file"> 會給 JavaScript 一個 File 物件。File 不是檔案的內容,而是一個參照:包含檔名、大小、MIME 類型,以及一個按需從磁碟讀取位元組到記憶體的方法(file.arrayBuffer())。
在這個方法被呼叫之前,零位元組被移動。檔案安靜地躺在你的檔案系統裡。瀏覽器的檔案選擇器是作業系統級別的對話框,網頁只能看到使用者明確選擇的 File 物件。
第 2 層:格式偵測
任何檔案的前幾個位元組都能可靠地標識其格式。JPEG 以 FF D8 FF 開頭。PNG 以 89 50 4E 47 開頭。HEIC 檔案包含一個 ftyp box,在位移 8 處帶有 heic 或 heif 品牌標記。
讀取檔案頭(通常是前 32 個位元組)足以確認它到底是什麼,無論副檔名是什麼。這項檢查在任何解碼器接觸像素資料之前執行。如果檔案頭不匹配,檔案立即被拒絕。沒有浪費的 CPU 週期,也不會在解碼到一半時彈出令人困惑的錯誤訊息。
第 3 層:解碼
原始位元組透過解碼器變成像素。用哪個解碼器取決於格式:
- JPEG、PNG、WebP、BMP:瀏覽器自帶這些格式的原生解碼器。
createImageBitmap()將壓縮位元組交給作業系統的編解碼器(Windows 上是 Windows Imaging Component,macOS 上是 Core Graphics,Linux/ChromeOS 上是 Skia),返回原始像素資料。這條路徑速度快,在作業系統支援的地方有硬體加速,且不需要額外程式碼。 - HEIC:除 Safari 外,沒有瀏覽器自帶 HEIC 原生解碼器。我們的轉換器內建了 libheif——一個編譯為 WebAssembly 的 C 函式庫。
.wasm二進位檔案(~1.2 MB 壓縮後)下載一次後快取。它在 WASM 沙箱內將 HEIF/HEIC 檔案解碼為原始 RGB 像素。 - PDF:PDF.js(Mozilla 的 PDF 渲染器)將每一頁以請求的解析度渲染到畫布。沒有伺服器端渲染。PDF 從未離開瀏覽器。
每個解碼器從記憶體讀取、向記憶體寫入。沒有解碼器會開啟 socket。WASM 沙箱尤其無法發起網路請求:瀏覽器不會向 WebAssembly 模組暴露網路 API。即使 C 程式碼呼叫了 socket(),沙箱也會攔截它。
第 4 層:編碼
原始像素進入 <canvas> 元素的 2D 上下文。canvas.toBlob() 或 canvas.toDataURL() 呼叫瀏覽器的內建編碼器輸出 JPG、PNG 或 WebP。編碼器是平台原生程式碼:和你的作業系統儲存截圖用的是同一條程式碼路徑。
輸出是一個 Blob——記憶體中的位元組緩衝區。它被交給下載連結,或者封裝進一個用 JavaScript 構建的 ZIP 壓縮檔。在整個過程中,沒有任何位元組觸碰到網路 socket。
瀏覽器強制執行了什麼
網頁執行在瀏覽器於引擎層面維護的沙箱內。這不是禮貌協議,而是由行程隔離強制執行的:
渲染器行程:JavaScript 引擎、DOM 和 WASM 執行時期執行在一個沙箱化行程中,沒有直接的檔案系統或網路存取權限。它透過 IPC 與瀏覽器行程通訊。
站點隔離:現代瀏覽器將每個來源放在自己獨立的渲染器行程中。你在 file-convert-factory.org 中的檔案對於執行在任何其他域名上的 JavaScript 是不可見的。
WASM 沙箱:WebAssembly 模組只能看到一塊平坦的線性記憶體緩衝區,別無他物。沒有檔案系統 API,沒有 fetch(除非 JavaScript 顯式匯入),沒有存取 DOM 或其他瀏覽器 API 的權限。一個被攻破的 WASM 模組最壞的情況是破壞自己的記憶體,讓分頁崩潰。
相比之下,基於伺服器的轉換器以特權行程執行在伺服器的作業系統上。它可以讀磁碟、寫磁碟、開啟網路連線、派生子行程。安全模型取決於伺服器營運者的能力和意圖。瀏覽器沙箱只取決於瀏覽器引擎的正確性,而瀏覽器沙箱是軟體領域中被審計最嚴格的安全邊界之一。
基於伺服器的轉換器承諾(和不承諾)什麼
基於伺服器的轉換器本身並不惡毒。很多是由善意的團隊營運的。問題出在結構上:
- 上傳步驟就是一次複製。你的檔案現在存在於兩個地方。你控制一個副本,別人控制另一個。
- 刪除是一個承諾。「我們 24 小時後刪除檔案」意味著你要信任那行日誌、那個定時工作、備份系統和每個有伺服器權限的員工。這些都無法從外部驗證。
- 元數據隨檔案一同傳輸。你照片的 EXIF 資料(GPS 座標、相機序號、時間戳)屬於檔案位元組的一部分。檔案上傳了,元數據也就上傳了。我們的 EXIF 隱私指南詳細介紹了裡面到底有什麼以及如何去除。簡單來說:本站的每個轉換器都會去除元數據,因為它解碼像素再重新編碼,丟棄了所有不屬於影像資料的內容。
- HTTPS 保護的是傳輸管道,不是端點。TLS 加密上傳過程中的資料,但對於檔案到達後發生的事情無能為力。
瀏覽器端轉換器的隱私保證更窄但更強。它說的是:你的檔案不會離開你的裝置,因為不存在讓它們離開的程式碼路徑。這是可驗證的。轉換檔案時開啟 DevTools 的 Network(網路)面板,你會看到 WASM 二進位檔案載入一次後就再也沒有任何網路請求。零位元組上傳。沒有對 /api/convert 的請求。沒有 WebSocket 流量。轉換完全在渲染器行程內發生。
親自驗證
你不必相信任何人的說辭。開啟 Chrome DevTools(F12),切換到 Network 面板,然後在任何工具頁面上轉換一個檔案。你能看到的唯一網路活動:
- 頁面 HTML、CSS 和 JavaScript:首次存取時載入一次。
- WASM 二進位檔案(針對 HEIC 轉換器):載入一次,之後快取。
- 分析請求(如果你沒有封鎖的話)。
沒有任何檔案資料離開瀏覽器。每個請求的 Content-Length 單位是 KB,不是 MB。任何會用 DevTools 的人都可以獨立驗證這一點。
對於基於伺服器的服務,你無法做同樣的斷言。你上傳檔案,得到結果,然後你只能相信伺服器確實刪除了它。
相關工具
本站的每一個轉換器都遵循這套架構。管線(拖放、驗證、解碼、編碼、下載)在所有 23 個工具上執行方式完全一致:
- HEIC 轉 JPG · HEIC 轉 PNG · HEIC 轉 WebP
- JPG 轉 PNG · JPG 轉 WebP · JPG 轉 ICO
- PNG 轉 JPG · PNG 轉 WebP · PNG 轉 ICO
- WebP 轉 JPG · WebP 轉 PNG · WebP 轉 ICO
- BMP 轉 JPG · BMP 轉 PNG · BMP 轉 WebP · BMP 轉 ICO
- PDF 轉 JPG · PDF 轉 PNG · PDF 轉 WebP
- 圖片轉文字 (OCR):同樣的用戶端架構,在 WASM 中執行 Tesseract
關於 WASM 沙箱的技術細節,參見我們的 WebAssembly 詳解。想深入了解你照片攜帶了什麼元數據,EXIF 隱私指南會逐位元組地教你讀取和去除它們。



