studio - resolving local merge
This commit is contained in:
@@ -7,18 +7,18 @@ Feature: Advanced (manual) course policy
|
||||
When I select the Advanced Settings
|
||||
Then I see only the display name
|
||||
|
||||
Scenario: A course author sees something sensible if there are no policy settings without existing UI controls
|
||||
Scenario: Test if there are no policy settings without existing UI controls
|
||||
Given I have opened a new course in Studio
|
||||
When I select the Advanced Settings
|
||||
And I delete the display name
|
||||
Then There are no advanced policy settings
|
||||
And I refresh and select the Advanced Settings
|
||||
Then There are no advanced policy settings
|
||||
Then there are no advanced policy settings
|
||||
And I reload the page
|
||||
Then there are no advanced policy settings
|
||||
|
||||
Scenario: A course author can add new entries, and they appear alphabetically after save
|
||||
Given I have opened a new course in Studio
|
||||
When I select the Advanced Settings
|
||||
And Create New Entries
|
||||
Then They are alphabetized
|
||||
And I refresh and select the Advanced Settings
|
||||
Then They are alphabetized
|
||||
Scenario: Add new entries, and they appear alphabetically after save
|
||||
Given I have opened a new course in Studio
|
||||
When I select the Advanced Settings
|
||||
And I create New Entries
|
||||
Then they are alphabetized
|
||||
And I reload the page
|
||||
Then they are alphabetized
|
||||
@@ -11,41 +11,43 @@ from selenium.webdriver.common.keys import Keys
|
||||
############### ACTIONS ####################
|
||||
@step('I select the Advanced Settings$')
|
||||
def i_select_advanced_settings(step):
|
||||
link_css = 'a#settings-tab'
|
||||
css_click(link_css)
|
||||
link_css = "[data-section='advanced']"
|
||||
expand_icon_css = 'li.nav-course-settings i.icon-expand'
|
||||
if world.browser.is_element_present_by_css(expand_icon_css):
|
||||
css_click(expand_icon_css)
|
||||
link_css = 'li.nav-course-settings-advanced a'
|
||||
css_click(link_css)
|
||||
|
||||
@step('I refresh and select the Advanced Settings$')
|
||||
def refresh_and_select_advanced_settings(step):
|
||||
reload()
|
||||
i_select_advanced_settings(step)
|
||||
|
||||
@step('I see only the display name$')
|
||||
def i_see_only_display_name(step):
|
||||
assert_policy_entries(["display_name"], ['"Robot Super Course"'])
|
||||
|
||||
|
||||
@step('I delete the display name')
|
||||
def i_delete_the_display_name(step):
|
||||
delete_entry(0)
|
||||
click_save()
|
||||
|
||||
@step("There are no advanced policy settings$")
|
||||
|
||||
@step('there are no advanced policy settings$')
|
||||
def no_policy_settings(step):
|
||||
assert_policy_entries([], [])
|
||||
|
||||
@step("Create New Entries")
|
||||
|
||||
@step('create New Entries$')
|
||||
def create_new_entries(step):
|
||||
create_entry("z", "apple")
|
||||
create_entry("a", "zebra")
|
||||
click_save()
|
||||
|
||||
@step("They are alphabetized")
|
||||
|
||||
@step('they are alphabetized$')
|
||||
def they_are_alphabetized(step):
|
||||
assert_policy_entries(["a", "display_name", "z"], ['"zebra"', '"Robot Super Course"', '"apple"'])
|
||||
|
||||
|
||||
def create_entry(key, value):
|
||||
css_click(".new-advanced-policy-item")
|
||||
css_click_at('a.new-advanced-policy-item')
|
||||
newKey = css_find('#__new_advanced_key__ input').first
|
||||
newKey.fill(key)
|
||||
# For some reason have to get the instance for each command (get error that it is no longer attached to the DOM)
|
||||
@@ -54,6 +56,7 @@ def create_entry(key, value):
|
||||
css_find('.CodeMirror textarea').last._element.send_keys(Keys.ARROW_LEFT)
|
||||
css_find('.CodeMirror textarea').last.fill(value)
|
||||
|
||||
|
||||
def delete_entry(index):
|
||||
""" index is 0-based
|
||||
"""
|
||||
@@ -63,17 +66,20 @@ def delete_entry(index):
|
||||
assert_true(len(delete_buttons) > index, "no delete button exists for entry " + str(index))
|
||||
delete_buttons[index].click()
|
||||
|
||||
|
||||
def assert_policy_entries(expected_keys, expected_values):
|
||||
assert_entries('.key input', expected_keys)
|
||||
assert_entries('.json', expected_values)
|
||||
|
||||
|
||||
def assert_entries(css, expected_values):
|
||||
webElements = css_find(css)
|
||||
assert_equal(len(expected_values),len(webElements))
|
||||
assert_equal(len(expected_values), len(webElements))
|
||||
# Sometimes get stale reference if I hold on to the array of elements
|
||||
for counter in range(len(expected_values)):
|
||||
assert_equal(expected_values[counter], css_find(css)[counter].value)
|
||||
|
||||
|
||||
def click_save():
|
||||
css = ".save-button"
|
||||
def is_shown(driver):
|
||||
@@ -85,6 +91,7 @@ def click_save():
|
||||
wait_for(is_shown)
|
||||
css_click(css)
|
||||
|
||||
|
||||
def fill_last_field(value):
|
||||
newValue = css_find('#__new_advanced_key__ input').first
|
||||
newValue.fill(value)
|
||||
newValue.fill(value)
|
||||
|
||||
@@ -10,6 +10,7 @@ from logging import getLogger
|
||||
logger = getLogger(__name__)
|
||||
|
||||
########### STEP HELPERS ##############
|
||||
|
||||
@step('I (?:visit|access|open) the Studio homepage$')
|
||||
def i_visit_the_studio_homepage(step):
|
||||
# To make this go to port 8001, put
|
||||
@@ -19,14 +20,17 @@ def i_visit_the_studio_homepage(step):
|
||||
signin_css = 'a.action-signin'
|
||||
assert world.browser.is_element_present_by_css(signin_css, 10)
|
||||
|
||||
|
||||
@step('I am logged into Studio$')
|
||||
def i_am_logged_into_studio(step):
|
||||
log_into_studio()
|
||||
|
||||
|
||||
@step('I confirm the alert$')
|
||||
def i_confirm_with_ok(step):
|
||||
world.browser.get_alert().accept()
|
||||
|
||||
|
||||
@step(u'I press the "([^"]*)" delete icon$')
|
||||
def i_press_the_category_delete_icon(step, category):
|
||||
if category == 'section':
|
||||
@@ -37,6 +41,7 @@ def i_press_the_category_delete_icon(step, category):
|
||||
assert False, 'Invalid category: %s' % category
|
||||
css_click(css)
|
||||
|
||||
|
||||
@step('I have opened a new course in Studio$')
|
||||
def i_have_opened_a_new_course(step):
|
||||
clear_courses()
|
||||
@@ -44,13 +49,14 @@ def i_have_opened_a_new_course(step):
|
||||
create_a_course()
|
||||
|
||||
####### HELPER FUNCTIONS ##############
|
||||
|
||||
def create_studio_user(
|
||||
uname='robot',
|
||||
email='robot+studio@edx.org',
|
||||
password='test',
|
||||
is_staff=False):
|
||||
is_staff=False):
|
||||
studio_user = UserFactory.build(
|
||||
username=uname,
|
||||
username=uname,
|
||||
email=email,
|
||||
password=password,
|
||||
is_staff=is_staff)
|
||||
@@ -63,6 +69,7 @@ def create_studio_user(
|
||||
|
||||
user_profile = UserProfileFactory(user=studio_user)
|
||||
|
||||
|
||||
def flush_xmodule_store():
|
||||
# Flush and initialize the module store
|
||||
# It needs the templates because it creates new records
|
||||
@@ -75,32 +82,53 @@ def flush_xmodule_store():
|
||||
xmodule.modulestore.django.modulestore().collection.drop()
|
||||
xmodule.templates.update_templates()
|
||||
|
||||
|
||||
def assert_css_with_text(css, text):
|
||||
assert_true(world.browser.is_element_present_by_css(css, 5))
|
||||
assert_equal(world.browser.find_by_css(css).text, text)
|
||||
|
||||
|
||||
def css_click(css):
|
||||
assert_true(world.browser.is_element_present_by_css(css, 5))
|
||||
world.browser.find_by_css(css).first.click()
|
||||
|
||||
|
||||
def css_click_at(css, x=10, y=10):
|
||||
'''
|
||||
A method to click at x,y coordinates of the element
|
||||
rather than in the center of the element
|
||||
'''
|
||||
assert_true(world.browser.is_element_present_by_css(css, 5))
|
||||
e = world.browser.find_by_css(css).first
|
||||
e.action_chains.move_to_element_with_offset(e._element, x, y)
|
||||
e.action_chains.click()
|
||||
e.action_chains.perform()
|
||||
|
||||
|
||||
def css_fill(css, value):
|
||||
world.browser.find_by_css(css).first.fill(value)
|
||||
|
||||
|
||||
def css_find(css):
|
||||
return world.browser.find_by_css(css)
|
||||
|
||||
|
||||
def wait_for(func):
|
||||
WebDriverWait(world.browser.driver, 10).until(func)
|
||||
|
||||
|
||||
def id_find(id):
|
||||
return world.browser.find_by_id(id)
|
||||
|
||||
|
||||
def reload():
|
||||
return world.browser.reload()
|
||||
|
||||
|
||||
def clear_courses():
|
||||
flush_xmodule_store()
|
||||
|
||||
|
||||
def fill_in_course_info(
|
||||
name='Robot Super Course',
|
||||
org='MITx',
|
||||
@@ -109,6 +137,7 @@ def fill_in_course_info(
|
||||
css_fill('.new-course-org', org)
|
||||
css_fill('.new-course-number', num)
|
||||
|
||||
|
||||
def log_into_studio(
|
||||
uname='robot',
|
||||
email='robot+studio@edx.org',
|
||||
@@ -130,6 +159,7 @@ def log_into_studio(
|
||||
|
||||
assert_true(world.browser.is_element_present_by_css('.new-course-button', 5))
|
||||
|
||||
|
||||
def create_a_course():
|
||||
css_click('a.new-course-button')
|
||||
fill_in_course_info()
|
||||
@@ -137,6 +167,7 @@ def create_a_course():
|
||||
course_title_css = 'span.course-title'
|
||||
assert_true(world.browser.is_element_present_by_css(course_title_css, 5))
|
||||
|
||||
|
||||
def add_section(name='My Section'):
|
||||
link_css = 'a.new-courseware-section-button'
|
||||
css_click(link_css)
|
||||
|
||||
@@ -21,6 +21,11 @@ def wait(step, seconds):
|
||||
time.sleep(float(seconds))
|
||||
|
||||
|
||||
@step('I reload the page$')
|
||||
def reload_the_page(step):
|
||||
world.browser.reload()
|
||||
|
||||
|
||||
@step('I (?:visit|access|open) the homepage$')
|
||||
def i_visit_the_homepage(step):
|
||||
world.browser.visit(django_url('/'))
|
||||
|
||||
Reference in New Issue
Block a user