diff --git a/wagtail/blocks/stream_block.py b/wagtail/blocks/stream_block.py index 433610c8f9..212803d60c 100644 --- a/wagtail/blocks/stream_block.py +++ b/wagtail/blocks/stream_block.py @@ -653,7 +653,7 @@ class StreamValue(MutableSequence): raw_values = OrderedDict( (i, raw_item["value"]) for i, raw_item in enumerate(self._raw_data) - if raw_item["type"] == type_name and self._bound_blocks[i] is None + if self._bound_blocks[i] is None and raw_item["type"] == type_name ) # pass the raw block values to bulk_to_python as a list converted_values = child_block.bulk_to_python(raw_values.values()) diff --git a/wagtail/tests/test_streamfield.py b/wagtail/tests/test_streamfield.py index 2872fe05c0..a284cca1ea 100644 --- a/wagtail/tests/test_streamfield.py +++ b/wagtail/tests/test_streamfield.py @@ -237,6 +237,24 @@ class TestStreamValueAccess(TestCase): self.assertEqual(fetched_body[1].block_type, "text") self.assertEqual(fetched_body[1].value, "bar") + def test_can_append_on_queried_instance(self): + # The test is analog to test_can_append(), but instead of working with the + # in-memory version from JSONStreamModel.objects.create(), we query a fresh + # instance from the db. + # It tests adding data to child blocks that + # have not yet been lazy loaded. This would previously crash. + self.json_body = JSONStreamModel.objects.get(pk=self.json_body.pk) + self.json_body.body.append(("text", "bar")) + self.json_body.save() + + fetched_body = JSONStreamModel.objects.get(id=self.json_body.id).body + self.assertIsInstance(fetched_body, StreamValue) + self.assertEqual(len(fetched_body), 2) + self.assertEqual(fetched_body[0].block_type, "text") + self.assertEqual(fetched_body[0].value, "foo") + self.assertEqual(fetched_body[1].block_type, "text") + self.assertEqual(fetched_body[1].value, "bar") + class TestStreamFieldRenderingBase(TestCase): model = JSONStreamModel