在这种情况下,最好的方法是在数据库或应用程序服务器上实现低负载:
比方说,我想构建一个Web应用程序,为每个用户提供一个概述页面。概述页面以汇总形式为每个用户显示用户的数据。例如,如果它是一个图书馆应用程序,它将显示用户总共访问了图书馆多少次,他总共阅读了多少本书,总共延迟交付了多少本书,在建筑物中花费了多少分钟。每次用户访问概述页面时,都应显示最新值。当用户与网站互动时,数字会发生变化。
我可以做的是为每个概述页面刷新在数据库中进行多次计数。但这会很昂贵。
views.py
def overview(request, userID):
booksCount = Book.objects.count()
booksReadCount = Book.objects.filter(UserID=userID, Status='read').count()
# ... many more, same way
libraryVisitedCount = LibraryVisits.objects.filter(UserID=userID).count()
# many counts like these on different tables for the user
data = {
"booksCount" : booksCount,
"booksReadCount" : booksReadCount,
# ... many more
"libraryVisitedCount" : libraryVisitedCount
}
render(..., context=data)
我以为我可以将JSON对象以及将在概述页面上显示的数据存储在数据库表中,并且每次站点上发生影响对象计数的事件时,我都会更新JSON。
或者我可以使用父视图,但是要刷新它,我每次都必须重新计算所有用户的所有数据,对吗?
还有其他想法吗?我正在使用django webframework和postgres数据库。
TL; DR:我想知道是否有比每次在数据库中多次计数更好的接收计数的方法?
谢谢。
答案 0 :(得分:0)
可以说,在 .top2 {
display: block;
/* example width - can use '%' as well */
width: 300px;
}
.wrapper2 {
position: relative;
padding-bottom: 56.25%;
height: 0;
}
video {
position: absolute;
top: 0;
left: 0;
width:100%;
height: 100%;
}
,Book
等模型中,有related_name的用户模型的ForeignKey是这样的:
LibraryVisit
然后您可以像这样使用annotation和conditional expression:
class Book(models.Model):
UserID = models.ForeignKey(User, related_name='books', on_delete=DO_NOTHING)
class LibraryVisit(models.Model):
UserID = models.ForeignKey(User, related_name='library_visit', on_delete=DO_NOTHING)
并在模板中渲染计数,如下所示:
from django.db.models import Case, IntegerField, Sum, When
def overview(request, userID):
users = User.objects.filter(pk=userId)
users = users.annotate(
booksReadCount=Sum(
Case(
When(book__Status='read', then=1),
output_field=IntegerField()
)
)
).annotate(library_visited_count=Count('library_visit'))
# FYI: please use snake_case when defining object attribute(like model fields) as per PEP-8 style guide
data = {
"user_object" : users.first(), # taking first item of the User queryset. Also DB is hit once in this step
"booksCount" : Book.objects.count()
}
# access counts in view like this:
# user.book_read_count
# user.library_visited_count
return render(..., context=data)
# bold marked words are related_name