Python爬蟲(chóng)模擬登錄遇到的問(wèn)題——CSRF防御

背景

去年在公司寫(xiě)過(guò)一個(gè)爬蟲(chóng)工具,用于抓取自動(dòng)化報(bào)告通過(guò)率判莉、自動(dòng)發(fā)送報(bào)告豆挽。由于當(dāng)時(shí)是第一次接觸爬蟲(chóng),難免會(huì)遇到各種問(wèn)題券盅,解決方案全都是按照網(wǎng)上的一些爬蟲(chóng)文章示例帮哈,照貓畫(huà)虎寫(xiě)的。雖然能正常使用渗饮,但其實(shí)很多地方都沒(méi)弄明白但汞。最近學(xué)習(xí)了一些前端和后臺(tái)的原理,了解了cookie與session的機(jī)制互站,總算弄明白了爬蟲(chóng)登錄過(guò)程中的一個(gè)疑問(wèn)。

用戶登錄請(qǐng)求中的authenticity_token

編寫(xiě)爬蟲(chóng)第一步僵缺,在登錄公司的自動(dòng)化平臺(tái)時(shí)就遇到了一個(gè)難題胡桃,登錄請(qǐng)求中必須包含一個(gè)authenticity_token字段。令人頭大的是磕潮,完全不知道這個(gè)字段從何而來(lái)翠胰,而且該字段還每次都不一樣,參考的爬蟲(chóng)登錄示例也沒(méi)教白愿之景!真是急壞苯寶寶了??


登錄表單

后來(lái)翻了好多CSDN的爬蟲(chóng)貼,了解到知乎的登錄請(qǐng)求中也包含這樣一個(gè)字段膏潮,而作者的處理方式就是先訪問(wèn)一次登錄頁(yè)锻狗,然后從登錄頁(yè)中查找一個(gè)隱藏的authenticity_token字段。
借助F12發(fā)現(xiàn)焕参,公司的自動(dòng)化平臺(tái)登錄頁(yè)中也包含了這樣一個(gè)隱藏字段轻纪,試之,果然成功了......

登錄頁(yè)面中隱藏的token
#登錄源碼:
def login(login_url = 'http://****.com/users/sign_in', username, password):
    #請(qǐng)求頭
    my_headers = {
        'User-Agent' : 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/48.0.2564.116 Safari/537.36',
        'Accept' : 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',
        'Accept-Encoding' : 'gzip',
        'Accept-Language' : 'zh-CN,zh;q=0.8,en;q=0.6,zh-TW;q=0.4'
    }

    #獲取token
    sss = requests.Session()
    r = sss.get(login_url, headers = my_headers)
    reg = r'<input name="authenticity_token" type="hidden" value="(.*)" />'
    pattern = re.compile(reg)
    result = pattern.findall(r.content)
    token = result[0]
    
    #postdata
    my_data = {
    'commit' : '登錄',
    'utf8' : '%E2%9C%93',
    'authenticity_token' : token,
    'user[email]': username,
    'user[password]':password
    }
    
    #登錄后
    r = sss.post(login_url, headers = my_headers, data = my_data)
    return sss

"多年后的一個(gè)平靜的下午叠纷,當(dāng)我無(wú)意間瀏覽了一片CSRF攻擊的帖子刻帚,突然眼前一亮......老衲終于明白了這個(gè)authenticity_token的含義了!I崇众!終于徹底理解了當(dāng)年困擾我兩小時(shí)的難題了5嘟!顷歌!"
其實(shí)看峻,該token的作用就是防御CSRF攻擊,關(guān)于什么是CSRF衙吩,還得先了解下Session id互妓。

關(guān)于Session id的機(jī)制

HTTP請(qǐng)求的一大特點(diǎn)就是無(wú)狀態(tài),這也就導(dǎo)致服務(wù)端無(wú)法區(qū)分請(qǐng)求來(lái)自哪個(gè)客戶端坤塞。為了記錄每個(gè)用戶的狀態(tài)冯勉,跟蹤用戶的整個(gè)會(huì)話,web程序普遍采用了cookie與session技術(shù)摹芙。(由于cookie與session的內(nèi)容過(guò)多灼狰,在此不表,詳細(xì)原理可以參考一片文章:Cookie與Session機(jī)制)
關(guān)于cookie與session浮禾,最需要了解的幾點(diǎn)是:

  1. session機(jī)制運(yùn)行依賴(lài)于session id交胚,用于服務(wù)端跟蹤每個(gè)會(huì)話,而session id存在于本地的cookie當(dāng)中盈电;
  2. session id會(huì)隨瀏覽器進(jìn)程關(guān)閉的關(guān)閉而清除蝴簇,也就表示一次完整的會(huì)話結(jié)束了。當(dāng)下次再次訪問(wèn)該網(wǎng)站還需要登錄匆帚,重新建立一個(gè)會(huì)話熬词;
  3. 現(xiàn)在絕大多數(shù)瀏覽器都支持子窗體,子窗體能共享父窗體的session id吸重,而另起的瀏覽器進(jìn)程無(wú)法訪問(wèn)該session互拾。這也是為什么當(dāng)我們?cè)谀尘W(wǎng)站登錄后,在新的頁(yè)簽下打開(kāi)該網(wǎng)站依然是登錄狀態(tài)嚎幸,而另起一個(gè)瀏覽器進(jìn)程訪問(wèn)卻是非登錄狀態(tài)颜矿。

根據(jù)session機(jī)制以上特點(diǎn),就引申出了一個(gè)問(wèn)題:CSRF攻擊嫉晶。

什么是跨站請(qǐng)求偽造(CSRF)攻擊骑疆?

用戶每次點(diǎn)擊一個(gè)鏈接、提交一個(gè)表單车遂,其本質(zhì)就是對(duì)服務(wù)端發(fā)起一次請(qǐng)求封断。而CSRF攻擊的原理就是:攻擊者誘導(dǎo)用戶點(diǎn)擊一個(gè)鏈接,用戶在不知情的情況下提交了一次表單請(qǐng)求舶担。而表單的內(nèi)容則是攻擊者事先準(zhǔn)備好的坡疼。
簡(jiǎn)單舉個(gè)栗子??:

  1. 用戶小明登錄了論壇A,同時(shí)也打開(kāi)了一個(gè)危險(xiǎn)網(wǎng)站B(同一個(gè)瀏覽器中)衣陶;
  2. 網(wǎng)站B上有一個(gè)鏈接柄瑰,該鏈接的實(shí)質(zhì)內(nèi)容是針對(duì)論壇A的一個(gè)發(fā)帖請(qǐng)求(比如廣告貼)闸氮。
  3. 小明處于好奇點(diǎn)擊了該鏈接,造成的結(jié)果就是:小明在完全不知情的情況下在論壇A成功發(fā)表了一篇帖子教沾。

備注: 以上攻擊成功實(shí)施的關(guān)鍵在于蒲跨,小明已經(jīng)登錄論壇A,并且點(diǎn)擊跳轉(zhuǎn)后的瀏覽器子窗體是可以訪問(wèn)父窗體的session id的授翻。
假如小明復(fù)制該鏈接或悲,然后手動(dòng)打開(kāi)一個(gè)新的瀏覽器粘貼訪問(wèn)該鏈接,則會(huì)提示用戶處于非登錄狀態(tài)堪唐,該發(fā)帖請(qǐng)求會(huì)被拒絕巡语。原因是新打開(kāi)的瀏覽器無(wú)法獲取前一個(gè)瀏覽器中的session id,服務(wù)端會(huì)將該請(qǐng)求當(dāng)成一個(gè)新的會(huì)話淮菠,需要重新登錄后才能成功執(zhí)行發(fā)帖請(qǐng)求男公。

CRSF攻擊防御

既然大家都了解CRSF攻擊,自然有相應(yīng)的防御措施合陵,其中比較常用的就是采用token驗(yàn)證枢赔。
工作機(jī)制就是:用戶在發(fā)送表單時(shí)還需要攜帶一個(gè)token值。該token一般是填寫(xiě)表單頁(yè)中的一個(gè)隱藏字段拥知,每次訪問(wèn)都不同踏拜。通過(guò)該token的驗(yàn)證,服務(wù)端就能知道用戶的表單請(qǐng)求是否從表單填寫(xiě)頁(yè)面跳轉(zhuǎn)而來(lái)了举庶。
簡(jiǎn)單舉例:

  1. 當(dāng)小明主動(dòng)發(fā)帖時(shí)执隧,必定要先點(diǎn)擊發(fā)帖編輯頁(yè)面A,當(dāng)填寫(xiě)完帖子內(nèi)容后再點(diǎn)擊【發(fā)帖】按鈕户侥。此時(shí)會(huì)將小明填寫(xiě)的表單內(nèi)容連帶頁(yè)面A中隱藏的一個(gè)token發(fā)送給服務(wù)端。服務(wù)端驗(yàn)證token通過(guò)后才表示發(fā)帖成功峦嗤。
  2. 當(dāng)危險(xiǎn)網(wǎng)站誘導(dǎo)小明點(diǎn)擊危險(xiǎn)鏈接時(shí)蕊唐,由于該鏈接實(shí)質(zhì)就是一個(gè)發(fā)帖的post請(qǐng)求,跳過(guò)了訪問(wèn)發(fā)帖編輯頁(yè)面A的過(guò)程烁设,自然也就無(wú)法獲取有效token替梨,最終服務(wù)端會(huì)認(rèn)為該發(fā)帖請(qǐng)求不合法。

簡(jiǎn)單來(lái)說(shuō)装黑,服務(wù)端每次通過(guò)請(qǐng)求數(shù)據(jù)中的token來(lái)驗(yàn)證表單請(qǐng)求是否由用戶主動(dòng)發(fā)送的副瀑,從而有效防御了CRSF攻擊。

至此恋谭,也就明白了為什么登錄頁(yè)面時(shí)需要攜帶一個(gè)authenticity_token參數(shù)了糠睡,同時(shí)也理解了為什么需要訪問(wèn)登錄頁(yè)面獲取該token。??

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末疚颊,一起剝皮案震驚了整個(gè)濱河市狈孔,隨后出現(xiàn)的幾起案子信认,更是在濱河造成了極大的恐慌,老刑警劉巖均抽,帶你破解...
    沈念sama閱讀 219,039評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件嫁赏,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡油挥,警方通過(guò)查閱死者的電腦和手機(jī)潦蝇,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,426評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)深寥,“玉大人攘乒,你說(shuō)我怎么就攤上這事◆媛酰” “怎么了持灰?”我有些...
    開(kāi)封第一講書(shū)人閱讀 165,417評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)负饲。 經(jīng)常有香客問(wèn)我堤魁,道長(zhǎng),這世上最難降的妖魔是什么返十? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,868評(píng)論 1 295
  • 正文 為了忘掉前任妥泉,我火速辦了婚禮,結(jié)果婚禮上洞坑,老公的妹妹穿的比我還像新娘盲链。我一直安慰自己,他們只是感情好迟杂,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,892評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布刽沾。 她就那樣靜靜地躺著,像睡著了一般排拷。 火紅的嫁衣襯著肌膚如雪侧漓。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 51,692評(píng)論 1 305
  • 那天监氢,我揣著相機(jī)與錄音布蔗,去河邊找鬼。 笑死浪腐,一個(gè)胖子當(dāng)著我的面吹牛纵揍,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播议街,決...
    沈念sama閱讀 40,416評(píng)論 3 419
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼泽谨,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起隔盛,我...
    開(kāi)封第一講書(shū)人閱讀 39,326評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤犹菱,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后吮炕,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體腊脱,經(jīng)...
    沈念sama閱讀 45,782評(píng)論 1 316
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,957評(píng)論 3 337
  • 正文 我和宋清朗相戀三年龙亲,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了陕凹。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,102評(píng)論 1 350
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡鳄炉,死狀恐怖杜耙,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情拂盯,我是刑警寧澤佑女,帶...
    沈念sama閱讀 35,790評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站谈竿,受9級(jí)特大地震影響团驱,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜空凸,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,442評(píng)論 3 331
  • 文/蒙蒙 一嚎花、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧呀洲,春花似錦紊选、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,996評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至滓窍,卻和暖如春趣些,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背贰您。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,113評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,332評(píng)論 3 373
  • 正文 我出身青樓乘综,卻偏偏與公主長(zhǎng)得像钉赁,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子枪芒,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,044評(píng)論 2 355