Skip to content
This repository has been archived by the owner on Jan 6, 2022. It is now read-only.

Commit

Permalink
Fixes how errors are passed to list & struct children.
Browse files Browse the repository at this point in the history
  • Loading branch information
BertrandBordage committed Oct 8, 2019
1 parent 8388775 commit eb9ba40
Show file tree
Hide file tree
Showing 5 changed files with 26 additions and 11 deletions.
13 changes: 13 additions & 0 deletions wagtail_react_streamfield/blocks/block.py
Expand Up @@ -16,6 +16,19 @@ def get_default(self):
default = default()
return default

def get_children_errors(self, errors):
if errors:
if len(errors) > 1:
# We rely on Block.get_children_errors throwing
# a single ValidationError with a specially crafted 'params'
# attribute that we can pull apart and distribute
# to the child blocks.
raise TypeError(
'Block.get_children_errors unexpectedly '
'received multiple errors.'
)
return errors.as_data()[0].params

def prepare_value(self, value, errors=None):
"""
Returns the value as it will be displayed in react-streamfield.
Expand Down
5 changes: 2 additions & 3 deletions wagtail_react_streamfield/blocks/list_block.py
Expand Up @@ -54,8 +54,7 @@ def value_from_datadict(self, data, files, prefix):
for child_block_data in data['value']]

def prepare_value(self, value, errors=None):
children_errors = (None if errors is None
else errors.as_data()[0].params)
children_errors = self.get_children_errors(errors)
if children_errors is None:
children_errors = [None] * len(value)
prepared_value = []
Expand All @@ -67,7 +66,7 @@ def prepare_value(self, value, errors=None):
'type': self.child_block.name,
'hasError': bool(child_errors),
'value': self.child_block.prepare_value(child_value,
errors=errors),
errors=child_errors),
})
if html is not None:
child_value['html'] = html
Expand Down
5 changes: 3 additions & 2 deletions wagtail_react_streamfield/blocks/stream_block.py
Expand Up @@ -53,8 +53,9 @@ def value_from_datadict(self, data, files, prefix):
def prepare_value(self, value, errors=None):
if value is None:
return []
children_errors = ({} if errors is None
else errors.as_data()[0].params)
children_errors = self.get_children_errors(errors)
if children_errors is None:
children_errors = {}
prepared_value = []
for i, stream_child in enumerate(value):
child_errors = children_errors.get(i)
Expand Down
8 changes: 5 additions & 3 deletions wagtail_react_streamfield/blocks/struct_block.py
Expand Up @@ -58,8 +58,9 @@ def value_from_datadict(self, data, files, prefix):
])

def prepare_value(self, value, errors=None):
children_errors = ({} if errors is None
else errors.as_data()[0].params)
children_errors = self.get_children_errors(errors)
if children_errors is None:
children_errors = {}
prepared_value = []
for k, child_block in self.child_blocks.items():
child_errors = (None if children_errors is None
Expand All @@ -71,7 +72,8 @@ def prepare_value(self, value, errors=None):
'id': str(uuid4()),
'type': k,
'hasError': bool(child_errors),
'value': child_block.prepare_value(child_value, errors=errors),
'value': child_block.prepare_value(child_value,
errors=child_errors),
})
if html is not None:
child_value['html'] = html
Expand Down
6 changes: 3 additions & 3 deletions wagtail_react_streamfield/monkey_patch.py
Expand Up @@ -63,9 +63,9 @@ def patch():
_patch_streamfield_panel()
_patch_block_widget()
_patch_with(Block, NewBlock,
'FIELD_NAME_TEMPLATE', 'get_default', 'prepare_value',
'get_instance_html', 'definition', 'html_declarations',
'all_html_declarations')
'FIELD_NAME_TEMPLATE', 'get_default', 'get_children_errors',
'prepare_value', 'get_instance_html', 'definition',
'html_declarations', 'all_html_declarations')
Block._meta_class.closed = False
_patch_with(BaseStreamBlock, NewBaseStreamBlock,
'definition', 'sorted_child_blocks', 'render_list_member',
Expand Down

0 comments on commit eb9ba40

Please sign in to comment.