允许用户创建MySQL过滤器时逃避危险代码

时间:2010-11-16 14:38:00

标签: jquery mysql django json filter

我目前可以显示数据库中所有电影的所有发行年份。用户可以选择一年并查看当年发布的所有电影。或者我可以展示所有类型的电影。用户可以选择一种类型并查看符合该条件的所有电影。我构建了一个表单,用户可以在其中动态选择自己的标准。因此,例如“发布日期”“之后”“2000”将返回过滤后的列表。

我写了一些UNPROTECTED jquery / django代码来将过滤器传递给数据库。通过下拉框和用户输入框的组合(就像你在iTunes中看到的那样),我使用jquery来构建过滤器。

举个例子,假设用户在第一个下拉列表中选择:“Year”。对于第二次下拉:“是”。最后一个是输入框,用户输入“2005”。这个标准放在一个数组中:

dictionary: 
[ 
   {"includes": [["year__iexact", "2005"]], 
    "excludes": []}, 
    "all" 
] 

“includes”/“excludes”将“is”,“is before”等条件与“is not”之类的内容分开 “all”表示过滤器应该“匹配所有”,而不是“匹配任何”

这转换为JSON:

[{"includes":[["year__iexact","2005"]],"excludes":[]},"all"]  

并张贴到django。

然后django中的视图将数据放入过滤器:

incdict[ filter[0].encode('utf-8') ] = filter[1].encode('utf-8') 

这变为:

incdict[ 'year__iexact' ] = 2005 

将其输入查询(按照指示here

query_set = Film.objects.filter(**incdict) 

好的,我希望这很清楚。我现在要问的是如何防止那些试图绕过/利用输入的不道德用户。我需要逃避特殊字符吗?数据验证?保护系统的最佳方法是什么?

3 个答案:

答案 0 :(得分:3)

我会验证输入,你必须做那个服务器端。

也许如果您将条件分为“__”(例如,给予[“年”,“iexact”]),您可以将这些值与白名单进行比较。这样您就可以确保只执行预定义的允许查询。

答案 1 :(得分:3)

即使您允许完全自由格式的数据进入filter()exclude(),也无法从他们那里制作危险的查询;查询的类型由调用的方法确定,而不是传递的数据。

答案 2 :(得分:0)

即使用户无法执行任何明显的恶意查询(删除或获取机密数据),您可能不得不担心有人经常使用复杂查询来访问您的数据库(想想多个连接和一些正则表达式或非索引的其他选择)列)这些可能需要很长时间才能回答。

它还取决于数据库的大小,它一次可以处理多少复杂查询,但这可能会使您的网站变慢。