我知道有兩種方法可以有效地做到這一點,因爲基本上沒有辦法阻止某人僞造任何請求。
第一個是不在查詢參數中使用裸ID。相反,生成一個大的隨機數,並將其鏈接出來。您必須在數據庫中保留一張表格,將您的隨機數字映射到它們所代表的實際ID,並且您最終必須清理表格。這很容易實現,但需要一些存儲空間,並且偶爾會對存儲的數據進行一些管理。
第二種方法是在您建立鏈接時簽署數據。通過向數據附加密碼簽名,並在請求發出時驗證簽名,確保只有您的Web服務可能創建了鏈接。即使請求本身是僞造的 - 也許是書籤,寫下來,複製並粘貼到另一個瀏覽器 - 你知道你的網站已經授權該URL。爲了做到這一點,你需要創建一個消息認證碼(MAC)和你正在簽名的數據(比如說,'id'值,或者可能是你簽名數據的id和時間)和與一個祕密密鑰,你只保留在你的服務器上。
然後,在您的視圖中,您將採用id值(或id和timestamp,如果這就是您正在使用的),然後再次構建MAC並查看它們是否匹配。如果有任何區別,您拒絕該請求被篡改。
查看所有細節的hmac module以及hashlib module的python文檔。
您可以像這樣在python中生成鏈接:
設置。潘岳:
hmac_secret_key = '12345'
views.py:
import time, hmac, hashlib
from django.conf import settings
def some_view(request):
...
id = 5
time = int(time.time())
mac = hmac.new(
settings.hmac_secret_key,
'%d/%d' % (id, time),
hashlib.sha1)
url = 'http://www.example.com/posts/id=%d&ts=%d&mac=%s' % (
id, time, mac.hexdigest())
# Now return a template with that url in it somewhere
進行驗證,另一種觀點認爲,你可以使用這樣的代碼:(警告,警告,不健壯,很多錯誤檢查還是要做)
def posts_view(request):
id = int(request.GET['id'])
ts = int(request.GET['ts'])
mac_from_url = request.GET['mac']
computed_mac = hmac.new(
settings.hmac_secret_key,
'%d/%d' % (id, time),
hashlib.sha1)
if mac_from_url <> computed_mac:
raise SomeSecurityException()
# Now you know that the request is legit.
# You can check the timestamp here, too, if you like.
用戶可以模擬瀏覽器可能提出的任何請求。 –
爲了防止用戶使用不需要的方法提供數據,有一個CSRF,它可以在POST請求中使用,所以它也應該在GET請求中工作(我希望)。但要正確 - 依靠URL中請求的參數並不是一件好事。檢查數據庫項目是否存在不是浪費時間和資源。這可能會在未來某個時候導致嚴重的問題。 – koressak
「......我不喜歡不能控制訪問某些信息的想法」。你怎麼知道哪些信息是「確定的」,哪些不是?正如我看到的最好的方法是添加'私人'布爾字段到您的模型。 – DrTyrsa