Django 如何验证 POST 参数
Django how to validate POST Parameters
我通过 POST 请求将一些参数传递给 django。我如何验证参数是否为整数、字符串以及内部是否没有代码注入等不安全的东西?
有我可以使用的 django 函数吗?
例如:
if request.method == 'POST':
print request.POST.get('user_comment')
如何检查 POST 参数是否包含对我的系统没有危险的字符串?像
request.POST.get('user_comment').is_valid()
谢谢。
最简单的方法是创建一个表单:
from django import forms
class SingleForm(forms.Form):
user_comment = forms.CharField(max_length=100)
然后
comment = SingleForm(request.POST or None)
if comment.is_valid():
# here everything is cleaned and safe
或者您想不使用表格?
要检查 POST
数据是否安全、类型是否正确等,您可以使用 django 中的表单。例如,如果您需要 3 个必需参数,一个字符串和 2 个整数,您可以创建表单:
from django import forms
class MyValidationForm(forms.Form):
first = forms.CharField()
second = forms.IntegerField()
third = forms.IntegerField()
并在视图中使用它:
if request.method == 'POST':
form = MyValidationForm(request.POST, request.FILES)
if not form.is_valid():
# print some error here
else:
# do whatever you like
对于不包含危险内容的字符串进行过滤,没有通用的解决方案。数据库、XSS 等有不同的威胁,因此无法全部过滤。
关于代码注入,您可以使用bleach来净化用户输入:
>>> import bleach
>>> bleach.clean('an <script>evil()</script> example')
u'an <script>evil()</script> example'
您可以在官方 Django 文档中找到有关安全性的更多信息:
如果您使用的是 Django REST Framework,那么您可以在视图中执行以下操作。
from rest_framework import status
from rest_framework.views import APIView
class MyView(APIView):
def post(self , request):
serializer = MySerializer(data = request.data)
if serializer.is_valid():
serializer.save()
return Response({"status" : "Success"} , status = status.HTTP_201_CREATED)
如果您不使用 DRF,请查看 serializers.py to see how is_valid()
is implemented. Basically, it calls run_validators()
function of django.db.models.fields。希望这对您有所帮助!
您可以考虑在字段前使用 cleaned_ 对其进行验证。
例如,如果你想检查用户名,并且你有一个为它定义的模型,
class MyModel(models.Model):
username = model.CharField(max_length = 255)
然后同样你有一个类似下面的表格
class MyForm(forms.ModelForm):
class Meta:
model = MyModel
fields = ['username']
def clean_username(self):
username = self.cleaned_data.get('username')
""" this will give you the actual username from the field
Now you may get that validated
"""
if username == "blah blah":
return forms.ValidationError("This isnt any name!")
else:
return username
这是根据 django 文档说的:
"Field 子类上的 clean() 方法负责 运行 to_python()、validate() 和 run_validators() 的正确顺序并传播它们错误。如果在任何时候,任何方法引发 ValidationError,验证将停止并引发该错误。此方法 returns 干净的数据,然后将其插入到表单的 cleaned_data 字典中.
在表单子类上调用了 clean_() 方法——其中替换为表单字段属性的名称。此方法执行特定于该特定属性的任何清理,与其所属的字段类型无关。此方法不传递任何参数。您将需要查找 self.cleaned_data 中字段的值,并记住此时它将是一个 Python 对象,而不是表单中提交的原始字符串(它将在 cleaned_data因为通用字段的clean()方法,上面已经清理过一次数据了)。"
我通过 POST 请求将一些参数传递给 django。我如何验证参数是否为整数、字符串以及内部是否没有代码注入等不安全的东西? 有我可以使用的 django 函数吗?
例如:
if request.method == 'POST':
print request.POST.get('user_comment')
如何检查 POST 参数是否包含对我的系统没有危险的字符串?像
request.POST.get('user_comment').is_valid()
谢谢。
最简单的方法是创建一个表单:
from django import forms
class SingleForm(forms.Form):
user_comment = forms.CharField(max_length=100)
然后
comment = SingleForm(request.POST or None)
if comment.is_valid():
# here everything is cleaned and safe
或者您想不使用表格?
要检查 POST
数据是否安全、类型是否正确等,您可以使用 django 中的表单。例如,如果您需要 3 个必需参数,一个字符串和 2 个整数,您可以创建表单:
from django import forms
class MyValidationForm(forms.Form):
first = forms.CharField()
second = forms.IntegerField()
third = forms.IntegerField()
并在视图中使用它:
if request.method == 'POST':
form = MyValidationForm(request.POST, request.FILES)
if not form.is_valid():
# print some error here
else:
# do whatever you like
对于不包含危险内容的字符串进行过滤,没有通用的解决方案。数据库、XSS 等有不同的威胁,因此无法全部过滤。
关于代码注入,您可以使用bleach来净化用户输入:
>>> import bleach
>>> bleach.clean('an <script>evil()</script> example')
u'an <script>evil()</script> example'
您可以在官方 Django 文档中找到有关安全性的更多信息:
如果您使用的是 Django REST Framework,那么您可以在视图中执行以下操作。
from rest_framework import status
from rest_framework.views import APIView
class MyView(APIView):
def post(self , request):
serializer = MySerializer(data = request.data)
if serializer.is_valid():
serializer.save()
return Response({"status" : "Success"} , status = status.HTTP_201_CREATED)
如果您不使用 DRF,请查看 serializers.py to see how is_valid()
is implemented. Basically, it calls run_validators()
function of django.db.models.fields。希望这对您有所帮助!
您可以考虑在字段前使用 cleaned_ 对其进行验证。 例如,如果你想检查用户名,并且你有一个为它定义的模型,
class MyModel(models.Model):
username = model.CharField(max_length = 255)
然后同样你有一个类似下面的表格
class MyForm(forms.ModelForm):
class Meta:
model = MyModel
fields = ['username']
def clean_username(self):
username = self.cleaned_data.get('username')
""" this will give you the actual username from the field
Now you may get that validated
"""
if username == "blah blah":
return forms.ValidationError("This isnt any name!")
else:
return username
这是根据 django 文档说的:
"Field 子类上的 clean() 方法负责 运行 to_python()、validate() 和 run_validators() 的正确顺序并传播它们错误。如果在任何时候,任何方法引发 ValidationError,验证将停止并引发该错误。此方法 returns 干净的数据,然后将其插入到表单的 cleaned_data 字典中.
在表单子类上调用了 clean_() 方法——其中替换为表单字段属性的名称。此方法执行特定于该特定属性的任何清理,与其所属的字段类型无关。此方法不传递任何参数。您将需要查找 self.cleaned_data 中字段的值,并记住此时它将是一个 Python 对象,而不是表单中提交的原始字符串(它将在 cleaned_data因为通用字段的clean()方法,上面已经清理过一次数据了)。"