From a8789dced903ff6236974fc268305379cd2ce057 Mon Sep 17 00:00:00 2001 From: JonahStanley Date: Thu, 20 Jun 2013 11:14:17 -0400 Subject: [PATCH] Fixed flakey check box by making a css_check function that behaves like css_click As a result, changed inputfield to return the css, and all of the element.fill() to css_fill --- common/djangoapps/terrain/ui_helpers.py | 32 +++++++++++++++++++ .../courseware/features/problems_setup.py | 32 +++++++++---------- 2 files changed, 48 insertions(+), 16 deletions(-) diff --git a/common/djangoapps/terrain/ui_helpers.py b/common/djangoapps/terrain/ui_helpers.py index 8e4330d940..9c837cbd0d 100644 --- a/common/djangoapps/terrain/ui_helpers.py +++ b/common/djangoapps/terrain/ui_helpers.py @@ -89,6 +89,38 @@ def css_click(css_selector, index=0, attempts=5, success_condition=lambda:True): return result +@world.absorb +def css_check(css_selector, index=0, attempts=5, success_condition=lambda: True): + """ + Checks a check box based on a CSS selector, retrying if it initially fails. + + This function handles errors that may be thrown if the component cannot be clicked on. + However, there are cases where an error may not be thrown, and yet the operation did not + actually succeed. For those cases, a success_condition lambda can be supplied to verify that the check worked. + + This function will return True if the check worked (taking into account both errors and the optional + success_condition). + """ + assert is_css_present(css_selector) + attempt = 0 + result = False + while attempt < attempts: + try: + world.css_find(css_selector)[index].check() + if success_condition(): + result = True + break + except WebDriverException: + # Occasionally, MathJax or other JavaScript can cover up + # an element temporarily. + # If this happens, wait a second, then try again + world.wait(1) + attempt += 1 + except: + attempt += 1 + return result + + @world.absorb def css_click_at(css, x=10, y=10): ''' diff --git a/lms/djangoapps/courseware/features/problems_setup.py b/lms/djangoapps/courseware/features/problems_setup.py index ce343bb853..b8f817f933 100644 --- a/lms/djangoapps/courseware/features/problems_setup.py +++ b/lms/djangoapps/courseware/features/problems_setup.py @@ -142,34 +142,34 @@ def answer_problem(problem_type, correctness): elif problem_type == "multiple choice": if correctness == 'correct': - inputfield('multiple choice', choice='choice_2').check() + world.css_check(inputfield('multiple choice', choice='choice_2')) else: - inputfield('multiple choice', choice='choice_1').check() + world.css_check(inputfield('multiple choice', choice='choice_1')) elif problem_type == "checkbox": if correctness == 'correct': - inputfield('checkbox', choice='choice_0').check() - inputfield('checkbox', choice='choice_2').check() + world.css_check(inputfield('checkbox', choice='choice_0')) + world.css_check(inputfield('checkbox', choice='choice_2')) else: - inputfield('checkbox', choice='choice_3').check() + world.css_check(inputfield('checkbox', choice='choice_3')) elif problem_type == 'radio': if correctness == 'correct': - inputfield('radio', choice='choice_2').check() + world.css_check(inputfield('radio', choice='choice_2')) else: - inputfield('radio', choice='choice_1').check() + world.css_check(inputfield('radio', choice='choice_1')) elif problem_type == 'string': textvalue = 'correct string' if correctness == 'correct' else 'incorrect' - inputfield('string').fill(textvalue) + world.css_fill(inputfield('string'), textvalue) elif problem_type == 'numerical': textvalue = "pi + 1" if correctness == 'correct' else str(random.randint(-2, 2)) - inputfield('numerical').fill(textvalue) + world.css_fill(inputfield('numerical'), textvalue) elif problem_type == 'formula': textvalue = "x^2+2*x+y" if correctness == 'correct' else 'x^2' - inputfield('formula').fill(textvalue) + world.css_fill(inputfield('formula'), textvalue) elif problem_type == 'script': # Correct answer is any two integers that sum to 10 @@ -181,8 +181,8 @@ def answer_problem(problem_type, correctness): if correctness == 'incorrect': second_addend += random.randint(1, 10) - inputfield('script', input_num=1).fill(str(first_addend)) - inputfield('script', input_num=2).fill(str(second_addend)) + world.css_fill(inputfield('script', input_num=1), str(first_addend)) + world.css_fill(inputfield('script', input_num=2), str(second_addend)) elif problem_type == 'code': # The fake xqueue server is configured to respond @@ -281,7 +281,7 @@ def add_problem_to_course(course, problem_type, extraMeta=None): def inputfield(problem_type, choice=None, input_num=1): - """ Return the element for *problem_type*. + """ Return the css element for *problem_type*. For example, if problem_type is 'string', return the text field for the string problem in the test course. @@ -299,7 +299,7 @@ def inputfield(problem_type, choice=None, input_num=1): assert world.is_css_present(sel) # Retrieve the input element - return world.browser.find_by_css(sel) + return sel def assert_checked(problem_type, choices): @@ -312,7 +312,7 @@ def assert_checked(problem_type, choices): all_choices = ['choice_0', 'choice_1', 'choice_2', 'choice_3'] for this_choice in all_choices: - element = inputfield(problem_type, choice=this_choice) + element = world.css_find(inputfield(problem_type, choice=this_choice)) if this_choice in choices: assert element.checked @@ -321,5 +321,5 @@ def assert_checked(problem_type, choices): def assert_textfield(problem_type, expected_text, input_num=1): - element = inputfield(problem_type, input_num=input_num) + element = world.css_find(inputfield(problem_type, input_num=input_num)) assert element.value == expected_text