我是Django的新手,我正在尝试构建一个应用程序来在表格和图表中显示我的数据。直到现在我的学习过程非常顺利,但现在我有点卡住了。
我的网页浏览从数据库中检索大量数据并将其放入上下文中。然后模板生成不同的html表。到目前为止一切顺利。
现在我想为模板添加不同的图表。我设法通过定义<img src=".../> tags.
来实现这一点。在我的chartview中生成Matplotlib图表并返回通过:
response=HttpResponse(content_type='image/png')
canvas.print_png(response)
return response
现在我有不同的问题:
<imgm src="chart/dataset1/dataset2/.../dataset20/chart.png />
)是正确的方法。答案 0 :(得分:6)
您无法将数据从页面视图传递到图表视图,因为它们是单独的HTTP请求。您有几个选择:
传递图表网址中的所有数据。这可能听起来很疯狂,但这正是谷歌图表的作用:http://code.google.com/apis/chart/docs/making_charts.html
将数据存储在会话中。页面视图将填充会话中的数据,图表视图将使用它来创建图表。
在memcache中缓存数据库查询。由于页面和图表都将引用相同的查询,因此您可能会访问缓存。这是一个很好的解决方案,因为即使没有首先渲染页面,您的图表仍然可以工作。
再次查询数据库。您的DBMS可能具有良好的缓存,性能可能不是您想象的问题。
对于您的第二个问题,网址中的20个字似乎不是什么大问题。当然,您可能会为所选的数据集找到一些模式,这样您就不需要每次都指定它们,但如果需要,只需制作长URL。
答案 1 :(得分:1)
使用模板标签可能就是我在这里采用的路线。我有类似的情况,我在同一页面上以不同的格式多次呈现日历信息。我处理它的方法是将查询的数据传递到请求上下文,然后简单地使用该查询集作为模板标记的参数。结果是你可以得到这样的模板语法:
查看强>
def my_view(request, *args, **kwargs):
yearly_sales_qs = SaleRecord.objects.filter(param=value)
monthly_sales_qs = SalesRecord.objects.filter(param=foo)
return render_to_response( ..., locals(), ... )
<强>模板强>
{% load data_tags %}
<div class="year">
{% render_data_table for yearly_sales_qs %}
{% render_bar_chart for yearly_sales_qs %}
</div>
<div class="month">
{% render_data_table for monthly_sales_qs %}
{% render_bar_chart for monthly_sales_qs %}
</div>
那么你怎么做那样的东西?首先查看Custom template tags and filters上的Django文档。比Django的其他部分更难开始,但是一旦你得到它,它就很容易了。
TEMPLATE_DIRS
中的settings.py
设置中(如果它尚未存在)因为我们将制作其中的几个,我们可以制作一个我们将继承的基本模板标签,它封装了我们的基本功能......
data_tags.py (存储在templatetags
文件夹中)
class DataForTag(tempalte.Node):
@classmethod
def handle_token(cls, parser, token, template):
tokens = token.contents.split()
if tokens[1] != 'for':
raise template.TemplateSyntaxError("First argument in %r must be 'for'" % tokens[0])
if len(tokens) == 3:
return cls(queryset=parser.compile_filter(tokens[2]), template=template)
else:
raise template.TemplateSyntaxError("%r tag requires 2 arguments" % tokens[0])
def __init__(self, queryset=None, template=None):
self.queryset = queryset
self.template = template
def render(self, context):
return render_to_string(self.template, {'queryset':self.queryset})
然后我们可以制作单独的标签来处理我们需要的任何东西......
@register.tag
def render_bar_chart(parser, token):
return DataForTag.handle_token(parser, token, 'data/charts/barchart.html')
@register.tag
def render_pie_chart(parser, token):
return DataForTag.handle_token(parser, token, 'data/charts/piechart.html')
@register.tag
def render_data_table(parser, token):
return DataForTag.handle_token(parser, token, 'data/table.html')