如何區分HttpRequest來自微信小程序還是瀏覽器?


當后端接收到一個request的時候,如何區分是來自於微信小程序還是瀏覽器的請求?

首先,微信小程序的請求並沒有明確的標記位來驗證請求來源。

一、網上的一些說法:
1、Header中的content-type
微信小程序的content-type默認“application/json”,POST請求一般自己定義為 “application/x-www-form-urlencoded”。如果是PC瀏覽器直接請求URL,content-type確實是null的,很多網友覺得可以使用這個區分。但是一旦我們在瀏覽器中通過Ajax請求,content-type就不是null了,就沒辦法區分是小程序的還是Ajax腳本的。

2、Header中的User-Agent
User-Agent可以區分終端類型。
如果是微信中請求,agent中有 MicroMessenger 字符串,其他則沒有!在一定程度上可以解決來源,但是不能解決根本問題。因為,可以直接復制url,在微信聊天中打開!

3、sessionid
因為微信小程序(包括公眾號)的request請求都是無狀態的,也就是說session是無效的。(我們可以在后台打印一下sessionid,就會發現每次request的sessionid都是不一樣的,所以session是無狀態的。)

所以,有的同學就模擬一個session:后端保存sessionid到內存或緩存,然后每次請求都帶上sessionid,比如用url?JSESSION=sessionid,或者在Header中添加Cookie的形式,以此來判斷和校驗用戶是否登錄或是否來自於小程序。

但是如果我們是Fiddle之類的工具抓取請求,就會獲得請求的參數sessionid,同樣的可以通過Ajax腳本來模擬(sessionid)請求服務器端。所以也是不安全的。

二、我的做法:
首先用User-Agent來做基本篩選!
然后:
1、在登錄的時候,一定要用wx.login獲取code,然后服務器端通過code獲取sessionkey和openid來實現登錄。sessionkey的有時效(timeout)的,類似於session有效時間。

2、獲取sessionid,並將sessionkey、openid和sessionid的關系,存儲到服務器內存或緩存中。這個關系開發者可以自己定義,一般我用map。

3、前端重新封裝wx.request,將sessionid保存到globalData中,globalData有失效時間,這樣sessionid的有效時間和sessionkey就一致了。所以,每次請求要帶上sessionid,后台校驗sessionid 和 sessionkey的關系。

4、只有sessionid並不能解決csrf攻擊(前面有說明)。還需要使用一個csrf-token,就是每次請求都會產生一個csrf-token返回給前端,前端下次請求的時候帶上csrf-token,后端校驗。 這里有一個問題,如果抓到response中的內容,就可以拿response中的csrf-token進行模擬訪問了,所以我們需要對csrf-token處理一下

5、csrf-token處理:可以用加密的方式,只要保證后端同樣的加密或解密能夠將token匹配即可。也可以簡單的通過移位、或者添加字符串等方式。總之這個方式只有開發者知道,前后端怎么處理token來校驗有效性!

6、為了保證絕對的安全,在一些關鍵業務的處理上,最好用wx.login產生code,后端根據code調用微信服務器接口進行校驗后再處理!

三、更好的方式?
這只是我個人的思路,如果你有更好的處理思路,可以留言,一起交流!
謝謝!




免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM