Skip to content

Commit

Permalink
Fix the property lock when the deserializer returns bytes or buffer
Browse files Browse the repository at this point in the history
Also, fix the case when the state is serialized with keys in a different order, by parsing the json we generated with jsondumps.
  • Loading branch information
jasongrout committed Aug 9, 2017
1 parent 349f556 commit db04817
Show file tree
Hide file tree
Showing 2 changed files with 10 additions and 7 deletions.
2 changes: 1 addition & 1 deletion ipywidgets/widgets/tests/test_set_state.py
Original file line number Diff line number Diff line change
Expand Up @@ -122,4 +122,4 @@ def test_set_state_data_truncate():

# Sanity:
assert len(buffers) == 1
assert buffers[0].tobytes() == data[:20].tobytes()
assert buffers[0] == data[:20].tobytes()
15 changes: 9 additions & 6 deletions ipywidgets/widgets/widget.py
Original file line number Diff line number Diff line change
Expand Up @@ -483,7 +483,7 @@ def _compare(self, a, b):
else:
return a == b

def _compare_buffers(self, a, b, key):
def _buffer_list_equal(self, a, b):
"""Compare two lists of buffers for equality.
Used to decide whether two sequences of buffers (memoryviews) differ,
Expand All @@ -501,7 +501,9 @@ def _compare_buffers(self, a, b, key):
# e.g. memoryview(np.frombuffer(ia, dtype='float32')) !=
# memoryview(np.frombuffer(b)), since the format info differs.
# However, since we only transfer bytes, we use `tobytes()`.
if ia.tobytes() != ib.tobytes():
iabytes = ia.tobytes() if isinstance(ia, memoryview) else ia
ibbytes = ib.tobytes() if isinstance(ib, memoryview) else ib
if ia != ib:
return False
return True

Expand Down Expand Up @@ -620,13 +622,14 @@ def _should_send_property(self, key, value):
# idiosyncracies of how python data structures map to json, for example
# tuples get converted to lists.
if key in self._property_lock:
# model_state, buffer_paths, buffers
split_value = _remove_buffers({ key: to_json(value, self)})
split_lock = _remove_buffers({ key: self._property_lock[key]})
# Compare state and buffer_paths
if jsondumps(split_value[:2]) == jsondumps(split_lock[:2]):
# Compare buffers
if self._compare_buffers(split_value[2], split_lock[2], key):
return False
if (jsonloads(jsondumps(split_value[0])) == jsonloads(jsondumps(split_lock[0]))
and split_value[1] == split_lock[1]
and self._buffer_list_equal(split_value[2], split_lock[2])):
return False
if self._holding_sync:
self._states_to_send.add(key)
return False
Expand Down

0 comments on commit db04817

Please sign in to comment.