diff --git a/a11y_tests/mixins.py b/a11y_tests/mixins.py
index fe7269c64..555e138d0 100644
--- a/a11y_tests/mixins.py
+++ b/a11y_tests/mixins.py
@@ -1,5 +1,3 @@
-from __future__ import absolute_import
-
from acceptance_tests.mixins import AnalyticsApiClientMixin, LoginMixin
@@ -10,6 +8,6 @@ class CoursePageTestsMixin(LoginMixin, AnalyticsApiClientMixin):
page = None
def setUp(self):
- super(CoursePageTestsMixin, self).setUp()
+ super().setUp()
self.api_date_format = self.analytics_api_client.DATE_FORMAT
self.api_datetime_format = self.analytics_api_client.DATETIME_FORMAT
diff --git a/a11y_tests/pages.py b/a11y_tests/pages.py
index 3e7dc24b7..a923d58bd 100644
--- a/a11y_tests/pages.py
+++ b/a11y_tests/pages.py
@@ -2,7 +2,6 @@
Tests for course analytics pages
"""
-from __future__ import absolute_import
from bok_choy.page_object import PageObject
@@ -16,13 +15,13 @@ class CoursePage(PageObject):
def __init__(self, browser, course_id=None):
# Create the path
self.course_id = course_id or TEST_COURSE_ID
- path = 'courses/{}'.format(self.course_id)
+ path = f'courses/{self.course_id}'
self.server_url = DASHBOARD_SERVER_URL
- self.page_url = '{0}/{1}'.format(self.server_url, path)
+ self.page_url = f'{self.server_url}/{path}'
# Call the constructor and setup the URL
- super(CoursePage, self).__init__(browser)
+ super().__init__(browser)
def is_browser_on_page(self):
return self.browser.current_url == self.page_url
@@ -36,13 +35,13 @@ class CourseEnrollmentDemographicsPage(CoursePage):
demographic = None
def __init__(self, browser, course_id=None):
- super(CourseEnrollmentDemographicsPage, self).__init__(browser, course_id)
- self.page_url += '/enrollment/demographics/{0}/'.format(self.demographic)
+ super().__init__(browser, course_id)
+ self.page_url += f'/enrollment/demographics/{self.demographic}/'
def is_browser_on_page(self):
return (
- super(CourseEnrollmentDemographicsPage, self).is_browser_on_page()
- and 'Enrollment Demographics by {0}'.format(self.demographic.title())
+ super().is_browser_on_page()
+ and f'Enrollment Demographics by {self.demographic.title()}'
in self.browser.title
)
diff --git a/a11y_tests/test_course_enrollment_demographics_axs.py b/a11y_tests/test_course_enrollment_demographics_axs.py
index a3d8a0169..ada860ca5 100644
--- a/a11y_tests/test_course_enrollment_demographics_axs.py
+++ b/a11y_tests/test_course_enrollment_demographics_axs.py
@@ -1,5 +1,3 @@
-from __future__ import absolute_import
-
from bok_choy.promise import EmptyPromise
from bok_choy.web_app_test import WebAppTest
@@ -15,7 +13,7 @@ class CourseEnrollmentDemographicsAgeTests(CoursePageTestsMixin, WebAppTest):
"""
def setUp(self):
- super(CourseEnrollmentDemographicsAgeTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentDemographicsAgePage(self.browser)
def test_a11y(self):
diff --git a/acceptance_tests/__init__.py b/acceptance_tests/__init__.py
index 38232a097..7e9415c20 100644
--- a/acceptance_tests/__init__.py
+++ b/acceptance_tests/__init__.py
@@ -1,5 +1,3 @@
-
-
import locale
import os
@@ -7,7 +5,7 @@
def str2bool(s):
- return str(s).lower() in (u"yes", u"true", u"t", u"1")
+ return str(s).lower() in ("yes", "true", "t", "1")
# Dashboard settings
@@ -40,27 +38,27 @@ def str2bool(s):
if ENABLE_OAUTH_TESTS and not (LMS_HOSTNAME and LMS_USERNAME and LMS_PASSWORD):
raise Exception('LMS settings must be set in order to test OAuth.')
-TEST_COURSE_ID = os.environ.get('TEST_COURSE_ID', u'edX/DemoX/Demo_Course')
+TEST_COURSE_ID = os.environ.get('TEST_COURSE_ID', 'edX/DemoX/Demo_Course')
TEST_ASSIGNMENT_TYPE = os.environ.get('TEST_ASSIGNMENT_TYPE', 'Homework')
-TEST_ASSIGNMENT_ID = os.environ.get('TEST_ASSIGNMENT_ID', u'i4x://edX/DemoX/sequential/basic_questions')
+TEST_ASSIGNMENT_ID = os.environ.get('TEST_ASSIGNMENT_ID', 'i4x://edX/DemoX/sequential/basic_questions')
TEST_GRADED_PROBLEM_ID = os.environ.get('TEST_GRADED_PROBLEM_ID',
- u'i4x://edX/DemoX/problem/a0effb954cca4759994f1ac9e9434bf4')
+ 'i4x://edX/DemoX/problem/a0effb954cca4759994f1ac9e9434bf4')
TEST_GRADED_PROBLEM_PART_ID = os.environ.get('TEST_GRADED_PROBLEM_PART_ID',
- u'i4x-edX-DemoX-problem-a0effb954cca4759994f1ac9e9434bf4_2_1')
+ 'i4x-edX-DemoX-problem-a0effb954cca4759994f1ac9e9434bf4_2_1')
TEST_UNGRADED_SECTION_ID = os.environ.get('TEST_UNGRADED_SECTION_ID',
- u'i4x://edX/DemoX/chapter/interactive_demonstrations')
+ 'i4x://edX/DemoX/chapter/interactive_demonstrations')
TEST_UNGRADED_SUBSECTION_ID = os.environ.get('TEST_UNGRADED_SUBSECTION_ID',
- u'i4x://edX/DemoX/sequential/19a30717eff543078a5d94ae9d6c18a5')
+ 'i4x://edX/DemoX/sequential/19a30717eff543078a5d94ae9d6c18a5')
TEST_UNGRADED_PROBLEM_ID = os.environ.get('TEST_UNGRADED_PROBLEM_ID',
- u'i4x://edX/DemoX/problem/303034da25524878a2e66fb57c91cf85')
+ 'i4x://edX/DemoX/problem/303034da25524878a2e66fb57c91cf85')
TEST_UNGRADED_PROBLEM_PART_ID = os.environ.get('TEST_UNGRADED_PROBLEM_PART_ID',
- u'i4x-edX-DemoX-problem-303034da25524878a2e66fb57c91cf85_2_1')
+ 'i4x-edX-DemoX-problem-303034da25524878a2e66fb57c91cf85_2_1')
TEST_VIDEO_SECTION_ID = os.environ.get('TEST_VIDEO_SECTION_ID',
- u'i4x://edX/DemoX/chapter/interactive_demonstrations')
+ 'i4x://edX/DemoX/chapter/interactive_demonstrations')
TEST_VIDEO_SUBSECTION_ID = os.environ.get('TEST_VIDEO_SUBSECTION_ID',
- u'i4x://edX/DemoX/sequential/19a30717eff543078a5d94ae9d6c18a5')
+ 'i4x://edX/DemoX/sequential/19a30717eff543078a5d94ae9d6c18a5')
TEST_VIDEO_ID = os.environ.get('TEST_VIDEO_ID',
- u'i4x://edX/DemoX/video/7e9b434e6de3435ab99bd3fb25bde807')
+ 'i4x://edX/DemoX/video/7e9b434e6de3435ab99bd3fb25bde807')
DOC_BASE_URL = os.environ.get('DOC_BASE_URL', 'http://edx-insights.readthedocs.org/en/latest')
diff --git a/acceptance_tests/course_validation/__init__.py b/acceptance_tests/course_validation/__init__.py
index 8809c47ef..b1b2293c7 100644
--- a/acceptance_tests/course_validation/__init__.py
+++ b/acceptance_tests/course_validation/__init__.py
@@ -1,5 +1,3 @@
-
-
import os
from acceptance_tests import str2bool
diff --git a/acceptance_tests/course_validation/report_generators.py b/acceptance_tests/course_validation/report_generators.py
index 6ff5d6050..ac7a7bd9b 100644
--- a/acceptance_tests/course_validation/report_generators.py
+++ b/acceptance_tests/course_validation/report_generators.py
@@ -1,5 +1,3 @@
-
-
import datetime
import logging
import traceback
@@ -50,11 +48,11 @@ def get_http_status_and_load_time(self, url):
def build_course_path(self, path):
path = path.strip('/')
- return '/courses/{}/{}/'.format(self.course_id, path)
+ return f'/courses/{self.course_id}/{path}/'
def get_dashboard_url(self, path):
path = path.strip('/')
- return '{}/{}/'.format(DASHBOARD_SERVER_URL, path)
+ return f'{DASHBOARD_SERVER_URL}/{path}/'
def generate_report(self):
"""
@@ -283,7 +281,7 @@ class CoursePerformanceScreenshotReporter(CoursePerformanceReportGenerator):
REPORT_NAME = 'course_performance_screenshot'
def __init__(self, course_id, http_cookies=None):
- super(CoursePerformanceScreenshotReporter, self).__init__(course_id, http_cookies)
+ super().__init__(course_id, http_cookies)
self.driver = webdriver.Firefox()
def _take_screenshot(self, url_path):
@@ -310,9 +308,9 @@ def _login(self):
if BASIC_AUTH_CREDENTIALS:
username = BASIC_AUTH_CREDENTIALS[0]
password = BASIC_AUTH_CREDENTIALS[1]
- url = url.replace('://', '://{}:{}@'.format(username, password))
+ url = url.replace('://', f'://{username}:{password}@')
- self.driver.get('{}/login'.format(url))
+ self.driver.get(f'{url}/login')
self.driver.find_element_by_id('login-email').send_keys(LMS_USERNAME)
self.driver.find_element_by_id('login-password').send_keys(LMS_PASSWORD)
self.driver.find_element_by_css_selector('button.login-button').click()
diff --git a/acceptance_tests/course_validation/report_runner.py b/acceptance_tests/course_validation/report_runner.py
index b3d2e1212..c9ff9ea9c 100755
--- a/acceptance_tests/course_validation/report_runner.py
+++ b/acceptance_tests/course_validation/report_runner.py
@@ -20,7 +20,6 @@
"""
import datetime
-import io
import json
import logging
import time
@@ -64,7 +63,7 @@ def _setup_logging():
msg_format = '%(asctime)s - %(levelname)s - %(message)s'
logging.basicConfig(
- filename='{}-course_report.log'.format(TIMESTAMP),
+ filename=f'{TIMESTAMP}-course_report.log',
format=msg_format,
level=level)
@@ -126,7 +125,7 @@ def login(http_client):
if ENABLE_AUTO_AUTH:
logger.info('Logging into dashboard with auto auth...')
- response = http_client.get('{}/test/auto_auth/'.format(DASHBOARD_SERVER_URL))
+ response = http_client.get(f'{DASHBOARD_SERVER_URL}/test/auto_auth/')
if response.status_code == 200:
logger.info('Login succeeded.')
@@ -140,8 +139,8 @@ def login(http_client):
if BASIC_AUTH_CREDENTIALS:
http_client.auth = BASIC_AUTH_CREDENTIALS
- lms_login = '{}/login'.format(LMS_URL)
- lms_login_ajax = '{}/login_ajax'.format(LMS_URL)
+ lms_login = f'{LMS_URL}/login'
+ lms_login_ajax = f'{LMS_URL}/login_ajax'
# Make a call to the login page to get cookies (esp. CSRF token)
http_client.get(lms_login)
@@ -175,7 +174,7 @@ def get_courses():
filename = 'courses.json'
try:
- with io.open(filename, 'r', encoding='utf-8') as f:
+ with open(filename, 'r', encoding='utf-8') as f:
courses = json.load(f)
except Exception as e: # pylint: disable=broad-except
logger.warning('Failed to read courses from file: %s', e)
@@ -188,7 +187,7 @@ def get_courses():
courses = [course['id'] for course in courses]
courses.sort(key=lambda course: course.lower())
- with io.open(filename, 'w', encoding='utf-8') as f:
+ with open(filename, 'w', encoding='utf-8') as f:
f.write(str(json.dumps(courses, ensure_ascii=False)))
logger.info('Retrieved %s courses.', len(courses))
@@ -212,7 +211,7 @@ def main():
# Create the mappings
mappings_file = join(dirname(abspath(__file__)), 'mappings.json')
- with io.open(mappings_file, 'r', encoding='utf-8') as f:
+ with open(mappings_file, 'r', encoding='utf-8') as f:
mappings = json.load(f)
for doc_type, body in mappings.items():
diff --git a/acceptance_tests/mixins.py b/acceptance_tests/mixins.py
index 23f477f7e..a6538340c 100644
--- a/acceptance_tests/mixins.py
+++ b/acceptance_tests/mixins.py
@@ -1,5 +1,3 @@
-
-
import datetime
import locale
from unittest import skip
@@ -36,7 +34,7 @@ class AnalyticsApiClientMixin:
analytics_api_client = None
def setUp(self):
- super(AnalyticsApiClientMixin, self).setUp()
+ super().setUp()
api_url = API_SERVER_URL
auth_token = API_AUTH_TOKEN
@@ -47,7 +45,7 @@ class CourseApiMixin:
course_api_client = None
def setUp(self):
- super(CourseApiMixin, self).setUp()
+ super().setUp()
if ENABLE_COURSE_API:
self.course_api_client = CourseStructureApiClient(COURSE_API_URL, COURSE_API_KEY, 5)
@@ -120,7 +118,7 @@ def assertTable(self, table_selector, columns, download_selector=None):
# check the headings
self.assertTableColumnHeadingsEqual(table_selector, columns)
- rows = self.page.browser.find_elements_by_css_selector('{} tbody tr'.format(table_selector))
+ rows = self.page.browser.find_elements_by_css_selector(f'{table_selector} tbody tr')
self.assertGreater(len(rows), 0)
if download_selector is not None:
@@ -150,30 +148,30 @@ def _test_footer(self):
self.assertTrue(element.present)
def test_page(self):
- super(FooterMixin, self).test_page()
+ super().test_page()
self._test_footer()
class FooterLegalMixin(FooterMixin):
def _test_footer(self):
- super(FooterLegalMixin, self)._test_footer()
+ super()._test_footer()
# Verify the terms of service link is present
selector = self.footer_selector + " a[data-role=tos]"
element = self.page.q(css=selector)
self.assertTrue(element.present)
- self.assertEqual(element.text[0], u'Terms of Service')
+ self.assertEqual(element.text[0], 'Terms of Service')
# Verify the privacy policy link is present
selector = self.footer_selector + " a[data-role=privacy-policy]"
element = self.page.q(css=selector)
self.assertTrue(element.present)
- self.assertEqual(element.text[0], u'Privacy Policy')
+ self.assertEqual(element.text[0], 'Privacy Policy')
class FooterFeedbackMixin(FooterMixin):
def _test_footer(self):
- super(FooterFeedbackMixin, self)._test_footer()
+ super()._test_footer()
# check that we have an email
self.assertValidFeedbackLink(self.footer_selector + " a[class=feedback-email]")
@@ -238,7 +236,7 @@ def test_page(self):
class LoginMixin:
def setUp(self):
- super(LoginMixin, self).setUp()
+ super().setUp()
self.lms_login_page = LMSLoginPage(self.browser)
def login(self):
@@ -248,7 +246,7 @@ def login(self):
self.login_with_lms()
def login_with_auto_auth(self):
- url = '{}/test/auto_auth/'.format(DASHBOARD_SERVER_URL)
+ url = f'{DASHBOARD_SERVER_URL}/test/auto_auth/'
self.browser.get(url)
def login_with_lms(self):
@@ -261,7 +259,7 @@ def login_with_lms(self):
class LogoutMixin:
def logout(self):
- url = '{}/logout/'.format(DASHBOARD_SERVER_URL)
+ url = f'{DASHBOARD_SERVER_URL}/logout/'
self.browser.get(url)
@@ -270,7 +268,7 @@ class ContextSensitiveHelpMixin:
@property
def help_url(self):
- return '{0}/{1}'.format(DOC_BASE_URL, self.help_path)
+ return f'{DOC_BASE_URL}/{self.help_path}'
def test_page(self):
# Validate the help link
@@ -292,7 +290,7 @@ def _test_soapbox_messages(self):
self.assertTrue(SOAPBOX_SINGLE_PAGE_MESSAGE in element.text)
def test_page(self):
- super(SoapboxMessagesMixin, self).test_page()
+ super().test_page()
self._test_soapbox_messages()
@@ -330,7 +328,7 @@ def assertSummaryPointValueEquals(self, data_selector, value):
if len(value) > MAX_SUMMARY_POINT_VALUE_LENGTH:
value = value[:(MAX_SUMMARY_POINT_VALUE_LENGTH - 1)] + '…'
- element = self.page.q(css="div[{0}] .summary-point-number".format(data_selector))
+ element = self.page.q(css=f"div[{data_selector}] .summary-point-number")
self.assertTrue(element.present)
self.assertEqual(element.text[0], value)
@@ -342,7 +340,7 @@ def assertSummaryTooltipEquals(self, data_selector, tip_text):
data_selector (String): Attribute selector (ex. data-stat-type=current_enrollment)
tip_text (String): expected text
"""
- help_selector = "div[{0}] .summary-point-help".format(data_selector)
+ help_selector = f"div[{data_selector}] .summary-point-help"
element = self.page.q(css=help_selector)
self.assertTrue(element.present)
@@ -371,7 +369,7 @@ class CoursePageTestsMixin(AnalyticsApiClientMixin, FooterLegalMixin, FooterFeed
page = None
def setUp(self):
- super(CoursePageTestsMixin, self).setUp()
+ super().setUp()
self.api_date_format = self.analytics_api_client.DATE_FORMAT
self.api_datetime_format = self.analytics_api_client.DATETIME_FORMAT
@@ -391,7 +389,7 @@ def format_last_updated_date_and_time(self, d):
def build_display_percentage(self, count, total, zero_percent_default='0.0%'):
if total and count:
percent = count / float(total) * 100.0
- return '{:.1f}%'.format(percent) if percent >= 1.0 else '< 1%'
+ return f'{percent:.1f}%' if percent >= 1.0 else '< 1%'
return zero_percent_default
def _get_data_update_message(self):
@@ -415,7 +413,7 @@ def test_page(self):
pass, execution of this parent method will leave the browser on the page being tested.
:return:
"""
- super(CoursePageTestsMixin, self).test_page()
+ super().test_page()
self._test_data_update_message()
self._test_course_home_nav()
@@ -430,7 +428,7 @@ class CourseDemographicsPageTestsMixin(CoursePageTestsMixin):
demographic_data = None
def test_page(self):
- super(CourseDemographicsPageTestsMixin, self).test_page()
+ super().test_page()
self._test_data_information_message()
self._test_chart()
self._test_table()
@@ -443,7 +441,7 @@ def _test_chart(self):
def _test_table(self):
self.assertTable(self.table_section_selector, self.table_columns, self.table_download_selector)
- rows = self.page.browser.find_elements_by_css_selector('{} tbody tr'.format(self.table_section_selector))
+ rows = self.page.browser.find_elements_by_css_selector(f'{self.table_section_selector} tbody tr')
self.assertGreater(len(rows), 0)
sum_count = 0.0
if self.demographic_data and 'count' in self.demographic_data[0]:
diff --git a/acceptance_tests/pages.py b/acceptance_tests/pages.py
index 6e5d2b896..13e94be73 100644
--- a/acceptance_tests/pages.py
+++ b/acceptance_tests/pages.py
@@ -36,10 +36,10 @@ def url(self):
return self.page_url
def __init__(self, browser, path=None):
- super(DashboardPage, self).__init__(browser)
+ super().__init__(browser)
path = path or self.path
self.server_url = DASHBOARD_SERVER_URL
- self.page_url = '{0}/{1}'.format(self.server_url, path)
+ self.page_url = f'{self.server_url}/{path}'
class LandingPage(DashboardPage):
@@ -53,10 +53,10 @@ class CoursePage(DashboardPage):
def __init__(self, browser, course_id=None):
# Create the path
self.course_id = course_id or TEST_COURSE_ID
- path = 'courses/{}'.format(self.course_id)
+ path = f'courses/{self.course_id}'
# Call the constructor and setup the URL
- super(CoursePage, self).__init__(browser, path)
+ super().__init__(browser, path)
def is_browser_on_page(self):
return self.browser.current_url == self.page_url
@@ -64,20 +64,20 @@ def is_browser_on_page(self):
class CourseHomePage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseHomePage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/'
def is_browser_on_page(self):
- return super(CourseHomePage, self).is_browser_on_page() and self.browser.title.startswith('Course Home')
+ return super().is_browser_on_page() and self.browser.title.startswith('Course Home')
class CourseEnrollmentActivityPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseEnrollmentActivityPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/enrollment/activity/'
def is_browser_on_page(self):
- return super(CourseEnrollmentActivityPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Enrollment Activity' in self.browser.title
@@ -87,9 +87,9 @@ def url(self):
protocol = 'https' if LMS_SSL_ENABLED else 'http'
if BASIC_AUTH_USERNAME and BASIC_AUTH_PASSWORD:
- return '{0}://{1}:{2}@{3}/login'.format(protocol, BASIC_AUTH_USERNAME, BASIC_AUTH_PASSWORD, LMS_HOSTNAME)
+ return f'{protocol}://{BASIC_AUTH_USERNAME}:{BASIC_AUTH_PASSWORD}@{LMS_HOSTNAME}/login'
- return '{0}://{1}/login'.format(protocol, LMS_HOSTNAME)
+ return f'{protocol}://{LMS_HOSTNAME}/login'
def is_browser_on_page(self):
return self.browser.title.startswith('Log into')
@@ -117,12 +117,12 @@ class CourseEnrollmentDemographicsPage(CoursePage):
demographic = None
def __init__(self, browser, course_id=None):
- super(CourseEnrollmentDemographicsPage, self).__init__(browser, course_id)
- self.page_url += '/enrollment/demographics/{0}/'.format(self.demographic)
+ super().__init__(browser, course_id)
+ self.page_url += f'/enrollment/demographics/{self.demographic}/'
def is_browser_on_page(self):
- return super(CourseEnrollmentDemographicsPage, self).is_browser_on_page() and \
- 'Enrollment Demographics by {0}'.format(self.demographic.title()) in self.browser.title
+ return super().is_browser_on_page() and \
+ f'Enrollment Demographics by {self.demographic.title()}' in self.browser.title
class CourseEnrollmentDemographicsAgePage(CourseEnrollmentDemographicsPage):
@@ -139,61 +139,61 @@ class CourseEnrollmentDemographicsEducationPage(CourseEnrollmentDemographicsPage
class CourseEnrollmentGeographyPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseEnrollmentGeographyPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/enrollment/geography/'
def is_browser_on_page(self):
- return super(CourseEnrollmentGeographyPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Enrollment Geography' in self.browser.title
class CourseEngagementContentPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseEngagementContentPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/engagement/content/'
def is_browser_on_page(self):
- return super(CourseEngagementContentPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Engagement Content' in self.browser.title
class CourseEngagementVideosContentPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseEngagementVideosContentPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/engagement/videos/'
def is_browser_on_page(self):
- return super(CourseEngagementVideosContentPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Engagement Videos' in self.browser.title
class CourseEngagementVideoSectionPage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None):
- super(CourseEngagementVideoSectionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_VIDEO_SECTION_ID
- self.page_url += '/engagement/videos/sections/{}/'.format(self.section_id)
+ self.page_url += f'/engagement/videos/sections/{self.section_id}/'
def is_browser_on_page(self):
- return super(CourseEngagementVideoSectionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Engagement Videos' in self.browser.title
class CourseEngagementVideoSubsectionPage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None, subsection_id=None):
- super(CourseEngagementVideoSubsectionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_VIDEO_SECTION_ID
self.subsection_id = subsection_id or TEST_VIDEO_SUBSECTION_ID
self.page_url += '/engagement/videos/sections/{}/subsections/{}/'.format(
self.section_id, self.subsection_id)
def is_browser_on_page(self):
- return super(CourseEngagementVideoSubsectionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Engagement Videos' in self.browser.title
class CourseEngagementVideoTimelinePage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None, subsection_id=None, video_id=None):
- super(CourseEngagementVideoTimelinePage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_VIDEO_SECTION_ID
self.subsection_id = subsection_id or TEST_VIDEO_SUBSECTION_ID
self.video_id = video_id or TEST_VIDEO_ID
@@ -201,7 +201,7 @@ def __init__(self, browser, course_id=None, section_id=None, subsection_id=None,
self.section_id, self.subsection_id, self.video_id)
def is_browser_on_page(self):
- return super(CourseEngagementVideoTimelinePage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Engagement Videos' in self.browser.title
@@ -214,41 +214,41 @@ def is_browser_on_page(self):
class CoursePerformanceUngradedContentPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CoursePerformanceUngradedContentPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/performance/ungraded_content/'
def is_browser_on_page(self):
- return super(CoursePerformanceUngradedContentPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Ungraded Problems' in self.browser.title
class CoursePerformanceUngradedSectionPage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None):
- super(CoursePerformanceUngradedSectionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_UNGRADED_SECTION_ID
- self.page_url += '/performance/ungraded_content/sections/{}/'.format(self.section_id)
+ self.page_url += f'/performance/ungraded_content/sections/{self.section_id}/'
def is_browser_on_page(self):
- return super(CoursePerformanceUngradedSectionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Ungraded Problems' in self.browser.title
class CoursePerformanceUngradedSubsectionPage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None, subsection_id=None):
- super(CoursePerformanceUngradedSubsectionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_UNGRADED_SECTION_ID
self.subsection_id = subsection_id or TEST_UNGRADED_SUBSECTION_ID
self.page_url += '/performance/ungraded_content/sections/{}/subsections/{}/'.format(
self.section_id, self.subsection_id)
def is_browser_on_page(self):
- return super(CoursePerformanceUngradedSubsectionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Ungraded Problems' in self.browser.title
class CoursePerformanceUngradedAnswerDistributionPage(CoursePage):
def __init__(self, browser, course_id=None, section_id=None, subsection_id=None, problem_id=None, part_id=None):
- super(CoursePerformanceUngradedAnswerDistributionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.section_id = section_id or TEST_UNGRADED_SECTION_ID
self.subsection_id = subsection_id or TEST_UNGRADED_SUBSECTION_ID
self.problem_id = problem_id or TEST_UNGRADED_PROBLEM_ID
@@ -258,45 +258,45 @@ def __init__(self, browser, course_id=None, section_id=None, subsection_id=None,
self.problem_id, self.part_id)
def is_browser_on_page(self):
- return super(CoursePerformanceUngradedAnswerDistributionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
self.browser.title.startswith('Performance: Problem Submissions')
class CoursePerformanceGradedContentPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CoursePerformanceGradedContentPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/performance/graded_content/'
def is_browser_on_page(self):
- return super(CoursePerformanceGradedContentPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Graded Content' in self.browser.title
class CoursePerformanceGradedContentByTypePage(CoursePage):
def __init__(self, browser, course_id=None, assignment_type=None):
- super(CoursePerformanceGradedContentByTypePage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.assignment_type = assignment_type or TEST_ASSIGNMENT_TYPE
- self.page_url += '/performance/graded_content/{}/'.format(self.assignment_type)
+ self.page_url += f'/performance/graded_content/{self.assignment_type}/'
def is_browser_on_page(self):
- return super(CoursePerformanceGradedContentByTypePage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
self.assignment_type in self.browser.title
class CoursePerformanceAssignmentPage(CoursePage):
def __init__(self, browser, course_id=None, assignment_id=None):
- super(CoursePerformanceAssignmentPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.assignment_id = assignment_id or TEST_ASSIGNMENT_ID
- self.page_url += '/performance/graded_content/assignments/{}/'.format(self.assignment_id)
+ self.page_url += f'/performance/graded_content/assignments/{self.assignment_id}/'
def is_browser_on_page(self):
- return super(CoursePerformanceAssignmentPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
'Graded Content' in self.browser.title
class CoursePerformanceAnswerDistributionPage(CoursePage):
def __init__(self, browser, course_id=None, assignment_id=None, problem_id=None, part_id=None):
- super(CoursePerformanceAnswerDistributionPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.assignment_id = assignment_id or TEST_ASSIGNMENT_ID
self.problem_id = problem_id or TEST_GRADED_PROBLEM_ID
self.part_id = part_id or TEST_GRADED_PROBLEM_PART_ID
@@ -304,17 +304,17 @@ def __init__(self, browser, course_id=None, assignment_id=None, problem_id=None,
self.assignment_id, self.problem_id, self.part_id)
def is_browser_on_page(self):
- return super(CoursePerformanceAnswerDistributionPage, self).is_browser_on_page() and \
+ return super().is_browser_on_page() and \
self.browser.title.startswith('Performance: Problem Submissions')
class CourseLearnersPage(CoursePage):
def __init__(self, browser, course_id=None):
- super(CourseLearnersPage, self).__init__(browser, course_id)
+ super().__init__(browser, course_id)
self.page_url += '/learners/'
def is_browser_on_page(self):
- return super(CourseLearnersPage, self).is_browser_on_page() \
+ return super().is_browser_on_page() \
and self.browser.title.startswith('Learners')
@@ -323,8 +323,8 @@ class ErrorPage(DashboardPage):
error_title = None
def __init__(self, browser):
- self.path = self.path or '{}/'.format(self.error_code)
- super(ErrorPage, self).__init__(browser)
+ self.path = self.path or f'{self.error_code}/'
+ super().__init__(browser)
def is_browser_on_page(self):
element = self.q(css='.error-title')
@@ -333,19 +333,19 @@ def is_browser_on_page(self):
class ServerErrorPage(ErrorPage):
error_code = 500
- error_title = u'An Error Occurred'
+ error_title = 'An Error Occurred'
class NotFoundErrorPage(ErrorPage):
error_code = 404
- error_title = u'Page Not Found'
+ error_title = 'Page Not Found'
class AccessDeniedErrorPage(ErrorPage):
error_code = 403
- error_title = u'Access Denied'
+ error_title = 'Access Denied'
class ServiceUnavailableErrorPage(ErrorPage):
error_code = 503
- error_title = u"We're having trouble loading this page. Please try again in a minute."
+ error_title = "We're having trouble loading this page. Please try again in a minute."
diff --git a/acceptance_tests/test_auth.py b/acceptance_tests/test_auth.py
index 5ef83c9bb..90c163fbb 100644
--- a/acceptance_tests/test_auth.py
+++ b/acceptance_tests/test_auth.py
@@ -1,5 +1,3 @@
-
-
from unittest import skipUnless
from bok_choy.web_app_test import WebAppTest
@@ -15,7 +13,7 @@ def setUp(self):
"""
Instantiate the page objects.
"""
- super(OAuth2FlowTests, self).setUp()
+ super().setUp()
self.insights_login_page = LoginPage(self.browser)
diff --git a/acceptance_tests/test_course_detail.py b/acceptance_tests/test_course_detail.py
index 2ba980148..38a8ff930 100644
--- a/acceptance_tests/test_course_detail.py
+++ b/acceptance_tests/test_course_detail.py
@@ -1,5 +1,3 @@
-
-
from bok_choy.web_app_test import WebAppTest
from acceptance_tests import ENABLE_COURSE_API
@@ -12,12 +10,12 @@
# pylint: disable=abstract-method
class CourseHomeTests(CoursePageTestsMixin, WebAppTest):
def setUp(self):
- super(CourseHomeTests, self).setUp()
+ super().setUp()
self.page = CourseHomePage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
def test_page(self):
- super(CourseHomeTests, self).test_page()
+ super().test_page()
self._test_table()
def _test_data_update_message(self):
@@ -29,7 +27,7 @@ def _view_to_href(self, view):
Generates a URL path from the specified view name.
"""
return '/' + view.replace('_', '/') \
- .replace('courses:', 'courses/{}/'.format(self.page.course_id)) \
+ .replace('courses:', f'courses/{self.page.course_id}/') \
.replace(':', '/') + '/'
def _test_table(self):
@@ -134,7 +132,7 @@ def _test_table(self):
self.assertEqual(title.text, row['title'])
expected = self._view_to_href(row['view'])
actual = title.find_element_by_css_selector('a').get_attribute('href')
- self.assertTrue(actual.endswith(expected), '{} should end with {}'.format(actual, expected))
+ self.assertTrue(actual.endswith(expected), f'{actual} should end with {expected}')
# Check the breadcrumbs
breadcrumbs = element.find_element_by_css_selector('.breadcrumbs')
diff --git a/acceptance_tests/test_course_engagement.py b/acceptance_tests/test_course_engagement.py
index 168b7435e..ca7e1c096 100644
--- a/acceptance_tests/test_course_engagement.py
+++ b/acceptance_tests/test_course_engagement.py
@@ -1,5 +1,3 @@
-
-
import datetime
from unittest import skipUnless
@@ -30,7 +28,7 @@ class CourseEngagementPageTestsMixin(CoursePageTestsMixin):
chart_selector = None
def test_page(self):
- super(CourseEngagementPageTestsMixin, self).test_page()
+ super().test_page()
self._test_chart()
self._test_table()
@@ -54,12 +52,12 @@ def setUp(self):
"""
Instantiate the page object.
"""
- super(CourseEngagementContentTests, self).setUp()
+ super().setUp()
self.page = CourseEngagementContentPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
def test_page(self):
- super(CourseEngagementContentTests, self).test_page()
+ super().test_page()
self._test_engagement_metrics()
def _get_data_update_message(self):
@@ -76,13 +74,13 @@ def _test_engagement_metrics(self):
# Verify the activity values
activity_types = [at.ANY, at.ATTEMPTED_PROBLEM, at.PLAYED_VIDEO]
expected_tooltips = {
- at.ANY: u'Learners who visited at least one page in the course content.',
- at.ATTEMPTED_PROBLEM: u'Learners who submitted an answer for a standard problem. '
- u'Not all problem types are included.',
- at.PLAYED_VIDEO: u'Learners who played one or more videos.'
+ at.ANY: 'Learners who visited at least one page in the course content.',
+ at.ATTEMPTED_PROBLEM: 'Learners who submitted an answer for a standard problem. '
+ 'Not all problem types are included.',
+ at.PLAYED_VIDEO: 'Learners who played one or more videos.'
}
for activity_type in activity_types:
- data_selector = 'data-activity-type={0}'.format(activity_type)
+ data_selector = f'data-activity-type={activity_type}'
self.assertSummaryPointValueEquals(data_selector, self.format_number(recent_activity[activity_type]))
self.assertSummaryTooltipEquals(data_selector, expected_tooltips[activity_type])
@@ -98,10 +96,10 @@ def _test_table(self):
table_selector = 'div[data-role=engagement-table] table'
- headings = [u'Week Ending', u'Active Learners', u'Watched a Video', u'Tried a Problem']
+ headings = ['Week Ending', 'Active Learners', 'Watched a Video', 'Tried a Problem']
if ENABLE_FORUM_POSTS:
- headings.append(u'Participated in Discussions')
- headings.append(u'Percent of Current Learners')
+ headings.append('Participated in Discussions')
+ headings.append('Percent of Current Learners')
self.assertTableColumnHeadingsEqual(table_selector, headings)
@@ -134,13 +132,13 @@ def _test_table(self):
class CourseEngagementVideoMixin(CourseEngagementPageTestsMixin):
help_path = 'engagement/Engagement_Video.html'
chart_selector = '#chart-view'
- expected_table_heading = u'Video Views'
+ expected_table_heading = 'Video Views'
expected_heading = None
expected_tooltip = None
expected_table_columns = None
def test_page(self):
- super(CourseEngagementVideoMixin, self).test_page()
+ super().test_page()
self._test_heading_question()
def _get_data_update_message(self):
@@ -160,7 +158,7 @@ def _test_table(self):
self.assertTableColumnHeadingsEqual('div[data-role="data-table"]', self.expected_table_columns)
def _test_chart(self):
- super(CourseEngagementVideoMixin, self)._test_chart()
+ super()._test_chart()
container_selector = '.analytics-chart-container'
element = self.page.q(css=container_selector + ' i')
self.assertEqual(element[0].get_attribute('data-original-title'), self.expected_tooltip)
@@ -172,63 +170,63 @@ def _test_heading_question(self):
@skipUnless(ENABLE_COURSE_API, 'Course API must be enabled to test the video pages.')
class CourseEngagementVideoContentTests(CourseEngagementVideoMixin, WebAppTest):
- expected_heading = u'How did learners interact with course videos?'
- expected_tooltip = u'Each bar shows the average number of complete and incomplete views for videos in that ' \
- u'section. Click on bars with low totals or a high incomplete rate to drill down and ' \
- u'understand why.'
- expected_table_columns = [u'Order', u'Section Name', u'Videos', u'Average Complete Views',
- u'Average Incomplete Views', u'Completion Percentage']
+ expected_heading = 'How did learners interact with course videos?'
+ expected_tooltip = 'Each bar shows the average number of complete and incomplete views for videos in that ' \
+ 'section. Click on bars with low totals or a high incomplete rate to drill down and ' \
+ 'understand why.'
+ expected_table_columns = ['Order', 'Section Name', 'Videos', 'Average Complete Views',
+ 'Average Incomplete Views', 'Completion Percentage']
def setUp(self):
- super(CourseEngagementVideoContentTests, self).setUp()
+ super().setUp()
self.page = CourseEngagementVideosContentPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@skipUnless(ENABLE_COURSE_API, 'Course API must be enabled to test the video pages.')
class CourseEngagementVideoSectionTests(CourseEngagementVideoMixin, WebAppTest):
- expected_heading = u'How did learners interact with videos in this section?'
- expected_tooltip = u'Each bar shows the average number of complete and incomplete views for videos in that ' \
- u'subsection. Click on bars with low totals or a high incomplete rate to drill down and ' \
- u'understand why.'
- expected_table_columns = [u'Order', u'Subsection Name', u'Videos', u'Average Complete Views',
- u'Average Incomplete Views', u'Completion Percentage']
+ expected_heading = 'How did learners interact with videos in this section?'
+ expected_tooltip = 'Each bar shows the average number of complete and incomplete views for videos in that ' \
+ 'subsection. Click on bars with low totals or a high incomplete rate to drill down and ' \
+ 'understand why.'
+ expected_table_columns = ['Order', 'Subsection Name', 'Videos', 'Average Complete Views',
+ 'Average Incomplete Views', 'Completion Percentage']
def setUp(self):
- super(CourseEngagementVideoSectionTests, self).setUp()
+ super().setUp()
self.page = CourseEngagementVideoSectionPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@skipUnless(ENABLE_COURSE_API, 'Course API must be enabled to test the video pages.')
class CourseEngagementVideoSubsectionTests(CourseEngagementVideoMixin, WebAppTest):
- expected_heading = u'How did learners interact with videos in this subsection?'
- expected_tooltip = u'Each bar shows the counts of complete and incomplete views for that video. ' \
- u'Click to understand where learners drop off and which parts they replay.'
- expected_table_columns = [u'Order', u'Video Name', u'Complete Views', u'Incomplete Views',
- u'Completion Percentage']
+ expected_heading = 'How did learners interact with videos in this subsection?'
+ expected_tooltip = 'Each bar shows the counts of complete and incomplete views for that video. ' \
+ 'Click to understand where learners drop off and which parts they replay.'
+ expected_table_columns = ['Order', 'Video Name', 'Complete Views', 'Incomplete Views',
+ 'Completion Percentage']
def setUp(self):
- super(CourseEngagementVideoSubsectionTests, self).setUp()
+ super().setUp()
self.page = CourseEngagementVideoSubsectionPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@skipUnless(ENABLE_COURSE_API, 'Course API must be enabled to test the video pages.')
class CourseEngagementVideoTimelineTests(CourseEngagementVideoMixin, WebAppTest):
- expected_heading = u'What were the viewing patterns for this video?'
- expected_tooltip = u'The number of learners who watched each segment of the video, and the ' \
- u'number of replays for each segment.'
- expected_table_columns = [u'Time', u'Unique Viewers', u'Replays']
- expected_table_heading = u'Total Video Views'
+ expected_heading = 'What were the viewing patterns for this video?'
+ expected_tooltip = 'The number of learners who watched each segment of the video, and the ' \
+ 'number of replays for each segment.'
+ expected_table_columns = ['Time', 'Unique Viewers', 'Replays']
+ expected_table_heading = 'Total Video Views'
def setUp(self):
- super(CourseEngagementVideoTimelineTests, self).setUp()
+ super().setUp()
self.page = CourseEngagementVideoTimelinePage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
def test_page(self):
- super(CourseEngagementVideoTimelineTests, self).test_page()
+ super().test_page()
self._test_metrics()
if ENABLE_VIDEO_PREVIEW:
self._test_video_preview()
@@ -272,6 +270,6 @@ def _test_metrics(self):
]
for expected in expected_metrics:
- data_selector = 'data-type={0}'.format(expected['data_type'])
+ data_selector = 'data-type={}'.format(expected['data_type'])
self.assertSummaryPointValueEquals(data_selector, expected['metric_value'])
self.assertSummaryTooltipEquals(data_selector, expected['tooltip'])
diff --git a/acceptance_tests/test_course_enrollment.py b/acceptance_tests/test_course_enrollment.py
index 091ca02f5..572cc480d 100644
--- a/acceptance_tests/test_course_enrollment.py
+++ b/acceptance_tests/test_course_enrollment.py
@@ -1,5 +1,3 @@
-
-
import datetime
from collections import OrderedDict
@@ -23,7 +21,7 @@ class CourseEnrollmentActivityTests(CoursePageTestsMixin, WebAppTest):
help_path = 'enrollment/Enrollment_Activity.html'
def setUp(self):
- super(CourseEnrollmentActivityTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentActivityPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@@ -36,7 +34,7 @@ def get_enrollment_data(self):
return self.course.enrollment('mode', start_date=None, end_date=end_date_string)
def test_page(self):
- super(CourseEnrollmentActivityTests, self).test_page()
+ super().test_page()
self._test_enrollment_metrics_and_graph()
self._test_enrollment_trend_table()
@@ -68,13 +66,13 @@ def _test_enrollment_metrics_and_graph(self):
enrollment = enrollment_data[-1]['count']
# Verify the current enrollment metric tile.
- tooltip = u'Learners currently enrolled in the course.'
+ tooltip = 'Learners currently enrolled in the course.'
self.assertMetricTileValid('current_enrollment', enrollment, tooltip)
# Verify the total enrollment change metric tile.
i = 7
enrollment = enrollment - enrollment_data[-(i + 1)]['count']
- tooltip = u'Net difference in current enrollment in the last week.'
+ tooltip = 'Net difference in current enrollment in the last week.'
self.assertMetricTileValid('enrollment_change_last_%s_days' % i, enrollment, tooltip)
valid_modes = self._get_valid_enrollment_modes(enrollment_data)
@@ -82,7 +80,7 @@ def _test_enrollment_metrics_and_graph(self):
if enrollment_modes.VERIFIED in valid_modes:
# Verify the verified enrollment metric tile.
verified_enrollment = enrollment_data[-1][enrollment_modes.VERIFIED]
- tooltip = u'Number of currently enrolled learners pursuing a verified certificate of achievement.'
+ tooltip = 'Number of currently enrolled learners pursuing a verified certificate of achievement.'
self.assertMetricTileValid('verified_enrollment', verified_enrollment, tooltip)
# Verify *something* rendered where the graph should be. We cannot easily verify what rendered
@@ -133,14 +131,14 @@ class CourseEnrollmentGeographyTests(CoursePageTestsMixin, WebAppTest):
help_path = 'enrollment/Enrollment_Geography.html'
def setUp(self):
- super(CourseEnrollmentGeographyTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentGeographyPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
self.enrollment_data = sorted(self.course.enrollment(demographics.LOCATION),
key=lambda item: item['count'], reverse=True)
def test_page(self):
- super(CourseEnrollmentGeographyTests, self).test_page()
+ super().test_page()
self._test_enrollment_country_map()
self._test_enrollment_country_table()
self._test_metrics()
@@ -178,7 +176,7 @@ def _test_enrollment_country_table(self):
self.assertTable(table_section_selector, ['Country or Region', 'Percent', 'Current Enrollment'],
'a[data-role=enrollment-location-csv]')
- rows = self.page.browser.find_elements_by_css_selector('{} tbody tr'.format(table_section_selector))
+ rows = self.page.browser.find_elements_by_css_selector(f'{table_section_selector} tbody tr')
sum_count = float(sum([datum['count'] for datum in self.enrollment_data]))
for i, row in enumerate(rows):
@@ -189,10 +187,10 @@ def _test_enrollment_country_table(self):
country_name = enrollment['country']['name']
if country_name == UNKNOWN_COUNTRY_CODE:
- country_name = u'Unknown Country'
+ country_name = 'Unknown Country'
# FIXME: because django-countries is different between dashboard and api
elif country_name == 'United States':
- country_name = u'United States of America'
+ country_name = 'United States of America'
expected = [country_name, expected_percent_display, self.format_number(enrollment['count'])]
actual = [columns[0].text, columns[1].text, columns[2].text]
@@ -209,5 +207,5 @@ def _test_metrics(self):
country = enrollment_data[i]['country']['name']
# FIXME: because django-countries is different between dashboard and api
if country == 'United States':
- country = u'United Sta...'
- self.assertSummaryPointValueEquals('data-stat-type=top-country-{0}'.format((i + 1)), country)
+ country = 'United Sta...'
+ self.assertSummaryPointValueEquals('data-stat-type=top-country-{}'.format(i + 1), country)
diff --git a/acceptance_tests/test_course_enrollment_demographics.py b/acceptance_tests/test_course_enrollment_demographics.py
index 3669b46b7..21a69870a 100644
--- a/acceptance_tests/test_course_enrollment_demographics.py
+++ b/acceptance_tests/test_course_enrollment_demographics.py
@@ -1,5 +1,3 @@
-
-
import datetime
from analyticsclient.constants import demographics
@@ -24,7 +22,7 @@ class CourseEnrollmentDemographicsAgeTests(CourseDemographicsPageTestsMixin, Web
table_columns = ['Age', 'Number of Learners', 'Percent of Total']
def setUp(self):
- super(CourseEnrollmentDemographicsAgeTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentDemographicsAgePage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@@ -35,7 +33,7 @@ def setUp(self):
self.demographic_data_without_none = [datum for datum in self.demographic_data if datum['birth_year']]
def test_page(self):
- super(CourseEnrollmentDemographicsAgeTests, self).test_page()
+ super().test_page()
self._test_metrics()
def _calculate_median_age(self, current_year):
@@ -121,7 +119,7 @@ class CourseEnrollmentDemographicsGenderTests(CourseDemographicsPageTestsMixin,
table_columns = ['Date', 'Current Enrollment', 'Female', 'Male', 'Other', 'Not Reported']
def setUp(self):
- super(CourseEnrollmentDemographicsGenderTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentDemographicsGenderPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
@@ -171,14 +169,14 @@ class CourseEnrollmentDemographicsEducationTests(CourseDemographicsPageTestsMixi
table_columns = ['Educational Background', 'Number of Learners']
def setUp(self):
- super(CourseEnrollmentDemographicsEducationTests, self).setUp()
+ super().setUp()
self.page = CourseEnrollmentDemographicsEducationPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
self.demographic_data = sorted(self.course.enrollment(self.demographic_type),
key=lambda item: item['count'], reverse=True)
def test_page(self):
- super(CourseEnrollmentDemographicsEducationTests, self).test_page()
+ super().test_page()
self._test_metrics()
def _test_metrics(self):
diff --git a/acceptance_tests/test_course_index.py b/acceptance_tests/test_course_index.py
index 1aa6bbde7..552f3f0b1 100644
--- a/acceptance_tests/test_course_index.py
+++ b/acceptance_tests/test_course_index.py
@@ -1,5 +1,3 @@
-
-
import requests
from bok_choy.promise import EmptyPromise
from bok_choy.web_app_test import WebAppTest
@@ -23,13 +21,13 @@ class CourseIndexTests(AnalyticsApiClientMixin, AnalyticsDashboardWebAppTestMixi
test_skip_link_url = False
def setUp(self):
- super(CourseIndexTests, self).setUp()
+ super().setUp()
self.page = CourseIndexPage(self.browser)
self.maxDiff = None
self.course_summaries = self.analytics_api_client.course_summaries()
def test_page(self):
- super(CourseIndexTests, self).test_page()
+ super().test_page()
self._test_course_list()
self._test_search()
self._test_clear_input()
@@ -70,7 +68,7 @@ def _test_course_list(self):
course_links = self.page.q(css='.course-list .course-name-cell a').attrs('href')
for link, course_id in zip(course_links, course_ids):
- self.assertTrue(link.endswith(u'/courses/{}'.format(course_id.text)))
+ self.assertTrue(link.endswith(f'/courses/{course_id.text}'))
def _test_search(self):
"""
@@ -297,7 +295,7 @@ def _test_download_csv(self):
# Steal the cookies from the logged-in firefox browser and use them in a python-initiated request
kwargs = dict()
- session_id = [{i['name']: i['value']} for i in self.browser.get_cookies() if i['name'] == u'sessionid']
+ session_id = [{i['name']: i['value']} for i in self.browser.get_cookies() if i['name'] == 'sessionid']
if session_id:
kwargs.update({
'cookies': session_id[0]
@@ -320,14 +318,14 @@ def _test_summary_metrics(self):
count_change_i_days = course_summaries[0]['count_change_%s_days' % i]
verified_enrollment = course_summaries[0]['enrollment_modes']['verified']['count']
- tooltip = u'Current enrollments across all of your courses.'
+ tooltip = 'Current enrollments across all of your courses.'
self.assertMetricTileValid('current_enrollment', current_enrollment, tooltip)
- tooltip = u'Total enrollments across all of your courses.'
+ tooltip = 'Total enrollments across all of your courses.'
self.assertMetricTileValid('total_enrollment', total_enrollment, tooltip)
- tooltip = u'Total change in enrollment last week across all of your courses.'
+ tooltip = 'Total change in enrollment last week across all of your courses.'
self.assertMetricTileValid('enrollment_change_%s_days' % i, count_change_i_days, tooltip)
- tooltip = u'Verified enrollments across all of your courses.'
+ tooltip = 'Verified enrollments across all of your courses.'
self.assertMetricTileValid('verified_enrollment', verified_enrollment, tooltip)
diff --git a/acceptance_tests/test_course_learners.py b/acceptance_tests/test_course_learners.py
index f577cf3c3..61385ccd1 100644
--- a/acceptance_tests/test_course_learners.py
+++ b/acceptance_tests/test_course_learners.py
@@ -1,5 +1,3 @@
-
-
from unittest import skipUnless
from bok_choy.web_app_test import WebAppTest
@@ -15,7 +13,7 @@ class CourseLearnersTests(CoursePageTestsMixin, WebAppTest):
help_path = 'learners/Learner_Activity.html'
def setUp(self):
- super(CourseLearnersTests, self).setUp()
+ super().setUp()
self.page = CourseLearnersPage(self.browser)
def _test_data_update_message(self):
diff --git a/acceptance_tests/test_course_performance.py b/acceptance_tests/test_course_performance.py
index b422bc987..bf7632789 100644
--- a/acceptance_tests/test_course_performance.py
+++ b/acceptance_tests/test_course_performance.py
@@ -1,5 +1,3 @@
-
-
import datetime
from unittest import skipUnless
@@ -28,7 +26,7 @@ class CoursePerformancePageTestsMixin(CoursePageTestsMixin):
table_selector = 'div[data-role="data-table"]'
def test_page(self):
- super(CoursePerformancePageTestsMixin, self).test_page()
+ super().test_page()
self._test_chart()
self._test_table()
@@ -83,7 +81,7 @@ def _get_sections(self):
def _find_child_block(self, blocks, child_id):
for block in blocks:
- if block[u'id'] == child_id:
+ if block['id'] == child_id:
return block
return None
@@ -145,7 +143,7 @@ def get_expected_row(self, index, block):
class CoursePerformanceAveragedTableMixin(CoursePerformancePageTestsMixin):
def get_expected_row(self, index, block):
- row = super(CoursePerformanceAveragedTableMixin, self).get_expected_row(index, block)
+ row = super().get_expected_row(index, block)
num_modules_denominator = float(block.get('num_modules', 1))
row += [
str(self._format_number_or_hyphen(block.get('num_modules', 0))),
@@ -173,7 +171,7 @@ def get_expected_row(self, index, block):
class CoursePerformanceModuleTableMixin(CoursePerformancePageTestsMixin):
def get_expected_row(self, index, block):
- row = super(CoursePerformanceModuleTableMixin, self).get_expected_row(index, block)
+ row = super().get_expected_row(index, block)
row += [
str(self._format_number_or_hyphen(block['correct_submissions'])),
str(self._format_number_or_hyphen(
@@ -205,12 +203,12 @@ def _get_grading_policy(self):
for item in policy:
weight = item['weight']
- item['weight_as_percentage'] = u'{:.0f}%'.format(weight * 100)
+ item['weight_as_percentage'] = '{:.0f}%'.format(weight * 100)
return policy
def setUp(self):
- super(CoursePerformanceGradedContentTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceGradedContentPage(self.browser)
self.grading_policy = self._get_grading_policy()
@@ -226,7 +224,7 @@ def _test_chart(self):
# Verify the URL to view the assignments is correct.
actual = element.find_element_by_css_selector('a').get_attribute('href')
- expected = u'{}{}/'.format(self.page.page_url, assignment_type)
+ expected = f'{self.page.page_url}{assignment_type}/'
self.assertEqual(actual, expected)
# Verify the displayed weight
@@ -254,7 +252,7 @@ class CoursePerformanceGradedContentByTypeTests(CoursePerformanceAveragedTableMi
"""
def setUp(self):
- super(CoursePerformanceGradedContentByTypeTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceGradedContentByTypePage(self.browser)
self.assignment_type = self.page.assignment_type
self.course = self.analytics_api_client.courses(self.page.course_id)
@@ -262,9 +260,9 @@ def setUp(self):
def _test_table(self):
self.assertTableColumnHeadingsEqual(self.table_selector,
- [u'Order', u'Assignment Name', u'Problems',
- u'Average Correct', u'Average Incorrect',
- u'Average Submissions Per Problem', u'Percentage Correct'])
+ ['Order', 'Assignment Name', 'Problems',
+ 'Average Correct', 'Average Incorrect',
+ 'Average Submissions Per Problem', 'Percentage Correct'])
self.assertBlockRows(self.assignments)
@@ -277,13 +275,13 @@ class CoursePerformanceAssignmentTests(CoursePerformanceModuleTableMixin, WebApp
def _get_assignment(self):
assignments = self._get_assignments()
for assignment in assignments:
- if assignment[u'id'] == self.assignment_id:
+ if assignment['id'] == self.assignment_id:
return assignment
raise AttributeError('Assignment not found!')
def setUp(self):
- super(CoursePerformanceAssignmentTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceAssignmentPage(self.browser)
self.assignment_id = self.page.assignment_id
self.course = self.analytics_api_client.courses(self.page.course_id)
@@ -292,7 +290,7 @@ def setUp(self):
def _test_table(self):
# Check the column headings
self.assertTableColumnHeadingsEqual(self.table_selector, [
- u'Order', u'Problem Name', u'Correct', u'Incorrect', u'Total', u'Percentage Correct'])
+ 'Order', 'Problem Name', 'Correct', 'Incorrect', 'Total', 'Percentage Correct'])
self.assertBlockRows(self.assignment['children'])
@@ -303,7 +301,7 @@ class CoursePerformanceAnswerDistributionMixin(CoursePerformancePageTestsMixin):
answer_distribution = None
def setUp(self):
- super(CoursePerformanceAnswerDistributionMixin, self).setUp()
+ super().setUp()
self.page = self.get_page()
self.course = self.analytics_api_client.courses(self.page.course_id)
self.module = self.analytics_api_client.modules(self.page.course_id, self.page.problem_id)
@@ -315,13 +313,13 @@ def get_page(self):
raise NotImplementedError
def test_page(self):
- super(CoursePerformanceAnswerDistributionMixin, self).test_page()
+ super().test_page()
self._test_heading_question()
self._test_problem_description()
def _test_heading_question(self):
element = self.page.q(css='.section-heading')
- self.assertEqual(element.text[0], u'How did learners answer this problem?')
+ self.assertEqual(element.text[0], 'How did learners answer this problem?')
def _test_problem_description(self):
section_selector = '.module-description'
@@ -353,7 +351,7 @@ def _test_table(self):
self.assertTable(table_section_selector, ['Answer', 'Correct', 'Submission Count'],
'a[data-role=performance-csv]')
- rows = self.page.browser.find_elements_by_css_selector('{} tbody tr'.format(table_section_selector))
+ rows = self.page.browser.find_elements_by_css_selector(f'{table_section_selector} tbody tr')
value_field = 'answer_value'
@@ -365,10 +363,10 @@ def _test_table(self):
for col in columns:
actual.append(col.text)
- expected = [answer[value_field] if answer[value_field] else u'(empty)']
- correct = u'-'
+ expected = [answer[value_field] if answer[value_field] else '(empty)']
+ correct = '-'
if answer['correct']:
- correct = u'Correct'
+ correct = 'Correct'
expected.append(correct)
expected.append(self.format_number(answer['last_response_count']))
@@ -394,16 +392,16 @@ def get_page(self):
class CoursePerformanceUngradedContentTests(CoursePerformanceAveragedTableMixin, WebAppTest):
def setUp(self):
- super(CoursePerformanceUngradedContentTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceUngradedContentPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
self.sections = self._get_sections()
def _test_table(self):
self.assertTableColumnHeadingsEqual(self.table_selector,
- [u'Order', u'Section Name', u'Problems', u'Average Correct',
- u'Average Incorrect', u'Average Submissions Per Problem',
- u'Percentage Correct'])
+ ['Order', 'Section Name', 'Problems', 'Average Correct',
+ 'Average Incorrect', 'Average Submissions Per Problem',
+ 'Percentage Correct'])
self.assertBlockRows(self.sections)
@@ -411,16 +409,16 @@ def _test_table(self):
class CoursePerformanceUngradedSectionTests(CoursePerformanceAveragedTableMixin, WebAppTest):
def setUp(self):
- super(CoursePerformanceUngradedSectionTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceUngradedSectionPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
self.section = self._find_child_block(self._get_sections(), self.page.section_id)
def _test_table(self):
self.assertTableColumnHeadingsEqual(self.table_selector,
- [u'Order', u'Subsection Name', u'Problems', u'Average Correct',
- u'Average Incorrect', u'Average Submissions Per Problem',
- u'Percentage Correct'])
+ ['Order', 'Subsection Name', 'Problems', 'Average Correct',
+ 'Average Incorrect', 'Average Submissions Per Problem',
+ 'Percentage Correct'])
self.assertBlockRows(self.section['children'])
@@ -428,13 +426,13 @@ def _test_table(self):
class CoursePerformanceUngradedSubsectionTests(CoursePerformanceModuleTableMixin, WebAppTest):
def setUp(self):
- super(CoursePerformanceUngradedSubsectionTests, self).setUp()
+ super().setUp()
self.page = CoursePerformanceUngradedSubsectionPage(self.browser)
self.course = self.analytics_api_client.courses(self.page.course_id)
subsections = self._find_child_block(self._get_sections(), self.page.section_id)['children']
self.problems = self._find_child_block(subsections, self.page.subsection_id)['children']
def _test_table(self):
- self.assertTableColumnHeadingsEqual(self.table_selector, [u'Order', u'Problem Name', u'Correct',
- u'Incorrect', u'Total', u'Percentage Correct'])
+ self.assertTableColumnHeadingsEqual(self.table_selector, ['Order', 'Problem Name', 'Correct',
+ 'Incorrect', 'Total', 'Percentage Correct'])
self.assertBlockRows(self.problems)
diff --git a/acceptance_tests/test_error_pages.py b/acceptance_tests/test_error_pages.py
index adb602814..c61aee0ca 100644
--- a/acceptance_tests/test_error_pages.py
+++ b/acceptance_tests/test_error_pages.py
@@ -1,5 +1,3 @@
-
-
from unittest import skipUnless
from bok_choy.web_app_test import WebAppTest
@@ -30,11 +28,11 @@ def test_valid_pages(self):
page.visit()
# Check the title
- expected = u'{0} | {1} {2}'.format(page.error_title, PLATFORM_NAME, APPLICATION_NAME)
+ expected = f'{page.error_title} | {PLATFORM_NAME} {APPLICATION_NAME}'
self.assertEqual(expected, self.browser.title)
# Check the support link
element = page.q(css='a[data-role=support-email]')
self.assertTrue(element.present)
href = element.attrs('href')[0]
- self.assertEqual(href, 'mailto:{}'.format(SUPPORT_EMAIL))
+ self.assertEqual(href, f'mailto:{SUPPORT_EMAIL}')
diff --git a/acceptance_tests/test_landing.py b/acceptance_tests/test_landing.py
index 3990a549a..015e71d86 100644
--- a/acceptance_tests/test_landing.py
+++ b/acceptance_tests/test_landing.py
@@ -1,5 +1,3 @@
-
-
from bok_choy.web_app_test import WebAppTest
from acceptance_tests import (
@@ -21,11 +19,11 @@
class LandingTests(PageTestMixin, LoginMixin, LogoutMixin, FooterLegalMixin, WebAppTest):
def setUp(self):
- super(LandingTests, self).setUp()
+ super().setUp()
self.page = LandingPage(self.browser)
def test_page(self):
- super(LandingTests, self).test_page()
+ super().test_page()
# landing page will not be viewable by logged in users
self.assertFalse(self.page.is_browser_on_page())
@@ -77,7 +75,7 @@ def _test_audience_messages(self):
self.assertTrue(action_link_elements.present)
self.assertEqual(len(action_link_elements), num_actions)
- expected_links = [OPEN_SOURCE_URL, RESEARCH_URL, 'mailto:{}'.format(SUPPORT_EMAIL)]
+ expected_links = [OPEN_SOURCE_URL, RESEARCH_URL, f'mailto:{SUPPORT_EMAIL}']
for i in range(num_actions):
self.assertEqual(header_elements[i].text, expected_headers[i])
self.assertEqual(action_link_elements.attrs('href')[i], expected_links[i])
diff --git a/acceptance_tests/test_status.py b/acceptance_tests/test_status.py
index 79a2bda59..3b9a631d6 100644
--- a/acceptance_tests/test_status.py
+++ b/acceptance_tests/test_status.py
@@ -1,5 +1,3 @@
-
-
from unittest import TestCase
import requests
@@ -8,10 +6,10 @@
class StatusTests(TestCase):
- POSITIVE_STATUS = u'OK'
+ POSITIVE_STATUS = 'OK'
def test_health(self):
- response = requests.get('{}/health'.format(DASHBOARD_SERVER_URL))
+ response = requests.get(f'{DASHBOARD_SERVER_URL}/health')
self.assertEqual(response.status_code, 200)
@@ -24,6 +22,6 @@ def test_health(self):
self.assertDictEqual(response.json(), expected_status)
def test_status(self):
- response = requests.get('{}/status'.format(DASHBOARD_SERVER_URL))
+ response = requests.get(f'{DASHBOARD_SERVER_URL}/status')
self.assertEqual(response.status_code, 200)
diff --git a/analytics_dashboard/help/middleware.py b/analytics_dashboard/help/middleware.py
index ea98e84c5..427a727ef 100644
--- a/analytics_dashboard/help/middleware.py
+++ b/analytics_dashboard/help/middleware.py
@@ -1,5 +1,3 @@
-
-
from django.utils.deprecation import MiddlewareMixin
from rest_framework.response import Response
diff --git a/analytics_dashboard/help/tests.py b/analytics_dashboard/help/tests.py
index 4aa99d85d..b0b7035cd 100644
--- a/analytics_dashboard/help/tests.py
+++ b/analytics_dashboard/help/tests.py
@@ -1,5 +1,3 @@
-
-
from django import http
from django.template.response import TemplateResponse
from django.test import TestCase
@@ -12,7 +10,7 @@
def build_doc_url(path):
- return '{0}/{1}'.format(DOC_BASE_URL, path)
+ return f'{DOC_BASE_URL}/{path}'
DOC_INDEX = build_doc_url('index.html')
diff --git a/analytics_dashboard/help/utils.py b/analytics_dashboard/help/utils.py
index 1b9c9c407..bc8cbb432 100644
--- a/analytics_dashboard/help/utils.py
+++ b/analytics_dashboard/help/utils.py
@@ -1,5 +1,3 @@
-
-
import logging
import configparser
diff --git a/analytics_dashboard/help/views.py b/analytics_dashboard/help/views.py
index cf4c6c269..d6e23adcd 100644
--- a/analytics_dashboard/help/views.py
+++ b/analytics_dashboard/help/views.py
@@ -1,5 +1,3 @@
-
-
from analytics_dashboard.help import HELP_CONTEXT_TOKEN_NAME
@@ -11,6 +9,6 @@ class ContextSensitiveHelpMixin:
help_token = None
def get_context_data(self, **kwargs):
- context = super(ContextSensitiveHelpMixin, self).get_context_data(**kwargs)
+ context = super().get_context_data(**kwargs)
context[HELP_CONTEXT_TOKEN_NAME] = self.help_token
return context
diff --git a/analytics_dashboard/learner_analytics_api/urls.py b/analytics_dashboard/learner_analytics_api/urls.py
index 57a87b963..7eea709a1 100644
--- a/analytics_dashboard/learner_analytics_api/urls.py
+++ b/analytics_dashboard/learner_analytics_api/urls.py
@@ -1,5 +1,3 @@
-
-
from django.conf.urls import include, url
app_name = 'learner_analytics_api'
diff --git a/analytics_dashboard/learner_analytics_api/v0/clients.py b/analytics_dashboard/learner_analytics_api/v0/clients.py
index 33b626d00..6faf21e8a 100644
--- a/analytics_dashboard/learner_analytics_api/v0/clients.py
+++ b/analytics_dashboard/learner_analytics_api/v0/clients.py
@@ -1,5 +1,3 @@
-
-
import requests
from django.conf import settings
from slumber import API, Resource, exceptions, serialize
@@ -11,7 +9,7 @@ def __init__(self, token):
self.token = token
def __call__(self, r):
- r.headers['Authorization'] = 'Token {}'.format(self.token)
+ r.headers['Authorization'] = f'Token {self.token}'
return r
@@ -40,7 +38,7 @@ def _request(self, *args, **kwargs):
# Doesn't hide 400s and 500s, however timeouts will still
# raise a requests.exceptions.ConnectTimeout.
try:
- response = super(LearnerApiResource, self)._request(*args, **kwargs)
+ response = super()._request(*args, **kwargs)
except exceptions.SlumberHttpBaseException as e:
response = e.response
return response
@@ -65,7 +63,7 @@ def __init__(self, timeout=5, serializer_type='json'):
TextSerializer(),
]
)
- super(LearnerAPIClient, self).__init__(
+ super().__init__(
settings.DATA_API_URL,
session=session,
auth=TokenAuth(settings.DATA_API_AUTH_TOKEN),
diff --git a/analytics_dashboard/learner_analytics_api/v0/permissions.py b/analytics_dashboard/learner_analytics_api/v0/permissions.py
index 82e15b3e9..2ead0767d 100644
--- a/analytics_dashboard/learner_analytics_api/v0/permissions.py
+++ b/analytics_dashboard/learner_analytics_api/v0/permissions.py
@@ -1,5 +1,3 @@
-
-
import logging
from rest_framework.permissions import BasePermission
diff --git a/analytics_dashboard/learner_analytics_api/v0/tests/test_views.py b/analytics_dashboard/learner_analytics_api/v0/tests/test_views.py
index 77cfd3b6d..3d3691bb0 100644
--- a/analytics_dashboard/learner_analytics_api/v0/tests/test_views.py
+++ b/analytics_dashboard/learner_analytics_api/v0/tests/test_views.py
@@ -1,5 +1,3 @@
-
-
import json
import unittest.mock as mock
diff --git a/analytics_dashboard/learner_analytics_api/v0/urls.py b/analytics_dashboard/learner_analytics_api/v0/urls.py
index 2b0c3d1c3..890e1af72 100644
--- a/analytics_dashboard/learner_analytics_api/v0/urls.py
+++ b/analytics_dashboard/learner_analytics_api/v0/urls.py
@@ -1,5 +1,3 @@
-
-
from django.conf import settings
from django.conf.urls import url
@@ -9,13 +7,13 @@
app_name = 'v0'
urlpatterns = [
- url(r'^learners/{}/$'.format(USERNAME_PATTERN), views.LearnerDetailView.as_view(), name='LearnerDetail'),
+ url(fr'^learners/{USERNAME_PATTERN}/$', views.LearnerDetailView.as_view(), name='LearnerDetail'),
url(r'^learners/$', views.LearnerListView.as_view(), name='LearnerList'),
url(r'^learners.csv$', views.LearnerListCSV.as_view(), name='LearnerListCSV'),
- url(r'^engagement_timelines/{}/$'.format(USERNAME_PATTERN),
+ url(fr'^engagement_timelines/{USERNAME_PATTERN}/$',
views.EngagementTimelinesView.as_view(),
name='EngagementTimeline'),
- url(r'^course_learner_metadata/{}/$'.format(settings.COURSE_ID_PATTERN),
+ url(fr'^course_learner_metadata/{settings.COURSE_ID_PATTERN}/$',
views.CourseLearnerMetadataView.as_view(),
name='CourseMetadata'),
]
diff --git a/analytics_dashboard/learner_analytics_api/v0/views.py b/analytics_dashboard/learner_analytics_api/v0/views.py
index e1b08cdac..d1a3ee9e2 100644
--- a/analytics_dashboard/learner_analytics_api/v0/views.py
+++ b/analytics_dashboard/learner_analytics_api/v0/views.py
@@ -1,5 +1,3 @@
-
-
from requests.exceptions import ConnectTimeout
from rest_framework.exceptions import PermissionDenied
from rest_framework.generics import RetrieveAPIView
@@ -23,7 +21,7 @@ class BaseLearnerApiView(RetrieveAPIView):
include_headers = False
def __init__(self, *args, **kwargs):
- super(BaseLearnerApiView, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self.client = LearnerAPIClient(serializer_type=self.serializer_type)
def get_queryset(self):
@@ -74,7 +72,7 @@ def handle_exception(self, exc):
data={'developer_message': 'Learner Analytics API timed out.', 'error_code': 'analytics_api_timeout'},
status=504
)
- return super(BaseLearnerApiView, self).handle_exception(exc)
+ return super().handle_exception(exc)
class DownloadLearnerApiViewMixin:
@@ -94,7 +92,7 @@ def get_api_response(self, request, **kwargs):
"""
request.META['Accept'] = self.content_type
request.accepted_renderer = TextRenderer()
- return super(DownloadLearnerApiViewMixin, self).get_api_response(request, **kwargs)
+ return super().get_api_response(request, **kwargs)
class NotFoundLearnerApiViewMixin:
@@ -115,7 +113,7 @@ def handle_exception(self, exc):
data={'developer_message': self.not_found_developer_message, 'error_code': self.not_found_error_code},
status=404
)
- return super(NotFoundLearnerApiViewMixin, self).handle_exception(exc)
+ return super().handle_exception(exc)
class LearnerDetailView(NotFoundLearnerApiViewMixin, BaseLearnerApiView):
@@ -127,7 +125,7 @@ class LearnerDetailView(NotFoundLearnerApiViewMixin, BaseLearnerApiView):
@property
def not_found_developer_message(self):
message = 'Learner {} not found'.format(self.kwargs.get('username', ''))
- message += 'for course {}.'.format(self.course_id) if self.course_id else '.'
+ message += f'for course {self.course_id}.' if self.course_id else '.'
return message
def get_api_response(self, request, username, **kwargs):
@@ -159,7 +157,7 @@ class EngagementTimelinesView(NotFoundLearnerApiViewMixin, BaseLearnerApiView):
@property
def not_found_developer_message(self):
message = 'Learner {} engagement timeline not found'.format(self.kwargs.get('username', ''))
- message += 'for course {}.'.format(self.course_id) if self.course_id else '.'
+ message += f'for course {self.course_id}.' if self.course_id else '.'
return message
def get_api_response(self, request, username, **kwargs):
diff --git a/analytics_dashboard/settings/base.py b/analytics_dashboard/settings/base.py
index dd72db99b..3853e224a 100644
--- a/analytics_dashboard/settings/base.py
+++ b/analytics_dashboard/settings/base.py
@@ -1,5 +1,3 @@
-
-
import os
from os.path import abspath, basename, dirname, join, normpath
from sys import path
@@ -311,7 +309,7 @@
########## DOCUMENTATION LINKS -- These values should be overridden for production deployments.
DOCUMENTATION_LOAD_ERROR_URL = 'http://127.0.0.1/en/latest/Reference.html#error-conditions'
# evaluated again at the end of production setting after DOCUMENTATION_LOAD_ERROR_URL has been set
-DOCUMENTATION_LOAD_ERROR_MESSAGE = 'Read more.'.format(error_documentation_link=DOCUMENTATION_LOAD_ERROR_URL)
+DOCUMENTATION_LOAD_ERROR_MESSAGE = f'Read more.'
########## END DOCUMENTATION LINKS
@@ -386,7 +384,7 @@
# The application and platform display names to be used in templates, emails, etc.
PLATFORM_NAME = 'edx'
APPLICATION_NAME = 'Insights'
-FULL_APPLICATION_NAME = '{0} {1}'.format(PLATFORM_NAME, APPLICATION_NAME)
+FULL_APPLICATION_NAME = f'{PLATFORM_NAME} {APPLICATION_NAME}'
########## DOCS/HELP CONFIGURATION
diff --git a/analytics_dashboard/settings/dev.py b/analytics_dashboard/settings/dev.py
index c05b8acc3..a30a0d575 100644
--- a/analytics_dashboard/settings/dev.py
+++ b/analytics_dashboard/settings/dev.py
@@ -50,7 +50,7 @@
########## BRANDING
PLATFORM_NAME = 'Open edX'
APPLICATION_NAME = 'Insights'
-FULL_APPLICATION_NAME = '{0} {1}'.format(PLATFORM_NAME, APPLICATION_NAME)
+FULL_APPLICATION_NAME = f'{PLATFORM_NAME} {APPLICATION_NAME}'
########## END BRANDING
diff --git a/analytics_dashboard/settings/production.py b/analytics_dashboard/settings/production.py
index c7f1e80be..a196c1d69 100644
--- a/analytics_dashboard/settings/production.py
+++ b/analytics_dashboard/settings/production.py
@@ -25,7 +25,7 @@
DATABASES['default'][override] = value
# Re-declare the full application name in case the components have been overridden.
-FULL_APPLICATION_NAME = u'{0} {1}'.format(PLATFORM_NAME, APPLICATION_NAME)
+FULL_APPLICATION_NAME = f'{PLATFORM_NAME} {APPLICATION_NAME}'
# Depends on DOCUMENTATION_LOAD_ERROR_URL, so evaluate at the end
DOCUMENTATION_LOAD_ERROR_MESSAGE = 'This data may not be available for your course. ' \
diff --git a/analytics_dashboard/settings/test.py b/analytics_dashboard/settings/test.py
index 02fa80f5a..d326d126c 100644
--- a/analytics_dashboard/settings/test.py
+++ b/analytics_dashboard/settings/test.py
@@ -1,5 +1,3 @@
-
-
from analytics_dashboard.settings.base import *
from analytics_dashboard.settings.logger import get_logger_config
diff --git a/analytics_dashboard/settings/yaml_config.py b/analytics_dashboard/settings/yaml_config.py
index 564292323..18dad9e3b 100644
--- a/analytics_dashboard/settings/yaml_config.py
+++ b/analytics_dashboard/settings/yaml_config.py
@@ -1,5 +1,3 @@
-
-
from os import environ
import yaml
diff --git a/common/clients.py b/common/clients.py
index b505249e6..2da994dab 100644
--- a/common/clients.py
+++ b/common/clients.py
@@ -1,5 +1,3 @@
-
-
import logging
from edx_rest_api_client.client import EdxRestApiClient
@@ -19,7 +17,7 @@ class CourseStructureApiClient(EdxRestApiClient):
DATETIME_FORMAT = "%Y-%m-%dT%H:%M:%SZ"
def __init__(self, url, access_token, timeout):
- super(CourseStructureApiClient, self).__init__(url, jwt=access_token, timeout=timeout)
+ super().__init__(url, jwt=access_token, timeout=timeout)
@property
def all_courses(self):
diff --git a/common/course_structure.py b/common/course_structure.py
index a58352d75..ff29d8e8b 100644
--- a/common/course_structure.py
+++ b/common/course_structure.py
@@ -1,5 +1,3 @@
-
-
class CourseStructure:
@staticmethod
def _filter_children(blocks, key, require_format=False, **kwargs):
@@ -15,9 +13,9 @@ def _filter_children(blocks, key, require_format=False, **kwargs):
"""
block = blocks[key]
- block_type = kwargs.pop(u'block_type', None)
+ block_type = kwargs.pop('block_type', None)
if block_type:
- kwargs[u'type'] = block_type
+ kwargs['type'] = block_type
matched = True
for name, value in kwargs.items():
@@ -27,14 +25,14 @@ def _filter_children(blocks, key, require_format=False, **kwargs):
if matched:
if require_format:
- if u'format' in block and block[u'format']:
+ if 'format' in block and block['format']:
return [block]
else:
return [block]
children = []
- if u'children' in block:
- for child in block[u'children']:
+ if 'children' in block:
+ for child in block['children']:
children += CourseStructure._filter_children(blocks, child, require_format=require_format, **kwargs)
return children
@@ -45,8 +43,8 @@ def course_structure_to_assignments(structure, graded=None, assignment_type=None
Returns the assignments and nested problems from the given course structure.
"""
- blocks = structure[u'blocks']
- root = blocks[structure[u'root']]
+ blocks = structure['blocks']
+ root = blocks[structure['root']]
# Break down the course structure into assignments and nested problems, returning only the data
# we absolutely need.
@@ -57,13 +55,13 @@ def course_structure_to_assignments(structure, graded=None, assignment_type=None
}
if assignment_type:
- kwargs[u'format'] = assignment_type
+ kwargs['format'] = assignment_type
- filtered = CourseStructure._filter_children(blocks, root[u'id'], require_format=True, **kwargs)
+ filtered = CourseStructure._filter_children(blocks, root['id'], require_format=True, **kwargs)
for assignment in filtered:
- filtered_children = CourseStructure._filter_children(blocks, assignment[u'id'], graded=graded,
- block_type=u'problem', require_format=False)
+ filtered_children = CourseStructure._filter_children(blocks, assignment['id'], graded=graded,
+ block_type='problem', require_format=False)
problems = []
for problem in filtered_children:
problems.append({
@@ -87,10 +85,10 @@ def course_structure_to_sections(structure, child_block_type, graded=None):
within 'children' attributes.
"""
- blocks = structure[u'blocks']
- root = blocks[structure[u'root']]
- sections = CourseStructure._build_sections(blocks, root[u'id'],
- graded, [u'chapter', u'sequential', str(child_block_type)])
+ blocks = structure['blocks']
+ root = blocks[structure['root']]
+ sections = CourseStructure._build_sections(blocks, root['id'],
+ graded, ['chapter', 'sequential', str(child_block_type)])
return sections
@staticmethod
@@ -110,7 +108,7 @@ def _build_sections(blocks, section_id, graded, block_types):
**filter_kwargs)
for section in structure_sections:
- children = CourseStructure._build_sections(blocks, section[u'id'], graded, block_types)
+ children = CourseStructure._build_sections(blocks, section['id'], graded, block_types)
sections.append({
'id': section['id'],
'name': section['display_name'],
diff --git a/common/tests/course_fixtures.py b/common/tests/course_fixtures.py
index 82f609f69..580a16a1e 100644
--- a/common/tests/course_fixtures.py
+++ b/common/tests/course_fixtures.py
@@ -1,4 +1,3 @@
-
import uuid
@@ -79,7 +78,7 @@ def id(self):
class CourseFixture(CourseStructureAPIFixtureMixin):
"""Represents a course as returned by the Course Structure API."""
def __init__(self, *args, **kwargs):
- super(CourseFixture, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self._type = 'course'
self.org = kwargs.get('org', 'test_org')
self.course = kwargs.get('course', 'test_course')
@@ -101,7 +100,7 @@ class ChapterFixture(CourseStructureAPIFixtureMixin):
"""Represents a chapter as returned by the Course Structure API."""
def __init__(self, *args, **kwargs):
- super(ChapterFixture, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self._type = 'chapter'
@@ -109,7 +108,7 @@ class SequentialFixture(CourseStructureAPIFixtureMixin):
"""Represents a sequential as returned by the Course Structure API."""
def __init__(self, *args, **kwargs):
- super(SequentialFixture, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self.graded = kwargs.get('graded', False)
self._assignment_type = kwargs.get('assignment_type')
self._type = 'sequential'
@@ -119,7 +118,7 @@ class VerticalFixture(CourseStructureAPIFixtureMixin):
"""Represents a vertical as returned by the Course Structure API."""
def __init__(self, *args, **kwargs):
- super(VerticalFixture, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self._type = 'vertical'
@@ -127,5 +126,5 @@ class VideoFixture(CourseStructureAPIFixtureMixin):
"""Represents a video as returned by the Course Structure API."""
def __init__(self, *args, **kwargs):
- super(VideoFixture, self).__init__(*args, **kwargs)
+ super().__init__(*args, **kwargs)
self._type = 'video'
diff --git a/common/tests/factories.py b/common/tests/factories.py
index dff6396f6..937301a21 100644
--- a/common/tests/factories.py
+++ b/common/tests/factories.py
@@ -1,5 +1,3 @@
-
-
import copy
import uuid
@@ -74,7 +72,7 @@ def _generate_subsection_children(self, assignment_type, display_name, problem_i
""" Overwrite if you want other subsection types (e.g. videos) """
problem = self._generate_block('problem',
assignment_type,
- '{} Problem {}'.format(display_name, problem_index),
+ f'{display_name} Problem {problem_index}',
graded)
self._structure['blocks'][problem['id']] = problem
return problem
@@ -102,7 +100,7 @@ def _generate_structure(self):
assignment_type = gp['assignment_type']
for assignment_index in range(1, count + 1):
- display_name = '{} {}'.format(assignment_type, assignment_index)
+ display_name = f'{assignment_type} {assignment_index}'
graded_children = []
# Generate the graded children
diff --git a/common/tests/test_course_structure.py b/common/tests/test_course_structure.py
index 4c230a332..6dd4c1153 100644
--- a/common/tests/test_course_structure.py
+++ b/common/tests/test_course_structure.py
@@ -1,5 +1,3 @@
-
-
from unittest import TestCase
from common.course_structure import CourseStructure
diff --git a/docs/en_us/dashboard/source/conf.py b/docs/en_us/dashboard/source/conf.py
index 0b13ba035..5b1615d6e 100644
--- a/docs/en_us/dashboard/source/conf.py
+++ b/docs/en_us/dashboard/source/conf.py
@@ -1,4 +1,3 @@
-# -*- coding: utf-8 -*-
#
import datetime