1、xss.pyhtml
過濾模塊正則表達式
# 經過beautifulsoup4 模塊能夠避免寫正則表達式來完成過濾上傳文件中的惡意攻擊 from bs4 import BeautifulSoup content = """ <p id='i1' a='123' b='999'>
<script>alert(123)</script>
</p>
<p id='i2'>
<div>
<p>asdfasdf</p>
</div>
<img id='i3' src="/static/imgs\1.jpg" alt="" />
</p>
""" soup = BeautifulSoup(content,'html.parser') # parser爲beautifulsoup4 模塊的內置解析塊,將html解析成對象 tag = soup.find(name='img') # 獲取的是img標籤,name= 標籤名 # print(tag) #<img alt="" id="i3" src="/static/imgs.jpg"/> ,爲字符串?? tag = soup.find(name='p') #獲取的是 p 標籤及 p 標籤內的子內容 # print(tag) #<p a="123" b="999" id="i1"><script>alert(123)</script></p> v = soup.find(name='p',attrs={'id':'i2','name':''}) # 也能夠經過id 和 name 獲取,條件是且的關係 # print(v) #<p id='i2'><div><p>asdfasdf</p></div><img id='i3' src="/static/imgs\1.jpg" alt="" /></p> # 以上find 獲取的都是選中的內容和其內部包含的子內容,且獲取的是字符串類型 #find_all 獲取的是列表類型,列表裏是對象 v = soup.find_all(name='p') # print(v) #遞歸找到全部的標籤,步驟:找第一個父類,父類和子類中符合的取出來,而後再把子類符合的標籤取出來。子類符合的標籤可能被取出來不少次 #[<p a="123" b="999" id="i1"><script>alert(123)</script></p>, <p id="i2"><div><p>asdfasdf</p></div><img alt="" id="i3" src="/static/imgs.jpg"/></p>, <p>asdfasdf</p>] #如下爲過濾部分 vaild_tag = ['p','img','div'] #白名單,設置白名單不設黑名單的緣由是xss攻擊的方式多種多樣,並且不斷更新 tags = soup.find_all() for tag in tags: if tag.name not in vaild_tag: # tag.clear() # tag.clear()只是把tag標籤的內容刪掉,標籤自己不被刪掉 tag.decompose() #刪除的是標籤內的內容和標籤自己 print(soup) #soup是對象,要拿到過濾後的結果,須要decode下 comment_str=soup.decode() #comment_str 這是拿到最終被過濾後的結果 #白名單也能夠設置爲字典格式,標籤部分屬性設置爲白名單 vaild_tag = {'p':['class','id'],'img':['src'],'div':['class']} for tag in tags: if tag.name not in vaild_tag: tag.decompose() if tag.attrs: for k in list(tag.attrs.keys()): if k not in vaild_tag[tag.name]: del tag.attrs[k] comment_str=soup.decode() #將soup對象轉換成字符串,encode()將soup對象轉換成字節 return comment_str
2、form驗證django
引用過濾模塊安全
from django.forms import Form,widgets,fields class ArticleForm(Form): title = fields.CharField(max_length=64) content = fields.CharField( widget=widgets.Textarea(attrs={'id':'i1'})) #此處爲xss驗證
def clean_content(self): old = self.cleaned_data['content'] from utils.xss import xss return xss(old)
3、視圖函數app
CONTENT='' def create_article(request,site): from app01.form import ArticleForm if request.method == 'GET': obj = ArticleForm() return render(request,'creat_article.html',{'site':site}) else: obj = ArticleForm(request.POST) if obj.is_valid(): content = obj.cleaned_data['content'] global CONTENT #這裏記得要設置全局變量,方便see函數使用該變量 CONTENT = content return HttpResponse('上傳成功') # 查看文章內容,只是簡單的 def see(request): return render(request,'see.html',{'CONTENT':CONTENT})
4、文章顯示頁面xss
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>$Title$</title> </head> <body> {{ CONTENT|safe }} <!--拿到HTML字符串,標記爲安全--> </body> </html>