如何从wagtail块模板中的struct_block.StructValue获取数据库id?

时间:2018-03-20 17:20:12

标签: django python-3.x wagtail wagtail-streamfield wagtail-snippet

为wagtail StreamField块构建自定义模板我发现自己处于需要以某种方式将当前块的ID传递给其他视图的情况。

例如,当在特定块中单击URL时,着陆页view必须确切地知道URL被单击的块中的哪个块。然后view可以提取与特定块相关联但不一定在视觉上呈现给用户的其他信息。

我目前的策略是使用snippets,因此我可以传递snippet的ID,而view可能会获得相关但事先隐藏的数据。

这不是很糟糕,但是人们必须在两个地方编辑内容,我必须看看他们悲伤的面孔。

似乎块模板上下文中的value变量是wagtail.core.blocks.struct_block.StructValue的一个实例,这使我可以访问块的所有字段,但它似乎没有透露它在DB中的足迹。

另外value有一个有趣的属性:value.block,它似乎是用于构建块的实际模型的一个实例,但我又找不到任何东西像idpk这样有用,可以识别数据库中的那个实例。

有办法吗?

2 个答案:

答案 0 :(得分:1)

您在StreamField的数据库表示中看到的块ID是由封闭的StreamBlock实现的详细信息,以便我们可以跟踪每个块在从流中添加/移动/删除时的历史记录。流中的项目不知道自己的ID - 这是因为它们可能是任何可能的数据类型(例如,CharBlock生成字符串值,并且您无法将ID附加到字符串)。因此,块模板也无法访问ID。

要访问ID,您需要使用每次迭代StreamField值时返回的BoundBlock(或更准确地说,StreamChild)对象(或通过索引访问它,例如模板代码中的page.body[0]page.body.0);这个对象是块值的包装器,它知道块的类型和ID。 (此处文档中BoundBlock的更多背景信息:http://docs.wagtail.io/en/v2.0/topics/streamfield.html#boundblocks-and-values

{% for block in page.body %}
    {% include_block block with id=block.id %}
{% endfor %}

此处blockStreamChild的一个实例,其值为',' block_type'并且' id'属性。通常情况下,{% include_block %}标记只会将value变量传递给块模板,但此处我们将id作为附加变量传递,该变量现在可在该块中使用模板。

StreamField块不是真实的'数据库对象,以便根据您需要使用以下代码扫描StreamField的ID再次检索值:

value = None
for block in page.body:
    if block.id == requested_id:
        value = block.value
        break

答案 1 :(得分:0)

在显示您的代码块的HTML文件中,尝试添加

{% with block.id|stringformat:"s" as block_id %}
 {{ block_id }}
{% endwith %}