Commit 1d4d81c2 by Diana Huang

Make the launch callback polling interval variable.

parent 14d6164c
......@@ -23,6 +23,9 @@ from edx_proctoring.api import (
from edx_proctoring.backends import get_backend_provider
from edx_proctoring.exceptions import ProctoredBaseException
from edx_proctoring.models import ProctoredExamStudentAttemptStatus
from edx_proctoring.utils import get_time_remaining_for_attempt
from edx_proctoring import constants
log = logging.getLogger(__name__)
......@@ -154,12 +157,17 @@ class AttemptStatus(APIView):
)
update_exam_attempt(attempt['id'], last_poll_timestamp=timestamp, last_poll_ipaddr=ip_address)
time_remaining_seconds = get_time_remaining_for_attempt(attempt)
polling_interval = constants.DEFAULT_CLIENT_POLLING_INTERVAL
if time_remaining_seconds < constants.EXAM_CONCLUDING_INTERVAL:
polling_interval = constants.REDUCED_CLIENT_POLLING_INTERVAL
return Response(
data={
# IMPORTANT: Don't add more information to this as it is an
# unauthenticated endpoint
'status': attempt['status'],
'polling_interval': polling_interval,
},
status=200
)
......@@ -46,7 +46,7 @@ REQUIRE_FAILURE_SECOND_REVIEWS = (
SOFTWARE_SECURE_CLIENT_TIMEOUT = (
settings.PROCTORING_SETTINGS['SOFTWARE_SECURE_CLIENT_TIMEOUT'] if
'SOFTWARE_SECURE_CLIENT_TIMEOUT' in settings.PROCTORING_SETTINGS
else getattr(settings, 'SOFTWARE_SECURE_CLIENT_TIMEOUT', 30)
else getattr(settings, 'SOFTWARE_SECURE_CLIENT_TIMEOUT', 60)
)
SOFTWARE_SECURE_SHUT_DOWN_GRACEPERIOD = (
......@@ -55,4 +55,23 @@ SOFTWARE_SECURE_SHUT_DOWN_GRACEPERIOD = (
else getattr(settings, 'SOFTWARE_SECURE_SHUT_DOWN_GRACEPERIOD', 10)
)
DEFAULT_CLIENT_POLLING_INTERVAL = (
settings.PROCTORING_SETTINGS['DEFAULT_CLIENT_POLLING_INTERVAL'] if
'DEFAULT_CLIENT_POLLING_INTERVAL' in settings.PROCTORING_SETTINGS
else getattr(settings, 'DEFAULT_CLIENT_POLLING_INTERVAL', 30)
)
REDUCED_CLIENT_POLLING_INTERVAL = (
settings.PROCTORING_SETTINGS['REDUCED_CLIENT_POLLING_INTERVAL'] if
'REDUCED_CLIENT_POLLING_INTERVAL' in settings.PROCTORING_SETTINGS
else getattr(settings, 'REDUCED_CLIENT_POLLING_INTERVAL', 10)
)
EXAM_CONCLUDING_INTERVAL = (
settings.PROCTORING_SETTINGS['EXAM_CONCLUDING_INTERVAL'] if
'EXAM_CONCLUDING_INTERVAL' in settings.PROCTORING_SETTINGS
else getattr(settings, 'EXAM_CONCLUDING_INTERVAL', 180)
)
MINIMUM_TIME = datetime.datetime.fromtimestamp(0)
......@@ -190,10 +190,7 @@
var _poll_interval = null;
$(document).ready(function() {
_poll_interval = setInterval(
poll_exam_status,
5000
);
poll_exam_status();
});
function poll_exam_status() {
......@@ -206,6 +203,9 @@
// NOTE: This is per the API documentation from SoftwareSecure
window.external.quitApplication();
}
clearInterval(_poll_interval);
// The polling interval is returned in seconds, so we need to multiply by 1000.
_poll_interval = setInterval(poll_exam_status, parseInt(data.polling_interval) * 1000);
});
}
......
......@@ -36,6 +36,7 @@ from .utils import (
LoggedInTestCase
)
from edx_proctoring import constants
from edx_proctoring.urls import urlpatterns
from edx_proctoring.backends.tests.test_review_payload import TEST_REVIEW_PAYLOAD
from edx_proctoring.backends.tests.test_software_secure import mock_response_content
......@@ -836,6 +837,29 @@ class TestStudentProctoredExamAttempt(LoggedInTestCase):
)
self.assertEqual(response.status_code, 200)
@patch('edx_proctoring.callbacks.get_time_remaining_for_attempt')
def test_attempt_status_poll_interval(self, time_remaining_mock):
"""
Test that the poll interval is correct depending on the amount of time remaining.
"""
exam_attempt = self._create_exam_attempt()
# test the polling callback point
polling_status_endpoint = reverse(
'edx_proctoring.anonymous.proctoring_poll_status',
args=[exam_attempt.attempt_code]
)
# When the exam has not reached the concluding interval.
time_remaining_mock.return_value = constants.EXAM_CONCLUDING_INTERVAL + 5
response = self.client.get(polling_status_endpoint)
response_data = json.loads(response.content)
self.assertEqual(response_data['polling_interval'], constants.DEFAULT_CLIENT_POLLING_INTERVAL)
time_remaining_mock.return_value = constants.EXAM_CONCLUDING_INTERVAL - 5
response = self.client.get(polling_status_endpoint)
response_data = json.loads(response.content)
self.assertEqual(response_data['polling_interval'], constants.REDUCED_CLIENT_POLLING_INTERVAL)
def test_attempt_status_stickiness(self):
"""
Test to confirm that a status timeout error will not alter a completed state
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment