我使用Django REST Framework构建Web应用程序。有一个简单的视图,它返回带有db字段的参考信息
resources.py:
RESOURCES = {
'genres': GenreSerializer(Genre.objects.all(), many=True).data,
'authors': AuthorSerializer(Author.objects.all(), many=True).data,
......
}
class ResourceApiView(views.APIView):
def get(self, request):
params = request.query_params
response_dict = {}
if params:
# Return RESOURSES based on query params
for i in params:
q = RESOURCES.get(i)
if q:
response_dict[i] = q
else:
# Return all RESOURSES
response_dict = RESOURCES
return Response(response_dict,
status=status.HTTP_200_OK
)
它工作正常,但是当我将新对象添加到资源查询集时。什么都没发生,它显示旧查询
我在我的模块中尝试打印RESOURSES
,打印一次,其他请求不会触发它
然后我直接在课程RESOURSES
中移动ResourceApiView
,其行为与模块中的RESOURSES
时的行为相同。
class ResourceApiView(views.APIView):
RESOURCES = {
'genres': GenreSerializer(Genre.objects.all(), many=True).data,
'authors': AuthorSerializer(Author.objects.all(), many=True).data,
......
}
def get(self, request):
...
只有在RESOURSES
方法中添加get
时才能正常工作。
class ResourceApiView(views.APIView):
def get(self, request):
RESOURCES = {
'genres': GenreSerializer(Genre.objects.all(), many=True).data,
'authors': AuthorSerializer(Author.objects.all(), many=True).data,
......
}
但为什么会这样呢?为什么我无法为每个方法调用评估类属性的查询?
答案 0 :(得分:2)
这与python比django更相关。让我们说你hava文件lib.py
def say_hello():
print "hello"
GREETINGS = {
"hello": say_hello()
}
现在转到另一个python文件(或shell),然后导入你的lib.py
,你打印"你好"到控制台,因为当你导入文件时它开始解析里面的代码,所以它创建了GREETINGS变量(在你的情况下为RESOURCES)并调用say_hello()方法,为你执行查询。然而,python足够聪明,如果你再次导入文件,他会记得你之前刚刚导入它,因此它不会再次加载模块,因为它已经保存了模块参考。
您的查询在首次加载视图时执行一次,重新导入视图不会使参考更改
将RESOURCES作为类属性放置相同。导入类时执行代码(同样可以通过在lib.py
示例上创建类来测试它)
希望这可以澄清:)但是文档可能会更好地解释https://docs.python.org/2/tutorial/modules.html
注意:强>
我认为序列化程序上的.data
实际上是在执行查询。如果没有它,您的查询和序列化程序将仅作为参考存储,因为ORM是惰性的。更改资源以提高端点的性能,因为如果您请求一个单一资源(例如作者),它仍在执行所有查询(' authors',' genres&#39 ;等等)