欧美成人精品手机在线观看_69视频国产_动漫精品第一页_日韩中文字幕网 - 日本欧美一区二区

LOGO OA教程 ERP教程 模切知識(shí)交流 PMS教程 CRM教程 開(kāi)發(fā)文檔 其他文檔  
 
網(wǎng)站管理員

[點(diǎn)晴永久免費(fèi)OA]詳解瀏覽器指紋

admin
2022年7月15日 8:55 本文熱度 1149

什么是瀏覽器指紋

瀏覽器指紋可以通過(guò)瀏覽器對(duì)網(wǎng)站可見(jiàn)的配置、設(shè)置信息,來(lái)跟蹤 Web 瀏覽器,它就像我們?nèi)耸稚系闹讣y一樣,具有個(gè)體辨識(shí)度,只不過(guò)現(xiàn)階段瀏覽器指紋辨別的是瀏覽器。

瀏覽器指紋辨識(shí)的信息可以是 UA、時(shí)區(qū)、地理位置或者是使用的語(yǔ)言等等,瀏覽器所開(kāi)發(fā)的信息決定了瀏覽器指紋的準(zhǔn)確性。

對(duì)于網(wǎng)站而言,拿到瀏覽器指紋并沒(méi)有實(shí)際價(jià)值,真正有價(jià)值的是瀏覽器指紋對(duì)應(yīng)的用戶信息。作為網(wǎng)站站長(zhǎng),收集用戶瀏覽器指紋并記錄用戶的操作,是一個(gè)有價(jià)值的行為,特別是針對(duì)沒(méi)有用戶身份的場(chǎng)景。

例如一個(gè)視頻網(wǎng)站,未注冊(cè)該網(wǎng)站的用戶 A 喜歡瀏覽二次元的視頻,通過(guò)瀏覽器指紋記錄這個(gè),那么下次可以直接向該瀏覽器推送二次元的視頻。因?yàn)楝F(xiàn)在的上網(wǎng)設(shè)備大都是私人的,這樣的推送方式很容易獲得大部分用戶的好感,從而使之成為網(wǎng)站的用戶。

瀏覽器指紋的發(fā)展

瀏覽器指紋技術(shù)的發(fā)展跟大多數(shù)技術(shù)一樣,并非一蹴而就的,現(xiàn)有的幾代瀏覽器指紋技術(shù)是這樣的:

  • 第一代是狀態(tài)化的,主要集中在用戶的 cookie 和 evercookie 上,需要用戶登錄才可以得到有效的信息。
  • 第二代才有了瀏覽器指紋的概念,通過(guò)不斷增加瀏覽器的特征值從而讓用戶更具有區(qū)分度,例如 UA、瀏覽器插件信息等
  • 第三代是已經(jīng)將目光放在人身上了,通過(guò)收集用戶的行為、習(xí)慣來(lái)為用戶建立特征值甚至模型,可以實(shí)現(xiàn)真正的追蹤技術(shù)。但是目前實(shí)現(xiàn)比較復(fù)雜,依然在探索中。

目前瀏覽器指紋的追蹤技術(shù)可以算是進(jìn)入 2.5 代,這么說(shuō)是因?yàn)榭鐬g覽器識(shí)別指紋的問(wèn)題仍沒(méi)有解決。

指紋采集

信息熵(entropy)是接收的每條消息中包含的信息的平均量,信息熵越高,則能傳輸越多的信息,信息熵越低,則意味著傳輸?shù)男畔⒃缴佟?/p>

瀏覽器指紋是由許多瀏覽器的特征信息綜合起來(lái)的,其中特征值的信息熵也不盡相同。因此,指紋也分為基本指紋和高級(jí)指紋。

基本指紋

基本指紋就是容易被發(fā)現(xiàn)和修改的部分,如 http 的 header。

{  "headers": {    
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3",     
    "Accept-Encoding": "gzip, deflate, br",     
    "Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",     
    "Host": "httpbin.org",     
    "Sec-Fetch-Mode": "navigate",     
    "Sec-Fetch-Site": "none",     
    "Sec-Fetch-User": "?1",     
    "Upgrade-Insecure-Requests": "1",     
    "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/77.0.3865.90 Safari/537.36"
  }}

除了 http 中拿到的指紋,還可以通過(guò)其他方式來(lái)獲得瀏覽器的特征信息,例如:

  • 每個(gè)瀏覽器的UA
  • 瀏覽器發(fā)送的 HTTP ACCEPT 標(biāo)頭
  • 瀏覽器中安裝的瀏覽器擴(kuò)展/插件,例如 Quicktime,F(xiàn)lash,Java 或 Acrobat,以及這些插件的版本
  • 計(jì)算機(jī)上安裝的字體。
  • 瀏覽器是否執(zhí)行 Javascript 腳本
  • 瀏覽器是否能種下各種 cookie 和 “super cookies”
  • 是否瀏覽器設(shè)置為“Do Not Track”
  • 系統(tǒng)平臺(tái)(例如 Win32、Linux x86)
  • 系統(tǒng)語(yǔ)言(例如 cn、en-US)
  • 瀏覽器是否支持觸摸屏

拿到這些值后可以進(jìn)行一些運(yùn)算,得到瀏覽器指紋具體的信息熵以及瀏覽器的 uuid。

這些信息就類似人類的體重、身高、膚色一樣,有很大的重復(fù)概率,只能作為輔助識(shí)別,所以我們需要更精確的指紋來(lái)判斷唯一性。

高級(jí)指紋

普通指紋是不夠區(qū)分獨(dú)特的個(gè)人,這時(shí)就需要高級(jí)指紋,將范圍進(jìn)一步縮小,甚至生成一個(gè)獨(dú)一無(wú)二的跨瀏覽器身份。

用于生產(chǎn)指紋的各個(gè)信息,有權(quán)重大小之分,信息熵大的將擁有較大的權(quán)重。

在論文《Cross-Browser Fingerprinting via OS and Hardware Level Features [http://yinzhicao.org/Tracking...]》中更是詳細(xì)研究了各個(gè)指標(biāo)的信息熵和穩(wěn)定性。


從該論文中可以看出,時(shí)區(qū)、屏幕分辨率和色深、Canvas、webGL 的信息熵在跨瀏覽器指紋上的權(quán)重是比較大的。下面我們就來(lái)看看這些高級(jí)指紋都包含了些什么信息。

Canvas 指紋

Canvas 是 HTML5 中的動(dòng)態(tài)繪圖標(biāo)簽,也可以用它生成圖片或者處理圖片。即便使用 Canvas 繪制相同的元素,但是由于系統(tǒng)的差別,字體渲染引擎不同,對(duì)抗鋸齒、次像素渲染等算法也不同,Canvas 將同樣的文字轉(zhuǎn)成圖片,得到的結(jié)果也是不同的。

實(shí)現(xiàn)代碼大致為:在畫布上渲染一些文字,再用 toDataURL 轉(zhuǎn)換出來(lái),即便開(kāi)啟了隱私模式一樣可以拿到相同的值。

function getCanvasFingerprint () {    
    var canvas = document.createElement('canvas');    
    var context = canvas.getContext("2d");    
    context.font = "18pt Arial";    
    context.textBaseline = "top";    
    context.fillText("Hello, user.", 2, 2);    
    return canvas.toDataURL("image/jpeg");
}
getCanvasFingerprint()

流程很簡(jiǎn)單,渲染文字,toDataURL 是將整個(gè) Canvas 的內(nèi)容導(dǎo)出,得到值。

WebGL 指紋

WebGL(Web圖形庫(kù))是一個(gè) Javascript API,可在任何兼容的 Web 瀏覽器中渲染高性能的交互式 3D 和 2D 圖形,而無(wú)需使用插件。WebGL 通過(guò)引入一個(gè)與 OpenGL ES 2.0 非常一致的 API 來(lái)做到這一點(diǎn),該 API 可以在 HTML5 元素中使用。這種一致性使 API 可以利用用戶設(shè)備提供的硬件圖形加速。網(wǎng)站可以利用 WebGL 來(lái)識(shí)別設(shè)備指紋,一般可以用兩種方式來(lái)做到指紋生產(chǎn):

WebGL 報(bào)告——完整的 WebGL 瀏覽器報(bào)告表是可獲取、可被檢測(cè)的。在一些情況下,它會(huì)被轉(zhuǎn)換成為哈希值以便更快地進(jìn)行分析。

WebGL 圖像 ——渲染和轉(zhuǎn)換為哈希值的隱藏 3D 圖像。由于最終結(jié)果取決于進(jìn)行計(jì)算的硬件設(shè)備,因此此方法會(huì)為設(shè)備及其驅(qū)動(dòng)程序的不同組合生成唯一值。這種方式為不同的設(shè)備組合和驅(qū)動(dòng)程序生成了唯一值。

可以通過(guò) Browserleaks test 檢測(cè)網(wǎng)站來(lái)查看網(wǎng)站可以通過(guò)該 API 獲取哪些信息。

產(chǎn)生WebGL指紋原理是首先需要用著色器(shaders)繪制一個(gè)梯度對(duì)象,并將這個(gè)圖片轉(zhuǎn)換為Base64字符串。然后枚舉WebGL所有的拓展和功能,并將他們添加到Base64字符串上,從而產(chǎn)生一個(gè)巨大的字符串,這個(gè)字符串在每臺(tái)設(shè)備上可能是非常獨(dú)特的。

例如fingerprint2js庫(kù)的 WebGL 指紋生產(chǎn)方式:

// 部分代碼 

gl = getWebglCanvas()    
if (!gl) { return null }    
var result = []    
var vShaderTemplate = 'attribute vec2 attrVertex;varying vec2 varyinTexCoordinate;uniform vec2 uniformOffset;void main(){varyinTexCoordinate=attrVertex+uniformOffset;gl_Position=vec4(attrVertex,0,1);}'
var fShaderTemplate = 'precision mediump float;varying vec2 varyinTexCoordinate;void main() {gl_FragColor=vec4(varyinTexCoordinate,0,1);}'
var vertexPosBuffer = gl.createBuffer()    
gl.bindBuffer(gl.ARRAY_BUFFER, vertexPosBuffer)    
var vertices = new Float32Array([-0.2, -0.9, 0, 0.4, -0.26, 0, 0, 0.732134444, 0])
// 創(chuàng)建并初始化了Buffer對(duì)象的數(shù)據(jù)存儲(chǔ)區(qū)。
gl.bufferData(gl.ARRAY_BUFFER, vertices, gl.STATIC_DRAW) 
vertexPosBuffer.itemSize = 3
vertexPosBuffer.numItems = 3
// 創(chuàng)建和初始化一個(gè)WebGLProgram對(duì)象。
var program = gl.createProgram()
// 創(chuàng)建著色器對(duì)象
var vshader = gl.createShader(gl.VERTEX_SHADER)
// 下兩行配置著色器 
gl.shaderSource(vshader, vShaderTemplate)  // 設(shè)置著色器代碼 
gl.compileShader(vshader) // 編譯一個(gè)著色器,以便被WebGLProgram對(duì)象所使用
var fshader = gl.createShader(gl.FRAGMENT_SHADER)   
gl.shaderSource(fshader, fShaderTemplate)    
gl.compileShader(fshader)    
// 添加預(yù)先定義好的頂點(diǎn)著色器和片段著色器 
gl.attachShader(program, vshader)
gl.attachShader(program, fshader) 
// 鏈接WebGLProgram對(duì)象 
gl.linkProgram(program)
// 定義好的WebGLProgram對(duì)象添加到當(dāng)前的渲染狀態(tài) 
gl.useProgram(program)    
program.vertexPosAttrib = gl.getAttribLocation(program, 'attrVertex')    
program.offsetUniform = gl.getUniformLocation(program, 'uniformOffset')                           gl.enableVertexAttribArray(program.vertexPosArray)    
gl.vertexAttribPointer(program.vertexPosAttrib, vertexPosBuffer.itemSize, gl.FLOAT, !1, 0, 0)    
gl.uniform2f(program.offsetUniform, 1, 1)
// 從向量數(shù)組中繪制圖元 
gl.drawArrays(gl.TRIANGLE_STRIP, 0, vertexPosBuffer.numItems)    
try {        
    result.push(gl.canvas.toDataURL())    
} catch (e) {        
    /* .toDataURL may be absent or broken (blocked by extension) */
}

如何防止被生成“用戶指紋”

文章開(kāi)頭也提到了,很多人對(duì)瀏覽器這項(xiàng)技術(shù)是又愛(ài)又恨。因?yàn)橐淮蠖丫W(wǎng)站使用各種技術(shù)來(lái)“生成”用戶指紋,以便給網(wǎng)站用戶帶來(lái)更精準(zhǔn)的推薦和符合用戶的瀏覽習(xí)慣。而用戶在享受技術(shù)帶來(lái)便利的同時(shí),也不免會(huì)有“隱私泄露”的焦躁和不安感。那么我們?nèi)绾畏乐贡簧伞坝脩糁讣y”呢?

混淆 Canvas 指紋

我們已經(jīng)了解了是如何獲取 canvas 指紋的,那么應(yīng)該如何防范被惡意獲取呢?想混淆 Canvas 指紋,只需要在 toDataURL 得到的結(jié)果上做手腳就可以。

toDataURL() 將整個(gè)canvas的內(nèi)容導(dǎo)出,我們需要將 Canvas 中的部分內(nèi)容修改,這個(gè)時(shí)候可以通過(guò) getImageData() 復(fù)制畫布上指定矩形的像素?cái)?shù)據(jù),然后通過(guò) putImageData()將圖像數(shù)據(jù)放回,然后再使用 toDataURL() 導(dǎo)出的圖片就有了差異。

CanvasRenderingContext2D.getImageData() 返回一個(gè)ImageData對(duì)象,用來(lái)描述 Canvas 區(qū)域隱含的像素?cái)?shù)據(jù)。這個(gè)區(qū)域通過(guò)矩形表示,起始點(diǎn)為(sx, sy)、寬為sw、高為sh。

ImageData 接口描述了<Canvas>元素的一個(gè)隱含像素?cái)?shù)據(jù)的區(qū)域,可以由 ImageData() 方法構(gòu)造,或者由canvas 在一起的 CanvasRenderingContext2D 對(duì)象的創(chuàng)建方法:createImageData() 和 getImageData()。

ImageData 對(duì)象存儲(chǔ)著canvas對(duì)象真實(shí)的像素?cái)?shù)據(jù),它包含幾個(gè)只讀屬性:

  • width 圖片寬度,單位像素
  • height 圖片高度,單位像素
  • data

Uint8ClampedArray 類型的一位數(shù)組,包含著 RGBA 的整型數(shù)據(jù),范圍在 0~255。它可以視作初始像素?cái)?shù)據(jù),每個(gè)像素用 4 個(gè) 1 bytes 值(按照 red、green、blue、alpha 的順序),每個(gè)顏色值用0~255 中的數(shù)字代表。每個(gè)部分被分配到一個(gè)數(shù)組內(nèi)的連續(xù)索引,左上角第一個(gè)像素的紅色部分,位于數(shù)組索引的第 0 位。像素從左到右從上到下被處理,遍歷整個(gè)數(shù)組。

Unit8ClampedArray 包含 高度寬度4 bytes數(shù)據(jù),索引值從 0 ~ (wh4)-1 。

例如,讀取圖片中位于第 50 行,200 列的像素的藍(lán)色部分,則:

const blueComponent = imageData[50*(imageData.width * 4) + 200*4 + 2]

下面是實(shí)現(xiàn)混淆 Canvas 指紋的方法:

const toBlob = HTMLCanvasElement.prototype.toBlob;

const toDataURL = HTMLCanvasElement.prototype.toDataURL;
HTMLCanvasElement.prototype.manipulate = function() {
  const {width, height} = this;
  // 拿到在進(jìn)行toDataURL或者toBlob前的canvas所生成的CanvasRenderingContext2D
  const context = this.getContext('2d'); 
  const shift = {
    'r': Math.floor(Math.random() * 10) - 5,
    'g': Math.floor(Math.random() * 10) - 5,
    'b': Math.floor(Math.random() * 10) - 5
  };
  const matt = context.getImageData(0, 0, width, height);
  // 對(duì)getImageData生成的imageData(像素源數(shù)據(jù))中的每一個(gè)像素的r、g、b部分的值進(jìn)行進(jìn)行隨機(jī)改變從而生成唯一的圖像。
  for (let i = 0; i < height; i += Math.max(1, parseInt(height / 10))) {
    for (let j = 0; j < width; j += Math.max(1, parseInt(width / 10))) {
      const n = ((i * (width * 4)) + (j * 4));
      matt.data[n + 0] = matt.data[n + 0] + shift.r; // 加上隨機(jī)擾動(dòng)
      matt.data[n + 1] = matt.data[n + 1] + shift.g;
      matt.data[n + 2] = matt.data[n + 2] + shift.b;
    }
  }
  context.putImageData(matt, 0, 0); // 重新放回去
// 修改prototype.toBlob
Object.defineProperty(HTMLCanvasElement.prototype, 'toBlob', {
  value: function() {
    if (script.dataset.active === 'true') {
      try {
        this.manipulate(); // 在每次toBlob前,先混淆下ImageData
      }
      catch(e) {
        console.warn('manipulation failed', e);
      }
    }
    return toBlob.apply(this, arguments);
  }
});
// 修改prototype. toDataURL
Object.defineProperty(HTMLCanvasElement.prototype, 'toDataURL', {
  value: function() {
    if (script.dataset.active === 'true') {
      try {
        this.manipulate(); // 在每次toDataURL前,先混淆下ImageData
      }
      catch(e) {
        console.warn('manipulation failed', e);
      }
    }
    return toDataURL.apply(this, arguments);
  }
});

混淆其他指紋

與前面混淆canvas指紋混淆的思路是一致的,都是更改被獲取對(duì)象的原型的方法。

比如混淆時(shí)區(qū),就是更改 Date.prototype.getTimezoneOffset 的返回值。

混淆分辨率則是更改documentElement.clientHeight documentElement.clientWidth

混淆 WebGL 則要更改 WebGLbufferData getParameter方法等等。

當(dāng)然,我們也有一些簡(jiǎn)單的方法來(lái)防止被生成用戶指紋。例如我們可以通過(guò)瀏覽器的擴(kuò)展插件(Canvas Blocker、WebGL Fingerprint Defender、Fingerprint Spoofing等),在網(wǎng)頁(yè)加載前執(zhí)行一段 JS 代碼,更改、重寫 JS 的各個(gè)函數(shù)來(lái)阻止網(wǎng)站獲取各種信息,或返回一個(gè)假的數(shù)據(jù),以此來(lái)保護(hù)我們的隱私信息。


該文章在 2022/7/15 8:55:01 編輯過(guò)
關(guān)鍵字查詢
相關(guān)文章
正在查詢...
點(diǎn)晴ERP是一款針對(duì)中小制造業(yè)的專業(yè)生產(chǎn)管理軟件系統(tǒng),系統(tǒng)成熟度和易用性得到了國(guó)內(nèi)大量中小企業(yè)的青睞。
點(diǎn)晴PMS碼頭管理系統(tǒng)主要針對(duì)港口碼頭集裝箱與散貨日常運(yùn)作、調(diào)度、堆場(chǎng)、車隊(duì)、財(cái)務(wù)費(fèi)用、相關(guān)報(bào)表等業(yè)務(wù)管理,結(jié)合碼頭的業(yè)務(wù)特點(diǎn),圍繞調(diào)度、堆場(chǎng)作業(yè)而開(kāi)發(fā)的。集技術(shù)的先進(jìn)性、管理的有效性于一體,是物流碼頭及其他港口類企業(yè)的高效ERP管理信息系統(tǒng)。
點(diǎn)晴WMS倉(cāng)儲(chǔ)管理系統(tǒng)提供了貨物產(chǎn)品管理,銷售管理,采購(gòu)管理,倉(cāng)儲(chǔ)管理,倉(cāng)庫(kù)管理,保質(zhì)期管理,貨位管理,庫(kù)位管理,生產(chǎn)管理,WMS管理系統(tǒng),標(biāo)簽打印,條形碼,二維碼管理,批號(hào)管理軟件。
點(diǎn)晴免費(fèi)OA是一款軟件和通用服務(wù)都免費(fèi),不限功能、不限時(shí)間、不限用戶的免費(fèi)OA協(xié)同辦公管理系統(tǒng)。
Copyright 2010-2025 ClickSun All Rights Reserved