java - 圖片驗(yàn)證碼實(shí)現(xiàn)原理
問(wèn)題描述
**測(cè)試網(wǎng)站:http://con.monyun.cn:9960/acc...
在這個(gè)頁(yè)面中有一個(gè)驗(yàn)證碼。這個(gè)驗(yàn)證碼的url是
<img src='http://www.aoyou183.cn/aut_checkCode.hts?=0.8963835985936632' class='icd'>
如何實(shí)現(xiàn)點(diǎn)擊驗(yàn)證碼的時(shí)候更改顯示圖片??
說(shuō)明:(1) 當(dāng)你點(diǎn)擊驗(yàn)證碼圖片的時(shí)候 ,img標(biāo)簽的src屬性的 后面部分的數(shù)字會(huì)更改,一旦數(shù)字更改會(huì)就會(huì)引起瀏覽器訪問(wèn)新的url獲取數(shù)據(jù)
(2)新的url中查詢字符串只有value沒(méi)有name,那么是不是說(shuō)就服務(wù)器端就無(wú)法獲取到這個(gè)數(shù)字值?0.8963835985936632
服務(wù)器端有辦法獲取這個(gè)數(shù)字值嗎??
(3)假若 沒(méi)有辦法獲取到數(shù)字值。 服務(wù)器端處理請(qǐng)求,返回二進(jìn)制圖像數(shù)據(jù)。這個(gè)時(shí)候會(huì)為圖片生成一個(gè)token嗎? 如果有生成那么如何傳遞給客戶端?
(4)用戶提交驗(yàn)證碼。服務(wù)器端處理,那么如何驗(yàn)證用戶提交的驗(yàn)證碼是否正確?服務(wù)器端根據(jù)什么能夠從redis中獲取到正確的驗(yàn)證碼?
各位說(shuō)說(shuō)給回復(fù)就頂!**
問(wèn)題解答
回答1:謝邀, 一般來(lái)說(shuō), 驗(yàn)證碼的工作步驟是這樣的:
實(shí)際上是服務(wù)器生成了一個(gè)4位字符串, 用這4位字符串生成圖片寫(xiě)到response中, 返回給瀏覽器, 并把這個(gè)4位字符串存在了當(dāng)前session中.
瀏覽器提交后, 用提交的字符串和session中的字符串進(jìn)行對(duì)比, 完成驗(yàn)證碼的校驗(yàn).
如果不用session比如可以設(shè)置到cookie中如下(key=test, value=test):
1.后面數(shù)字更改是避免瀏覽器緩存問(wèn)題、2.不用使用任何參數(shù),服務(wù)端會(huì)自動(dòng)去按照時(shí)間銼什么的生成一個(gè)驗(yàn)證碼(想看服務(wù)端是否能獲取)
3.驗(yàn)證碼原理就是生成一串隨機(jī)數(shù)先存入session,最后生成images傳給客戶端給你識(shí)別,用戶提交驗(yàn)證碼答案,服務(wù)端對(duì)你得答案和session當(dāng)中的隨機(jī)數(shù)進(jìn)行對(duì)比,一樣就說(shuō)明驗(yàn)證成功
4.如3
5.redis配合使用一般都會(huì)用到token或者session之內(nèi)的,這樣可以標(biāo)識(shí)這個(gè)驗(yàn)證碼到底是哪一個(gè)用戶的,比如如下key
>keys *>uid_100_login_verify偽代碼
獲取驗(yàn)證碼
User u=User();u.tmp_id=100;//唯一標(biāo)識(shí),傳給客戶端表單Random rand=new Random(種子);int v=rand.rand();//一般會(huì)生成其他得英文字母配合生成復(fù)雜的redisCli.add('uid_100_login_verify',random)//key,valueres.return(new Verify());
驗(yàn)證
User u=User();u.tmp_id=$POST[’tmp_id’];//獲取客戶端string value=redisCli.get('uid_100_login_verify');//key return valueif($POST[’verify_code’]===value){ return '驗(yàn)證成功';}回答3:
第一個(gè):驗(yàn)證碼的大致流程就是和你描述的一樣的。
第二個(gè):生成驗(yàn)證碼是不用往后臺(tái)傳值的,你給的例子,后面的那串?dāng)?shù)字的改變其實(shí)是為了實(shí)現(xiàn)重新請(qǐng)求 URL 而已,一般是圖片鏈接指向生成驗(yàn)證碼的鏈接,點(diǎn)擊后使用 js 來(lái)給連接進(jìn)行改變,就是后面加一串隨機(jī)數(shù),這樣瀏覽器檢測(cè)到 src 后面的連接改變了(那串隨機(jī)字符串就是這個(gè)作用),然后就會(huì)重新請(qǐng)求后臺(tái),獲取重新生成的驗(yàn)證碼圖片。
第三個(gè):后臺(tái)返回二進(jìn)制圖片后,不需要生成 token ,但是需要把生成驗(yàn)證碼的那串?dāng)?shù)字存到 session 里。要保存在服務(wù)器端,才安全,不需要返回到客戶端。
第四個(gè):用戶輸入提交的驗(yàn)證碼后,就把用戶提交的驗(yàn)證碼數(shù)字,和服務(wù)端 session 里的數(shù)字進(jìn)行對(duì)比。 如果一樣的話,就驗(yàn)證通過(guò)。
至于最后把驗(yàn)證碼放到redis里,你可以去搜索一下,如何把 session 存到 redis 里,相關(guān)的資料。
回答4:后臺(tái)代碼大體上是
public void genAuthImage(){
//生成token uuid //寫(xiě)入cookieresponse.addCookie();--->實(shí)際上是設(shè)置set-cookie頭信息
//生成圖片使用response寫(xiě)出end}前端:
前端:
chrome 檢查
控制臺(tái)
不確定的結(jié)論: response返回響應(yīng)類型為image/jpg的時(shí)候 無(wú)法設(shè)置cookie。原因各位有看到的朋友可以解釋下嗎
相關(guān)文章:
1. javascript - 微信網(wǎng)頁(yè)開(kāi)發(fā)從菜單進(jìn)入頁(yè)面后,按返回鍵沒(méi)有關(guān)閉瀏覽器而是刷新當(dāng)前頁(yè)面,求解決?2. mysql replace 死鎖3. android - 安卓做前端,PHP做后臺(tái)服務(wù)器 有什么需要注意的?4. mysql - ubuntu開(kāi)啟3306端口失敗,有什么辦法可以解決?5. 求救一下,用新版的phpstudy,數(shù)據(jù)庫(kù)過(guò)段時(shí)間會(huì)消失是什么情況?6. extra沒(méi)有加載出來(lái)7. python3.x - Python not 運(yùn)算符的問(wèn)題8. python - 數(shù)據(jù)與循環(huán)次數(shù)對(duì)應(yīng)不上9. mysql - C#連接數(shù)據(jù)庫(kù)時(shí)一直這一句出問(wèn)題int i = cmd.ExecuteNonQuery();10. python小白,關(guān)于函數(shù)問(wèn)題
