Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
path: root/tests/coretests.py
diff options
context:
space:
mode:
authorVincent Vinet <vince.vinet@gmail.com>2009-12-06 19:43:16 (GMT)
committer Vincent Vinet <vince.vinet@gmail.com>2009-12-06 20:41:39 (GMT)
commit2bda2c8c50797a6214126edc5afdc3fc5d8e9969 (patch)
tree4697873cfa4de532ee691a17a29e781fe5c5782d /tests/coretests.py
parentfb422aef7ee6832c85c8fa8a703e491838e74d62 (diff)
improve coverage report and cleanup old stuff
Diffstat (limited to 'tests/coretests.py')
-rw-r--r--tests/coretests.py629
1 files changed, 0 insertions, 629 deletions
diff --git a/tests/coretests.py b/tests/coretests.py
deleted file mode 100644
index 1cc5431..0000000
--- a/tests/coretests.py
+++ /dev/null
@@ -1,629 +0,0 @@
-# Copyright (C) 2009, Tutorius.org
-# Copyright (C) 2009, Michael Janelle-Montcalm <michael.jmontcalm@gmail.com>
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; either version 2 of the License, or
-# (at your option) any later version.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program; if not, write to the Free Software
-# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
-"""
-Core Tests
-
-This module contains all the tests that pertain to the usage of the Tutorius
-Core. This means that the Event Filters, the Finite State Machine and all the
-related elements and interfaces are tested here.
-
-Usage of actions and event filters is tested, but not the concrete actions
-and event filters. Those are in their separate test module
-
-"""
-
-import unittest
-
-from copy import deepcopy
-import logging
-from sugar.tutorius.actions import *
-from sugar.tutorius.addon import *
-from sugar.tutorius.core import *
-from sugar.tutorius.filters import *
-
-from actiontests import CountAction, FakeEventFilter
-
-# Helper classes to help testing
-class SimpleTutorial(Tutorial):
- """
- Fake tutorial
- """
- def __init__(self, start_name="INIT"):
- #Tutorial.__init__(self, "Simple Tutorial", None)
- self.current_state_name = start_name
- self.activity = "TODO : This should be an activity"
-
- def set_state(self, name):
- self.current_state_name = name
-
-class TutorialTest(unittest.TestCase):
- """Tests the tutorial functions that are not covered elsewhere."""
- def test_detach(self):
- class Activity(object):
- name = "this"
-
- activity1 = Activity()
- activity2 = Activity()
-
- fsm = FiniteStateMachine("Sample example")
-
- tutorial = Tutorial("Test tutorial", fsm)
-
- assert tutorial.activity == None, "There is a default activity in the tutorial"
-
- tutorial.attach(activity1)
-
- assert tutorial.activity == activity1, "Activity should have been associated to this tutorial"
-
- tutorial.attach(activity2)
- assert tutorial.activity == activity2, "Activity should have been changed to activity2"
-
-class TutorialWithFSM(Tutorial):
- """
- Fake tutorial, but associated with a FSM.
- """
- def __init__(self, start_name="INIT", fsm=None):
- Tutorial.__init__(self, start_name, fsm)
- self.activity = activity.Activity()
-
-class TrueWhileActiveAction(Action):
- """
- This action's active member is set to True after a do and to False after
- an undo.
-
- Used to verify that a State correctly triggers the do and undo actions.
- """
- def __init__(self):
- Action.__init__(self)
- self.active = False
-
- def do(self):
- self.active = True
-
- def undo(self):
- self.active = False
-
-# State testing class
-class StateTest(unittest.TestCase):
- """
- This class has to test the State interface as well as the expected
- functionality.
- """
-
- def test_action_toggle(self):
- """
- Validate that the actions are properly done on setup and undone on
- teardown.
-
- Pretty awesome.
- """
- act = TrueWhileActiveAction()
-
- state = State("action_test", action_list=[act])
-
- assert act.active == False, "Action is not initialized properly"
-
- state.setup()
-
- assert act.active == True, "Action was not triggered properly"
-
- state.teardown()
-
- assert act.active == False, "Action was not undone properly"
-
- def test_event_filter(self):
- """
- Tests the fact that the event filters are correctly installed on setup
- and uninstalled on teardown.
- """
- event_filter = addon.create('TriggerEventFilter')
-
- state = State("event_test", event_filter_list=[(event_filter, "second_state")])
- state.set_tutorial(SimpleTutorial())
-
- assert event_filter.toggle_on_callback == False, "Wrong init of event_filter"
- assert event_filter._callback == None, "Event filter has a registered callback before installing handlers"
-
- state.setup()
-
- assert event_filter._callback != None, "Event filter did not register callback!"
-
- # 'Trigger' the event - This is more like a EventFilter test.
- event_filter.do_callback()
-
- assert event_filter.toggle_on_callback == True, "Event filter did not execute callback"
-
- state.teardown()
-
- assert event_filter._callback == None, "Event filter did not remove callback properly"
-
- def test_warning_set_tutorial_twice(self):
- """
- Calls set_tutorial twice and expects a warning on the second.
- """
- state = State("start_state")
- tut = SimpleTutorial("First")
- tut2 = SimpleTutorial("Second")
-
- state.set_tutorial(tut)
-
- try:
- state.set_tutorial(tut2)
- assert False, "No RuntimeWarning was raised on second set_tutorial"
- except :
- pass
-
- def test_add_action(self):
- """
- Tests on manipulating the actions inside a state.
- """
- state = State("INIT")
-
- act1 = CountAction()
- act2 = CountAction()
- act3 = CountAction()
-
- # Try to add the actions
- assert state.add_action(act1), "Could not add the first action"
- assert state.add_action(act2), "Could not add the second action"
- assert state.add_action(act3), "Could not add the third action"
-
- # Fetch the associated actions
- actions = state.get_action_list()
-
- # Make sure all the actions are present in the state
- assert act1 in actions and act2 in actions and act3 in actions, \
- "The actions were not properly inserted in the state"
-
- # Clear the list
- state.clear_actions()
-
- # Make sure the list of actions is empty now
- assert len(state.get_action_list()) == 0, "Clearing of actions failed"
-
- def test_add_event_filter(self):
- state = State("INIT")
-
- event1 = addon.create('TriggerEventFilter')
- event2 = addon.create('TriggerEventFilter')
-
- # Insert the event filters
- assert state.add_event_filter(event1, "s"), "Could not add event filter 1"
-
- # Make sure we cannot insert an event twice
- assert state.add_event_filter(event1, "s") == False, "Could add twice the event filter"
- assert state.add_event_filter(event2, "t") == False, "Could add event filter 2"
-
- # Get the list of event filters
- event_filters = map(lambda x: x[0],state.get_event_filter_list())
-
- #even if we added only the event 1, they are equivalent
- assert event1 in event_filters and event2 in event_filters, \
- "The event filters were not all added inside the state"
-
- # Clear the list
- state.clear_event_filters()
-
- assert len(state.get_event_filter_list()) == 0, \
- "Could not clear the event filter list properly"
-
- def test_eq_simple(self):
- """
- Two empty states with the same name must be identical
- """
- st1 = State("Identical")
- st2 = State("Identical")
-
- assert st1 == st2, "Empty states with the same name should be identical"
-
- def test_eq(self):
- """
- Test whether two states share the same set of actions and event filters.
- """
- st1 = State("Identical")
- st2 = State("Identical")
-
- non_state = object()
-
- act1 = addon.create("BubbleMessage", message="Hi", position=[132,450])
- act2 = addon.create("BubbleMessage", message="Hi", position=[132,450])
-
- event1 = addon.create("GtkWidgetEventFilter", object_id="0.0.0.1.1.2.3.1", event_name="clicked")
-
- act3 = addon.create("DialogMessage", message="Hello again.", position=[200, 400])
-
- # Build the first state
- st1.add_action(act1)
- st1.add_action(act3)
- st1.add_event_filter(event1, "nextState")
-
- # Build the second state
- st2.add_action(act2)
- st2.add_action(act3)
- st2.add_event_filter(event1, "nextState")
-
- # Make sure that they are identical for now
- assert st1 == st2, "States should be considered as identical"
- assert st2 == st1, "States should be considered as identical"
-
- # Modify the second bubble message action
- act2.message = "New message"
-
- # Since one action changed in the second state, this should indicate that the states
- # are not identical anymore
- assert not (st1 == st2), "Action was changed and states should be different"
- assert not (st2 == st1), "Action was changed and states should be different"
-
- # Make sure that trying to find identity with something else than a State object fails properly
- assert not (st1 == non_state), "Passing a non-State object should fail for identity"
-
- st2.name = "Not identical anymore"
- assert not(st1 == st2), "Different state names should give different states"
- st2.name = "Identical"
-
- st3 = deepcopy(st1)
- st3.add_action(addon.create("BubbleMessage", message="Hi!", position=[128,264]))
-
- assert not (st1 == st3), "States having a different number of actions should be different"
-
- st4 = deepcopy(st1)
- st4.add_event_filter(addon.create("GtkWidgetEventFilter", object_id="0.0.1.1.2.2.3", event_name="clicked"), "next_state")
-
- assert not (st1 == st4), "States having a different number of events should be different"
-
- st5 = deepcopy(st1)
- st5._event_filters = []
-
- st5.add_event_filter(addon.create("GtkWidgetEventFilter", object_id="0.1.2.3.4.1.2", event_name="pressed"), "other_state")
-
- assert not (st1 == st5), "States having the same number of event filters" \
- + " but those being different should be different"
-
-class FSMTest(unittest.TestCase):
- """
- This class needs to text the interface and functionality of the Finite
- State Machine.
- """
-
- def test_sample_usage(self):
- act_init = TrueWhileActiveAction()
- act_second = TrueWhileActiveAction()
-
- event_init = FakeEventFilter()
-
- content = {
- "INIT": State("INIT", action_list=[act_init],event_filter_list=[(event_init,"SECOND")]),
- "SECOND": State("SECOND", action_list=[act_second])
- }
-
- fsm = FiniteStateMachine("SampleUsage", state_dict=content)
-
- assert fsm is not None, "Unable to create FSM"
-
- tut = Tutorial("SampleUsageTutorial", fsm)
-
- tut.attach(None)
- event_init.set_tutorial(tut)
-
- assert fsm.current_state.name == "INIT", "Unable to set state to initial state"
-
- assert act_init.active, "FSM did not call the state's action DO properly"
-
- # Trigger the event of the INIT state
- event_init.do_callback()
-
- assert act_init.active == False, "FSM did not teardown INIT properly"
-
- assert fsm.current_state.name == "SECOND", "FSM did not switch to SECOND state"
-
- assert act_second.active == True, "FSM did not setup SECOND properly"
-
- tut.detach()
-
- assert act_second.active == False, "FSM did not teardown SECOND properly"
-
-
-
- def test_state_insert(self):
- """
- This is a simple test to insert, then find a state.
- """
- st1 = State("FakeState")
-
- fsm = FiniteStateMachine("StateInsertTest")
-
- fsm.add_state(st1)
-
- inserted_state = fsm.get_state_by_name(st1.name)
-
- assert inserted_state is st1, "Inserting, then fetching a state did not work"
-
- # Make sure we cannot insert it twice
- try :
- fsm.add_state(st1)
- assert False, "No error raised on addition of an already present state"
- except KeyError:
- pass
-
- def test_state_find_by_name(self):
- """
- Tests the interface for fetching a state by name.
- - Basic functionnality
- - Non-existent state
- """
-
- st1 = State("INIT")
-
- st2 = State("second")
-
- fsm = FiniteStateMachine("StateFindTest")
-
- fsm.add_state(st1)
- fsm.add_state(st2)
-
- # Test the fetch by name
- fetched_st1 = fsm.get_state_by_name(st1.name)
-
- assert fetched_st1 is st1, "Fetched state is not the same as the inserted one"
-
- fetched_st2 = fsm.get_state_by_name(st2.name)
-
- assert fetched_st2 is st2, "Fetched state is not the same as the inserted one"
-
- try:
- fsm.get_state_by_name("no such state")
- assert False, "Did not get a KeyError on non-existing key search"
- except KeyError:
- pass
- except Exception:
- assert False, "Did not get the right error on non-existing key search"
-
- def test_state_removal(self):
- """
- This test removes a state from the FSM. It also verifies that the links
- from other states going into the removed state are gone.
- """
- st1 = State("INIT", event_filter_list=[(addon.create('TriggerEventFilter'), "second")])
- st2 = State("second", event_filter_list=[(addon.create('TriggerEventFilter'), "third")])
- st3 = State("third", event_filter_list=[(addon.create('TriggerEventFilter'), "second")])
-
- fsm = FiniteStateMachine("StateRemovalTest")
-
- fsm.add_state(st1)
- fsm.add_state(st2)
- fsm.add_state(st3)
-
- # First tests - Removing a non-existing state and make sure we get a
- # KeyError
- try:
- fsm.remove_state("Non-existing")
- assert False, "Removing a non-existing state did not throw a KeyError"
- except KeyError:
- pass
- except Exception:
- assert False, "Removing a non-existing state dit not throw the right kind of exception"
-
- # Now try removing the second state
- fsm.remove_state("second")
-
- # Make sure it cannot be fetched
- try :
- fetched_state = fsm.get_state_by_name("second")
- assert False, "The supposedly removed state is still present in the FSM"
- except KeyError:
- pass
-
- # Make sure that there is no link to the removed state in the rest
- # of the FSM
- assert "second" not in fsm.get_following_states("INIT"), \
- "The link to second from INIT still exists after removal"
-
- assert "second" not in fsm.get_following_states("third"), \
- "The link to second from third still exists after removal"
-
- def test_set_same_state(self):
- fsm = FiniteStateMachine("Set same state")
-
- st1 = State("INIT")
- st1.add_action(CountAction())
-
- fsm.add_state(st1)
-
- tut = SimpleTutorial()
-
- fsm.set_tutorial(tut)
-
- fsm.set_state("INIT")
-
- assert fsm.get_state_by_name("INIT").get_action_list()[0].do_count == 1, \
- "The action was not triggered on 'INIT'"
-
- fsm.set_state("INIT")
-
- do_count = fsm.get_state_by_name("INIT").get_action_list()[0].do_count
- assert fsm.get_state_by_name("INIT").get_action_list()[0].do_count == 1, \
- "The action was triggered a second time, do_count = %d"%do_count
-
- undo_count = fsm.get_state_by_name("INIT").get_action_list()[0].undo_count
- assert fsm.get_state_by_name("INIT").get_action_list()[0].undo_count == 0, \
- "The action has been undone unappropriately, undo_count = %d"%undo_count
-
- def test_setup(self):
- fsm = FiniteStateMachine("New state machine")
-
- try:
- fsm.setup()
- assert False, "fsm should throw an exception when trying to setup and not bound to a tutorial"
- except UnboundLocalError:
- pass
-
- def test_setup_actions(self):
- tut = SimpleTutorial()
-
- states_dict = {"INIT": State("INIT")}
- fsm = FiniteStateMachine("New FSM", state_dict=states_dict)
-
- act = CountAction()
- fsm.add_action(act)
-
- fsm.set_tutorial(tut)
-
- fsm.setup()
-
- # Let's also test the current state name
- assert fsm.get_current_state_name() == "INIT", "Initial state should be INIT"
-
- assert act.do_count == 1, "Action should have been called during setup"
-
- fsm._fsm_has_finished = True
-
- fsm.teardown()
-
- assert act.undo_count == 1, "Action should have been undone"
-
- def test_string_rep(self):
- fsm = FiniteStateMachine("Testing machine")
-
- st1 = State("INIT")
- st2 = State("Other State")
- st3 = State("Final State")
-
- st1.add_action(addon.create("BubbleMessage", message="Hi!", position=[132,312]))
-
- fsm.add_state(st1)
- fsm.add_state(st2)
- fsm.add_state(st3)
-
- assert str(fsm) == "INIT, Final State, Other State, "
-
- def test_eq_(self):
- fsm = FiniteStateMachine("Identity test")
-
- non_fsm_object = object()
-
- assert not (fsm == non_fsm_object), "Testing with non FSM object should not give identity"
-
- # Compare FSMs
- act1 = CountAction()
-
- fsm.add_action(act1)
-
- fsm2 = deepcopy(fsm)
-
- assert fsm == fsm2
-
- act2 = CountAction()
- fsm2.add_action(act2)
-
- assert not(fsm == fsm2), \
- "FSMs having a different number of actions should be different"
-
- fsm3 = FiniteStateMachine("Identity test")
-
- act3 = addon.create("BubbleMessage", message="Hi!", position=[123,312])
- fsm3.add_action(act3)
-
- assert not(fsm3 == fsm), \
- "Actions having the same number of actions but different ones should be different"
-
- st1 = State("INIT")
-
- st2 = State("OtherState")
-
- fsm.add_state(st1)
- fsm.add_state(st2)
-
- fsm4 = deepcopy(fsm)
-
- assert fsm == fsm4
-
- st3 = State("Last State")
-
- fsm4.add_state(st3)
-
- assert not (fsm == fsm4), "FSMs having a different number of states should not be identical"
-
- fsm4.remove_state("OtherState")
-
- assert not (fsm == fsm4), "FSMs having different states should be different"
-
- fsm4.remove_state("Last State")
-
- st5 = State("OtherState")
- st5.add_action(CountAction())
-
- fsm4.add_state(st5)
-
- assert not(fsm == fsm4), "FSMs having states with same name but different content should be different"
-
-class FSMExplorationTests(unittest.TestCase):
- def setUp(self):
- self.buildFSM()
-
- def buildFSM(self):
- """
- Create a sample FSM to play with in the rest of the tests.
- """
- st1 = State("INIT")
- st1.add_action(CountAction())
- st1.add_event_filter(addon.create('TriggerEventFilter'), "Second")
- st1.add_event_filter(addon.create('TriggerEventFilter'), "Third")
-
- st2 = State("Second")
- st2.add_action(TrueWhileActiveAction())
- st2.add_event_filter(addon.create('TriggerEventFilter'), "Third")
- st2.add_event_filter(addon.create('TriggerEventFilter'), "Fourth")
-
- st3 = State("Third")
- st3.add_action(CountAction())
- st3.add_action(TrueWhileActiveAction())
-
- self.fsm = FiniteStateMachine("ExplorationTestingMachine")
- self.fsm.add_state(st1)
- self.fsm.add_state(st2)
- self.fsm.add_state(st3)
-
- def validate_following_states(self, in_name, out_name_list):
- nextStates = self.fsm.get_following_states(in_name)
- assert list(nextStates).sort() == list(out_name_list).sort(), \
- "The following states for %s are wrong : got %s"%\
- (in_name, str(nextStates))
-
- def validate_previous_states(self, in_name, out_name_list):
- prevStates = self.fsm.get_previous_states(in_name)
- assert list(prevStates).sort() == list(out_name_list).sort(), \
- "The following states for %s are wrong : got %s"%\
- (in_name, str(prevStates))
-
- def test_get_following_states(self):
- self.validate_following_states("INIT", ('Second', 'Third'))
-
- self.validate_following_states("Second", ("Third", "Fourth"))
-
- self.validate_following_states("Third", ())
-
- def test_get_previous_states(self):
- self.validate_previous_states("INIT", ())
-
- self.validate_previous_states("Second", ("INIT"))
-
- self.validate_previous_states("Third", ("INIT", "Second"))
-
- self.validate_previous_states("Fourth", ("Second"))
-
-if __name__ == "__main__":
- unittest.main()