Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix collection item trait tracing #55

Merged
merged 4 commits into from
Feb 24, 2014
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
87 changes: 83 additions & 4 deletions traits_enaml/tests/test_trait_operators.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
#----------------------------------------------------------------------------
import unittest

from traits.api import Event, HasTraits, Str
from traits.api import Event, HasTraits, Str, List, Dict, Set
from traits_enaml.testing.enaml_test_assistant import EnamlTestAssistant


Expand All @@ -23,6 +23,9 @@ class TraitModel(HasTraits):
value_update = Str()
value_simple = Str('simple_text')
value_notify = Event()
list_values = List(Str)
dict_values = Dict(Str, Str)
set_values = Set(Str)


class TraitOperatorsTestCase(EnamlTestAssistant, unittest.TestCase):
Expand Down Expand Up @@ -52,6 +55,15 @@ def setUp(self):
name = 'test_op_notify'
text ::
model.value_notify = True
Field:
name = 'test_list_subscribe'
text << str(model.list_values)
Field:
name = 'test_dict_subscribe'
text << str(model.dict_values)
Field:
name = 'test_set_subscribe'
text << str(model.set_values)
"""
self.model = TraitModel()
view, toolkit_view = self.parse_and_create(
Expand All @@ -74,7 +86,7 @@ def test_op_delegate(self):

self.assertEquals(self.model.value_delegate, 'new_value')

with self.assertAtomChanges(enaml_widget, 'text'):
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.value_delegate = 'updated_trait'

self.assertEquals(enaml_widget.text, 'updated_trait')
Expand All @@ -86,7 +98,7 @@ def test_op_subscribe(self):
with self.assertTraitDoesNotChange(self.model, 'value_subscribe'):
enaml_widget.text = 'new_value'

with self.assertAtomChanges(enaml_widget, 'text'):
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.value_subscribe = 'updated_trait'

self.assertEquals(enaml_widget.text, 'updated_trait')
Expand Down Expand Up @@ -127,5 +139,72 @@ def test_op_notify(self):
with self.assertTraitDoesNotChange(self.model, 'value_notify'):
enaml_widget.text = 'changing text'

with self.assertTraitChanges(self.model, 'value_notify'):
with self.assertTraitChanges(self.model, 'value_notify', count=1):
enaml_widget.text = 'new text'

def test_list_subscribe(self):

enaml_widget = self.view.find('test_list_subscribe')

with self.assertTraitDoesNotChange(self.model, 'list_values'):
enaml_widget.text = 'new_value'

# check on replace
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.list_values = ['1']
self.assertEquals(enaml_widget.text, "['1']")

# check on append
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.list_values.append('2')
self.assertEquals(enaml_widget.text, "['1', '2']")

# check on remove
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.list_values.remove('1')
self.assertEquals(enaml_widget.text, "['2']")

def test_dict_subscribe(self):

enaml_widget = self.view.find('test_dict_subscribe')

with self.assertTraitDoesNotChange(self.model, 'list_values'):
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copypasta

enaml_widget.text = 'new_value'

# check on replace
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.dict_values = {'one': '1'}
self.assertEquals(enaml_widget.text, "{'one': '1'}")

# check on append
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.dict_values['two'] = '2'
self.assertEquals(
enaml_widget.text, str({'one': '1', 'two': '2'}))

# check on remove
with self.assertAtomChanges(enaml_widget, 'text', count=1):
del self.model.dict_values['one']
self.assertEquals(enaml_widget.text, "{'two': '2'}")

def test_set_subscribe(self):

enaml_widget = self.view.find('test_set_subscribe')

with self.assertTraitDoesNotChange(self.model, 'list_values'):
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copypasta

enaml_widget.text = 'new_value'

# check on replace
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.set_values = {'1'}
self.assertEquals(enaml_widget.text, "TraitSetObject(['1'])")

# check on append
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.set_values.add('2')
self.assertEquals(enaml_widget.text, "TraitSetObject(['1', '2'])")

# check on remove
with self.assertAtomChanges(enaml_widget, 'text', count=1):
self.model.set_values.remove('1')
self.assertEquals(enaml_widget.text, "TraitSetObject(['2'])")
3 changes: 3 additions & 0 deletions traits_enaml/traits_tracer.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,9 @@ def _trace_trait(self, obj, name):
trait = obj.trait(name)
if trait is not None and trait.trait_type is not Disallow:
self.traced_traits.add((obj, name))
# Check for collections.
if trait.handler.has_items:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If a trait is defined as a Property with no other type:

some_trait = Property(depends_on=['another_trait'])

then line 65 will raise an AttributeError since trait.handler will be None.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have added a new issue #57 for the introduced bug. Thanks for looking into the issue.

self.traced_traits.add((obj, '{}_items'.format(name)))

#--------------------------------------------------------------------------
# AbstractScopeListener Interface
Expand Down