Python 我可以使用金字塔分别渲染Jinja2模板的不同部分吗?
我有一个页面,在特定页面上加载了很多分析和数据,到目前为止,它的加载还可以,但我想知道我是否可以加快加载速度。我要加速的想法是分别渲染图像的每个部分 例如,在SO上查看您的个人资料页面:它有问题、答案、声誉、标签、帐户、徽章、投票,在我当前的模型中,这些信息将收集在Python 我可以使用金字塔分别渲染Jinja2模板的不同部分吗?,python,pyramid,jinja2,Python,Pyramid,Jinja2,我有一个页面,在特定页面上加载了很多分析和数据,到目前为止,它的加载还可以,但我想知道我是否可以加快加载速度。我要加速的想法是分别渲染图像的每个部分 例如,在SO上查看您的个人资料页面:它有问题、答案、声誉、标签、帐户、徽章、投票,在我当前的模型中,这些信息将收集在view.py中,然后由模板呈现。但是,如果“声誉”或“标签”查询由于XYZ原因而变慢,那么它将降低整个页面的加载速度,即使这对大多数用户来说不是非常重要。我曾考虑使用JavaScript发出请求并在页面上异步呈现json回复来解决这
view.py
中,然后由模板呈现。但是,如果“声誉”或“标签”查询由于XYZ原因而变慢,那么它将降低整个页面的加载速度,即使这对大多数用户来说不是非常重要。我曾考虑使用JavaScript发出请求并在页面上异步呈现json回复来解决这个问题,但我非常喜欢Pyramid和Python,因此如果可能的话,我希望使用我已经知道的工具,而不是学习JavaScript来实现这一点。这种方法的好处是,我可以先加载/显示页面顶部,然后在查询完成时呈现页面的其余部分,或者按查询速度排序呈现
这可能吗?或者你对如何做到这一点有什么建议吗 这当然是可能的,但实现几乎完全与Pyramid或Jinja2无关。Pyramid(或任何其他web框架)的工作方式是,它从客户机(被抽象为请求对象)获取一点文本,并基本上返回另一个文本块作为响应,因此,该操作或多或少是原子性的——在模板引擎完成生成页面全文之前,不会将响应发送回客户端 实际上,有一种方法可以使金字塔逐位向客户机发送数据,这将使浏览器以增量方式呈现页面(就像拨号连接时一样)-直接写入表示响应主体的类似文件的对象:
import time
def some_view(request):
for i in range(1, 31):
request.response.body_file.write(".")
time.sleep(1)
但是这个方法有点有限,因为你只能把数据附加到你已经发送的东西上,没有办法,比如说,“请等待,图表加载”消息并用真实图表替换它,或者甚至加载页面页眉和页脚,然后在中间插入一些东西。此外,这种方法需要手动呈现模板,或者根本不使用模板。我只在一些长时间运行的批处理操作中使用它
正如您在问题中提到的,更好的技术是使用JavaScript从单独的URL加载页面的位。我相信异步加载的块通常被称为“partials”- 您注册了几个单独的视图,这些视图表示您的主页和要插入的位,因此,例如,
将加载页面的主要部分,/questions/123454
将加载带有徽章的块,/questions/123454/badges
将加载相关问题列表/questions/123454/related
- 您可以在页面中定义要插入部分的占位符:
加载…
- 在页面中添加一点javascript来加载部分内容(如果使用:,则会很小):
因此,正如您所见,JavaScript解决方案更干净、更简单、更灵活。我建议您在问题中添加“JavaScript”和“jquery”标记,以吸引更多具有相关知识的人。我没有足够的代表亲自做这件事。@Sergey我知道我能做到。用javascript实现这一点,但我试着测试我的运气,看看我是否可以只用python来做一些事情(如果不需要的话,还可以避免学习新语言)。好的,我将沿着jquery路线走。我还有一个问题,可能有点不相关。金字塔中是否有办法确保只有我的应用程序得到json响应?我还没有准备好向世界开放api,但在我的源代码中,您可以看到我正在查询的金字塔url。@Lostsoul:公开访问HTML和公开访问返回JSON数据的视图之间没有区别。如果你需要限制访问,你需要在你的应用程序中实现身份验证——金字塔在这方面有大量的文档。我的意思是,在万维网中,每个页面都是只读API方法,每个表单都是读写方法——它们只是碰巧使用HTML作为数据格式。JSON API与此没有什么不同。谢谢你,这是一个很好的思考方式。我将更深入地研究安全性,我想我是在试图阻止随机用户在没有任何控制的情况下访问我的站点api(并为访问站点的用户降低服务器速度)。
$(function () {
$("#badges-partial").load("/questions/123454/badges");
$("#related-partial").load("/questions/123454/related");
});