def test_submachines_machine(self):
        states, trans = make_submachines_machine(use_logging=False)
        hsm = HSM(states, trans)

        l0_start = get_state_by_sig(('left', 0, 'start'), hsm.flattened)
        s0_top = get_state_by_sig(('subs', 0, 'top'), hsm.flattened)
        s1_final = get_state_by_sig(('subs', 1, 'final'), hsm.flattened)

        tree = tree_from_state_set( set([l0_start, s0_top, s1_final]) )
        assert len(tree) == 1  # only one root node

        assert self.extract_names(tree) == [
            ('top', [
                ('left', [
                    ('left[0].top', [
                        ('left[0].start', [])
                    ]),
                ]),
                ('right', [
                    ('subs', [
                        ('subs[0].top', []),
                        ('subs[1].top', [
                            ('subs[1].final', []),
                        ]),
                    ]),
                ])
            ]),
        ]
예제 #2
0
    def test_with_HSM_instance(self):
        states = {
            'root': State({
                'left': State({
                    'left_A': State(),
                    'left_B': State(),
                }),
                'middle': State({
                    'middle_A': State(),
                    'middle_B': State(),
                    'middle_C': State(),
                }),
                'right': State({
                    'right_A': State({
                        'right_A_1': State(),
                        'deep': State(),
                        'right_A_2': State(),
                    }),
                    'right_B': State(),
                })
            })
        }

        flattened = HSM(states, {}, skip_validation=True).flattened

        left_B = get_state_by_sig(('left_B',), flattened)
        deep = get_state_by_sig(('deep',), flattened)

        exits, parent, entries = get_path(deep, left_B)
        exits = [st.name for st in exits]
        entries = [st.name for st in entries]

        assert exits == ['deep', 'right_A', 'right']
        assert parent.name == 'root'
        assert entries == ['left', 'left_B']
    def test_miro_machine(self):
        states, trans = make_miro_machine(use_logging=False)
        hsm = HSM(states, trans)

        s1 = get_state_by_sig(('s11',), hsm.flattened)
        s211 = get_state_by_sig(('s211',), hsm.flattened)

        tree = tree_from_state_set( set([s1, s211]) )
        assert len(tree) == 1  # only one root node

        assert self.extract_names(tree) == [
            ('top', [
                ('s', [
                    ('s1', [
                        ('s11', [])
                    ]),
                    ('s2', [
                        ('s21', [
                            ('s211', []),
                        ])
                    ])
                ]),
                # ('final', []),  # final should NOT be in the tree
            ])
        ]
예제 #4
0
def check(hsm, state_name, Event, foo_before, foo_expected,
          expected_leaf_state, expected_exits, expected_entries):
    mock_hsm = MockHSM()
    mock_hsm.data.foo = foo_before
    # state set and expected state set are not specified in the parameters list
    # so we'll build them on the fly - knowing the leaf states, state set is
    # path from root to that leaf state
    state_set = set(
        get_path_from_root(
            get_state_by_sig((state_name,), hsm.flattened)))
    expected_state_set = set(
        get_path_from_root(
            get_state_by_sig((expected_leaf_state,), hsm.flattened)))

    exit_actions, entry_actions, new_state_set = get_merged_sequences(
        state_set, Event(), hsm.trans, hsm.flattened, mock_hsm)

    exit_action_names = [str(act) for act in exit_actions]
    entry_action_names = [str(act) for act in entry_actions]

    assert exit_action_names == expected_exits
    assert entry_action_names == expected_entries
    assert new_state_set  == expected_state_set

    # perform actions to update 'foo' value in mock_hsm.data
    [exit_act(None, mock_hsm) for exit_act in exit_actions]
    [entry_act(None, mock_hsm) for entry_act in entry_actions]

    if foo_expected != _:  # only if we care about the value of 'foo'
        assert mock_hsm.data.foo == foo_expected
예제 #5
0
    def test_after_reformat(self):
        states = {
            'root': State({
                'left': State({
                    'left_A': State(),
                    'left_B': State(),
                }),
                'middle': State({
                    'middle_A': State(),
                    'middle_B': State(),
                    'middle_C': State(),
                }),
                'right': State({
                    'right_A': State({
                        'right_A_1':  State(),
                        'right_A_2': State(),
                    }),
                    'right_B': State(),
                })
            })
        }

        flattened = HSM(states, {}, skip_validation=True).flattened

        left_A = get_state_by_sig(('left_A',), flattened)
        left_B = get_state_by_sig(('left_B',), flattened)
        right_A_1 = get_state_by_sig(('right_A_1',), flattened)
        right_B = get_state_by_sig(('right_B',), flattened)

        assert get_common_parent(left_A, left_B).name == 'left'
        assert get_common_parent(left_A, right_A_1).name == 'root'
        assert get_common_parent(right_A_1, right_B).name == 'right'
예제 #6
0
    def test_run(self, state_name, Event, foo_before, foo_expected,
                 exp_responding_state, exp_transition_target):
        mock_hsm = MockHSM()
        mock_hsm.data.foo = foo_before
        state = get_state_by_sig((state_name,), self.hsm.flattened)
        tree = tree_from_state_set(set([state]))

        resps = get_responses(tree, Event(), self.hsm.trans, mock_hsm)

        if exp_responding_state is None:
            assert resps == []
        else:
            assert len(resps) == 1  # no orthogonal regions in this HSM
            resp_subtrees, trans = zip(*resps)
            assert resp_subtrees[0][0].name == exp_responding_state
            tran = trans[0]

            if exp_transition_target is not None:
                assert State.sig_to_name(tran.target) == exp_transition_target
            else:
                assert tran.target is None

            tran.action(None, mock_hsm)  # this call might change 'foo' value
                                         # event is not relevant

        if foo_expected != 'ignored':
            assert mock_hsm.data.foo == foo_expected
예제 #7
0
    def test_with_HSM_instance(self):
        states = {
            'root': State({
                'left': State({
                    'left_A': State(),
                    'left_B': State(),
                }),
                'middle': State({
                    'middle_A': State(),
                    'middle_B': State(),
                    'middle_C': State(),
                }),
                'right': State({
                    'right_A': State({
                        'right_A_1': State(),
                        'deep': State(),
                        'right_A_2': State(),
                    }),
                    'right_B': State(),
                })
            })
        }

        flattened = HSM(states, {}, skip_validation=True).flattened
        deep = get_state_by_sig(('deep',), flattened)
        state_names = [state.name for state in get_path_from_root(deep)]
        assert state_names == ['root', 'right', 'right_A', 'deep']
예제 #8
0
 def test_enter_right(self):
     expected_action_names = ['right-entry', 'right-Initial', 'subs-entry',
                              'subs[0].top-entry', 'subs[0].top-Initial',
                              'subs[0].start-entry', 'subs[1].top-entry',
                              'subs[1].top-Initial', 'subs[1].start-entry']
     right = get_state_by_sig(('right',), self.hsm.flattened)
     seq = entry_sequence(right, self.hsm.trans,
                          self.hsm.flattened, self.hsm)
     assert [str(act) for act in seq] == expected_action_names
예제 #9
0
    def test_enter_B(self):
        mock = MockHSM()
        B_state = get_state_by_sig(('B',), self.hsm.flattened)

        for key in [3, 4, 5, 6, 'blah']:
            mock.data.foo = key

            expected_action_names = ['B-entry', 'B-Initial', 'C-entry']
            seq = entry_sequence(B_state, self.hsm.trans,
                                 self.hsm.flattened, mock)
            assert [str(act) for act in seq] == expected_action_names
예제 #10
0
def check(hsm, states, Event, exp_resp_states, exp_tran_targets):
    state_set = set([get_state_by_sig(sig, hsm.flattened) for sig in states])
    tree = tree_from_state_set(state_set)
    resps = get_responses(tree, Event(), hsm.trans, None)

    if exp_resp_states or exp_tran_targets:
        resp_subtrees, trans = zip(*resps)
        assert len(resp_subtrees) == len(exp_resp_states)
        resp_sigs = set([st.sig for st, _ in resp_subtrees])
        assert resp_sigs == set(exp_resp_states)

        assert len(trans) == len(exp_tran_targets)
        target_ids = set([tr.target for tr in trans])
        assert target_ids == set(exp_tran_targets)
    else:
        assert resps == []
예제 #11
0
    def test_choice(self, states, event, exp_resp_states, exp_tran_targets):
        state_set = set([get_state_by_sig((name,), self.hsm.flattened)
                         for name in states])
        tree = tree_from_state_set(state_set)
        resps = get_responses(tree, event, self.hsm.trans, None)
        print resps

        if exp_resp_states or exp_tran_targets:
            resp_subtrees, trans = zip(*resps)
            assert len(resp_subtrees) == len(exp_resp_states)
            resp_names = set([st.name for st, _ in resp_subtrees])
            assert resp_names == set(exp_resp_states)

            assert len(trans) == len(exp_tran_targets)
            target_ids = set([State.sig_to_name(tr.target) for tr in trans])
            assert target_ids == set(exp_tran_targets)
        else:
            assert resps == []
예제 #12
0
    def test_enter_A(self):
        mock = MockHSM()
        A_state = get_state_by_sig(('A',), self.hsm.flattened)

        for key in [1, 3, 4, 5, 6, 'asd']:
            mock.data.foo = key

            expected_action_names = ['A-entry', 'A-Initial', 'B-entry',
                                     'C-entry']
            seq = entry_sequence(A_state, self.hsm.trans,
                                 self.hsm.flattened, mock)
            assert [str(act) for act in seq] == expected_action_names

        mock.data.foo = 2
        expected_action_names = ['A-entry', 'A-Initial', 'B-entry',
                                 'B-Initial', 'C-entry']
        seq = entry_sequence(A_state, self.hsm.trans,
                             self.hsm.flattened, mock)
        assert [str(act) for act in seq] == expected_action_names
예제 #13
0
 def test_enter_s2(self):
     expected_action_names = ['s2-entry', 's2-Initial', 's21-entry',
                              's211-entry']
     s2 = get_state_by_sig(('s2',), self.hsm.flattened)
     seq = entry_sequence(s2, self.hsm.trans, self.hsm.flattened, self.hsm)
     assert [str(act) for act in seq] == expected_action_names
예제 #14
0
def assert_curr_state(hsm, leaf_name):
    """Check that HSM's state set is same as set of states from root to leaf"""
    exp_set = set(
        get_path_from_root(
            get_state_by_sig((leaf_name,), hsm.flattened)))
    assert hsm.current_state_set == exp_set
예제 #15
0
 def test_get_state_by_sig_in_orthogonal(self):
     f = lambda tup: get_state_by_sig(tup, self.hsm.flattened)
     assert f(('ortho',)).sig == ('ortho',)
     assert f(('ortho', 0, 'sub1')).sig == ('ortho', 0, 'sub1')
     assert f(('ortho', 1, 'sub2')).sig == ('ortho', 1, 'sub2')
예제 #16
0
 def test_get_state_by_sig(self):
     f = lambda nice: get_state_by_sig((nice,), self.hsm.flattened)
     assert f('top').name == 'top'
     assert f('left').name == 'left'
     assert f('mid_A').name == 'mid_A'
     assert f('right_B').name == 'right_B'