瀏覽器的時區與語系設定可能與 IP 所在地相矛盾。本文說明這種矛盾的成因,以及網站如何藉此識別 VPN。
你的 IP 位址顯示你在法蘭克福。你的瀏覽器 JavaScript 引擎卻回報系統時鐘設定為 America/Chicago,而 Accept-Language 請求頭要求的是 en-US。這三項資訊並非來自同一個源頭——IP 地理位置是從網路路由推斷出來的,而時區與語系則是直接讀取自你的作業系統——因此當 VPN 或代理只改變了 IP 時,另外兩項資訊會原地不動,矛盾便會暴露在任何檢查它們的人面前。這是用來識別非住宅連線最簡單、也最常用的訊號之一。
核心要點
- 瀏覽器的 JavaScript 時區與
Accept-Language請求頭來自作業系統/瀏覽器設定,並非來自網路連線——VPN 改變 IP 預設不會動到這兩者。 - 時區或語系與 IP 所在國家不符,是一種經典且成本低廉的 VPN/代理識別訊號,常與 IP 封鎖清單、WebRTC 洩漏檢測一併使用。
- 單一矛盾本身證據力薄弱:旅行者、僑民、跨國團隊每天都會產生真實的時區落差,因此偵測系統會把它與其他訊號合併評分。
- 商業代理/反偵測工具會嘗試自動把時區與語系對齊到出口 IP 所在地區——但不完整或不一致的對齊,本身就是一種可被偵測的模式。
- 你可以透過 BrowserInsight 的指紋檢測與VPN/代理檢測,確切查看自己瀏覽器目前廣播的時區、語系與 IP 位置。
三項訊號,三個不同來源
網站從你系統中互不相關的層面拼湊出你的「身分」,而這正是矛盾得以暴露的原因:
- IP 地理位置是伺服器端根據 IP 位址、對照註冊機構分配資訊與商業地理資料庫推算出來的。它反映的是你連線的出口位置——你的家用 ISP,或某台 VPN 伺服器——而非你人實際所在的地方。
- 時區來自作業系統時鐘,可透過
Intl.DateTimeFormat().resolvedOptions().timeZone暴露給 JavaScript,較粗略的方式則是Date.getTimezoneOffset()。它反映的是你(或你的裝置)設定的時區,多數人會把它留在「自動」,跟著自己實際所在地走。 - 語系/語言來自瀏覽器設定的語言清單,會隨每次請求以
Accept-Language請求頭送出,也可在 JavaScript 中透過navigator.language/navigator.languages讀取。它反映的是使用者設定作業系統或瀏覽器時選的語言——通常是母語,與目前連線所在地無關。
VPN 或代理會立即改變第一項訊號,卻不會動到另外兩項,除非有其他機制介入。這正是這種偵測方法的全部原理:時區或語系本身並不可疑,只是它們通常會跟著 IP 位置一起變動,而隧道只切斷了這層關聯中的一環。
JavaScript 時區與 IP 地理位置的對比
這是最常見的一種偵測方式。偵測器會讀取瀏覽器回報的 IANA 時區(例如 Europe/Berlin、America/New_York),並把它的 UTC 偏移量拿來和 IP 地理定位國家通常對應的偏移量比較。如果 IP 定位到德國,但瀏覽器回報的是 America/Chicago,這種長達數小時的偏移落差,對於一個實際身處法蘭克福的人來說,沒有任何合理的日常解釋。
這項檢查成本極低,因為兩份資料本來就已經存在:伺服器本來就掌握請求的 IP,而一行客戶端 JavaScript 程式碼就能暴露時區。依據規範內容協商請求頭的 RFC 9110 HTTP 語意規範,這一切都不需要任何特殊權限——它只是普通、未受保護的瀏覽器中繼資料,這正是它被廣泛用作被動訊號的原因。
值得注意的是,IP 地理位置本身就是近似值——它在國家層級相對可靠,但在城市層級雜訊很大——因此嚴謹的偵測器通常只檢查國家層級的時區區間是否合理,而不會要求偏移量精確到分鐘。
Accept-Language 與 IP 所在國家的對比
第二條偵測路徑原理與時區檢查相同,只是換成語言而非時鐘偏移。如果某個 IP 定位到日本,但請求的 Accept-Language 頭只列出 ru-RU 與 ru,完全沒有日語,這種組合對一名真實居民來說並不常見——但也遠非不可能,畢竟許多旅行者與僑民無論身處何地都會用母語瀏覽。
這正是為何在多數偵測體系中,語言不符通常被視為比時區不符更弱的證據:人們更換居住國的頻率,遠低於更換閱讀語言的頻率,因此一個來自東京 IP 的 ru-RU 請求頭本身只是輕微可疑,但與其他矛盾疊加起來就另當別論。
代理服務如何嘗試對齊這些訊號
住宅代理網路與反偵測瀏覽器的營運方深知這種檢測方式,因此許多產品會在頁面載入前,嘗試自動把時區與語系對齊到代理出口地區——偽造 Intl.DateTimeFormat 與 Accept-Language 請求頭,使其符合 IP 所在國家。
但這種做法只有在偽造完整且一致時才有效:
- 部分偽造很常見:某個工具覆寫了 JavaScript 時區 API,卻忘了同步修改 HTTP
Accept-Language請求頭,反之亦然——這會讓兩項訊號即使都已偏離原始值,彼此之間依然互相矛盾。 - 粗粒度對齊同樣常見:某個代理池把整個國家對應到單一固定時區或單一固定語言,這對小國家還行,但對橫跨多個時區(美國、俄羅斯、巴西)或常用多種語言的地區就會露餡——這些地區的真實居民展現出的差異,遠比統一打補丁的代理叢集豐富得多。
- 層與層之間的漂移會發生在作業系統層時區、JavaScript 回報的時區,以及 HTTP 語言頭分別由不同機制修補,並在瀏覽器更新或設定重置後失去同步時。
光看偽造後的某一個值,是看不出這些失效模式的——只有當偵測器交叉比對多項訊號、並把它們與 IP 一併核對時,這些問題才會顯現。這正是以一致性為基礎的指紋檢測要做的事。
時區/語系訊號對比
| 訊號 | 來源 | 讀取方式 | 作為 VPN 線索的強度 | 代理工具中常見的失誤模式 |
|---|---|---|---|---|
JS 時區(Intl/Date) | 作業系統時鐘+時區設定 | 客戶端 JavaScript | 中—高 | 已偽造但與 HTTP 語言頭不一致 |
Accept-Language 請求頭 | 瀏覽器語言清單 | 每次 HTTP 請求 | 低—中 | 時區已偽造,語言頭被遺漏 |
| IP 地理位置 | 網路路由/IP 資料庫 | 伺服器端 | 高(針對國家層級的聲明) | 不適用——這是被比對的基準訊號 |
| 綜合一致性評分 | 以上全部訊號交叉核對 | 伺服器+客戶端 | 高 | 各層之間對齊不一致 |
表中任何一列單獨看都不是決定性證據——跨國旅行者與跨國團隊每天都會產生真實的不符。綜合評分之所以有用,正是因為它「綜合」:一個時區對了但語言錯了(或反過來)的工具,看起來更像是自動化補丁,而不像一個真實生活跨越兩個時區的人。
如何檢查自己的設定
如果你想知道一個網站目前能從你的連線中看到什麼,可以照偵測器的順序逐一排查:
- 檢查瀏覽器廣播的資訊。 BrowserInsight 的指紋檢測會在同一處顯示你回報的 JavaScript 時區、語系與語言清單。
- 檢查 IP 聲稱的資訊。 執行 IP 情報或 VPN/代理檢測,查看你的連線被定位到哪個國家,以及是否被標記為已知的 VPN/代理網段——更完整的訊號清單請見網站如何偵測 VPN。
- 手動比對。 如果你的 IP 顯示一個國家,而時區或語系明顯指向另一個地方,且沒有旅行相關的合理解釋,那正是偵測器要捕捉的那種矛盾。
如果你刻意使用 VPN,並希望它看起來一致,實際可行的做法是選擇一台位於你想呈現地區的出口伺服器,並檢查瀏覽器回報的時區與語系是否與之吻合——而不是想當然地以為單單改變 IP 就足夠了。
常見問題
VPN 會自動改變我瀏覽器的時區嗎?
不會。VPN 只會改變你的 IP 位址以及流量經過的網路路徑。作業系統的時區與瀏覽器的語系設定獨立於網路連線,絕大多數 VPN 對這兩者都不會做任何更動。
光憑時區不符就足以讓我被封鎖嗎?
通常不會單獨觸發封鎖。偵測系統會把時區與語系訊號和 IP 信譽、WebRTC/DNS 洩漏檢測,以及連線模式綜合評分。單一矛盾會提高可疑度,但很少單獨導致封鎖。
為什麼我的真實時區有時仍與 IP 所在國家不符?
原因有很多且都合理:旅行時沒改家鄉時區設定、為總部位於異地的公司工作、使用經由其他國家路由的企業 VPN,或單純搬家後沒更新作業系統的自動時區。正因如此,偵測系統通常只會給這項訊號較低的權重。
我該如何查看瀏覽器具體回報的時區與語系?
打開 BrowserInsight 的指紋檢測,它會連同其餘瀏覽器指紋一併顯示你的 JavaScript 時區、Accept-Language 值與語系設定,方便你跟 IP 情報結果中聲稱的位置對照。
結語
時區與語系洩漏並非什麼精巧的單一招數——它只是瀏覽器從通常一致、偶爾不一致的獨立資訊源拼湊身分這個過程的副產品。VPN 會瞬間改變你的 IP,卻不會動到作業系統時鐘與語系設定,除非有別的機制介入;而「變了什麼」和「沒變什麼」之間的這道縫隙,正是一致性檢查要尋找的目標。了解其原理,能讓你審視自己的設定,而不是想當然地以為換了 IP 就萬事大吉。
推薦閱讀:


