2012-11-29 51 views
3

我的頁面中有一個textarea,它是一個HTML輸入字段。其目的是允許用戶註冊一個確認的HTML,在發生特定操作後將在用戶的瀏覽器中顯示。您可以將它想象成paypal確認後付款的東西,並將您重定向到一個網站,上面寫着「感謝您的購買」。這已經實現了,但現在我正在考慮用戶的安全性(XSS/SQL注入)。將html保存到數據庫的安全方法

我想知道的是如何在我的控制器後動作中安全地過濾掉某些html標記,所以如果我檢測到HTML內部存在惡意HTML,我將在保存之前停止執行。現在我在做這樣的:

[CustomHandleError] 
[HttpPost] 
[ValidateAntiForgeryToken] 
[AccessDeniedAuthorize(Roles = "Admin,CreateMerchant")] 
public ActionResult Create(MerchantDTO merchantModel) 
{ 
    if (ModelState.IsValid) 
    { 
     if (!IsSafeConfirmationHtml(merchantModel.ConfirmationHtml)) 
     { 
     ModelState.AddModelError("ConfirmationHtml", "Unallowed HTML tags inputted"); 
     return View("Create", merchantModel); 
     } 
     . 
     . 
     . 
    } 
} 

和我IsSafeConfirmationHTML被定義爲

private bool IsSafeConfirmationHtml(string html) 
{ 
    if (html.ToLower().Contains("<script") || html.ToLower().Contains("<embed") || html.ToLower().Contains("<object")) 
    { 
     return false; 
    } 
    return true; 
} 

是否有一個更聰明,更清潔的方式做到這一點?我的意思是,我不希望得到阻止「對象」,「腳本」等字樣的誤報,但是我也不想被編碼將「<」翻譯爲「%3C」等的編碼愚弄。 ..

Ontopic:標籤內的間距是否有效?例如:<script> alert("1"); </script >

回答

1

所以你可以做的一件事是擊敗編碼攻擊,將運行UrlDecodeHtmlDecode(html解碼可能是多餘的,但它取決於你對腳本的處理)。

加速檢查的另一件事是轉向預編譯的正則表達式。

private static Regex disallowedHtml = new Regex(@"script|embed|object", 
    RegexOptions.IgnoreCase); 

private bool IsSafeConfirmationHtml(string html) 
{ 
    Match match = disallowedHtml.Match(html); 
    return !match.success; 
} 

靜態正則表達式的情況下削減了大部分正則表達式的開銷的每一個運行,但第一位的,使得正則表達式匹配速度遠遠超過運行3個獨立的包含。您可以使正則表達式複雜到足以搜索開頭尖括號,html實體和url編碼字符,匹配這些字符和實際標記名稱之間的任何空格等等。多年來,Microsoft regex info已經相當不錯了。

我仍然不會說這會讓您對用戶(上傳者?客戶?正確的字取決於您的商業模式)100%安全地運行XSS或針對您網站訪問者的注入式攻擊。他們可以指向一個圖像或一個css文件,該文件返回爲mime類型的x應用程序或其他類型。而且這些天HTML的變化非常迅速。防止這種情況的最好方式是讓一個人也參與批准過程,但是人類會犯錯誤,電腦可能會被愚弄,而且沒有法律說這兩個事件不可能同時發生。但是你有權利實施一些保護措施。