Commit af522af2 by Adam Palay

formatting

parent 4a3b680e
...@@ -242,11 +242,15 @@ class LoncapaProblem(object): ...@@ -242,11 +242,15 @@ class LoncapaProblem(object):
return None return None
# Get a list of timestamps of all queueing requests, then convert it to a DateTime object # Get a list of timestamps of all queueing requests, then convert it to a DateTime object
queuetime_strs = [self.correct_map.get_queuetime_str(answer_id) queuetime_strs = [
for answer_id in self.correct_map self.correct_map.get_queuetime_str(answer_id)
if self.correct_map.is_queued(answer_id)] for answer_id in self.correct_map
queuetimes = [datetime.strptime(qt_str, xqueue_interface.dateformat) if self.correct_map.is_queued(answer_id)
for qt_str in queuetime_strs] ]
queuetimes = [
datetime.strptime(qt_str, xqueue_interface.dateformat)
for qt_str in queuetime_strs
]
return max(queuetimes) return max(queuetimes)
......
...@@ -37,23 +37,27 @@ class CorrectMap(object): ...@@ -37,23 +37,27 @@ class CorrectMap(object):
return self.cmap.__iter__() return self.cmap.__iter__()
# See the documentation for 'set_dict' for the use of kwargs # See the documentation for 'set_dict' for the use of kwargs
def set(self, def set(
answer_id=None, self,
correctness=None, answer_id=None,
npoints=None, correctness=None,
msg='', npoints=None,
hint='', msg='',
hintmode=None, hint='',
queuestate=None, **kwargs): hintmode=None,
queuestate=None,
**kwargs
):
if answer_id is not None: if answer_id is not None:
self.cmap[str(answer_id)] = {'correctness': correctness, self.cmap[str(answer_id)] = {
'npoints': npoints, 'correctness': correctness,
'msg': msg, 'npoints': npoints,
'hint': hint, 'msg': msg,
'hintmode': hintmode, 'hint': hint,
'queuestate': queuestate, 'hintmode': hintmode,
} 'queuestate': queuestate,
}
def __repr__(self): def __repr__(self):
return repr(self.cmap) return repr(self.cmap)
......
...@@ -1365,9 +1365,11 @@ class CodeResponse(LoncapaResponse): ...@@ -1365,9 +1365,11 @@ class CodeResponse(LoncapaResponse):
# Note that submission can be a file # Note that submission can be a file
submission = student_answers[self.answer_id] submission = student_answers[self.answer_id]
except Exception as err: except Exception as err:
log.error('Error in CodeResponse %s: cannot get student answer for %s;' log.error(
' student_answers=%s' % 'Error in CodeResponse %s: cannot get student answer for %s;'
(err, self.answer_id, convert_files_to_filenames(student_answers))) ' student_answers=%s' %
(err, self.answer_id, convert_files_to_filenames(student_answers))
)
raise Exception(err) raise Exception(err)
# We do not support xqueue within Studio. # We do not support xqueue within Studio.
...@@ -1386,14 +1388,15 @@ class CodeResponse(LoncapaResponse): ...@@ -1386,14 +1388,15 @@ class CodeResponse(LoncapaResponse):
anonymous_student_id = self.system.anonymous_student_id anonymous_student_id = self.system.anonymous_student_id
# Generate header # Generate header
queuekey = xqueue_interface.make_hashkey(str(self.system.seed) + qtime + queuekey = xqueue_interface.make_hashkey(
anonymous_student_id + str(self.system.seed) + qtime + anonymous_student_id + self.answer_id
self.answer_id) )
callback_url = self.system.xqueue['construct_callback']() callback_url = self.system.xqueue['construct_callback']()
xheader = xqueue_interface.make_xheader( xheader = xqueue_interface.make_xheader(
lms_callback_url=callback_url, lms_callback_url=callback_url,
lms_key=queuekey, lms_key=queuekey,
queue_name=self.queue_name) queue_name=self.queue_name
)
# Generate body # Generate body
if is_list_of_files(submission): if is_list_of_files(submission):
...@@ -1406,9 +1409,10 @@ class CodeResponse(LoncapaResponse): ...@@ -1406,9 +1409,10 @@ class CodeResponse(LoncapaResponse):
# Metadata related to the student submission revealed to the external # Metadata related to the student submission revealed to the external
# grader # grader
student_info = {'anonymous_student_id': anonymous_student_id, student_info = {
'submission_time': qtime, 'anonymous_student_id': anonymous_student_id,
} 'submission_time': qtime,
}
contents.update({'student_info': json.dumps(student_info)}) contents.update({'student_info': json.dumps(student_info)})
# Submit request. When successful, 'msg' is the prior length of the # Submit request. When successful, 'msg' is the prior length of the
......
...@@ -30,9 +30,11 @@ def make_xheader(lms_callback_url, lms_key, queue_name): ...@@ -30,9 +30,11 @@ def make_xheader(lms_callback_url, lms_key, queue_name):
'queue_name': designate a specific queue within xqueue server, e.g. 'MITx-6.00x' (string) 'queue_name': designate a specific queue within xqueue server, e.g. 'MITx-6.00x' (string)
} }
""" """
return json.dumps({'lms_callback_url': lms_callback_url, return json.dumps({
'lms_key': lms_key, 'lms_callback_url': lms_callback_url,
'queue_name': queue_name}) 'lms_key': lms_key,
'queue_name': queue_name
})
def parse_xreply(xreply): def parse_xreply(xreply):
...@@ -60,7 +62,7 @@ class XQueueInterface(object): ...@@ -60,7 +62,7 @@ class XQueueInterface(object):
''' '''
def __init__(self, url, django_auth, requests_auth=None): def __init__(self, url, django_auth, requests_auth=None):
self.url = url self.url = url
self.auth = django_auth self.auth = django_auth
self.session = requests.session(auth=requests_auth) self.session = requests.session(auth=requests_auth)
...@@ -95,13 +97,13 @@ class XQueueInterface(object): ...@@ -95,13 +97,13 @@ class XQueueInterface(object):
return (error, msg) return (error, msg)
def _login(self): def _login(self):
payload = {'username': self.auth['username'], payload = {
'password': self.auth['password']} 'username': self.auth['username'],
'password': self.auth['password']
}
return self._http_post(self.url + '/xqueue/login/', payload) return self._http_post(self.url + '/xqueue/login/', payload)
def _send_to_queue(self, header, body, files_to_upload): def _send_to_queue(self, header, body, files_to_upload):
payload = {'xqueue_header': header, payload = {'xqueue_header': header,
'xqueue_body': body} 'xqueue_body': body}
...@@ -112,7 +114,6 @@ class XQueueInterface(object): ...@@ -112,7 +114,6 @@ class XQueueInterface(object):
return self._http_post(self.url + '/xqueue/submit/', payload, files=files) return self._http_post(self.url + '/xqueue/submit/', payload, files=files)
def _http_post(self, url, data, files=None): def _http_post(self, url, data, files=None):
try: try:
r = self.session.post(url, data=data, files=files) r = self.session.post(url, data=data, files=files)
......
...@@ -1126,8 +1126,12 @@ class CapaDescriptor(CapaFields, RawDescriptor): ...@@ -1126,8 +1126,12 @@ class CapaDescriptor(CapaFields, RawDescriptor):
mako_template = "widgets/problem-edit.html" mako_template = "widgets/problem-edit.html"
js = {'coffee': [resource_string(__name__, 'js/src/problem/edit.coffee')]} js = {'coffee': [resource_string(__name__, 'js/src/problem/edit.coffee')]}
js_module_name = "MarkdownEditingDescriptor" js_module_name = "MarkdownEditingDescriptor"
css = {'scss': [resource_string(__name__, 'css/editor/edit.scss'), css = {
resource_string(__name__, 'css/problem/edit.scss')]} 'scss': [
resource_string(__name__, 'css/editor/edit.scss'),
resource_string(__name__, 'css/problem/edit.scss')
]
}
# Capa modules have some additional metadata: # Capa modules have some additional metadata:
# TODO (vshnayder): do problems have any other metadata? Do they # TODO (vshnayder): do problems have any other metadata? Do they
......
...@@ -213,22 +213,28 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours ...@@ -213,22 +213,28 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours
return None return None
# Setup system context for module instance # Setup system context for module instance
ajax_url = reverse('modx_dispatch', ajax_url = reverse(
kwargs=dict(course_id=course_id, 'modx_dispatch',
location=descriptor.location.url(), kwargs=dict(
dispatch=''), course_id=course_id,
) location=descriptor.location.url(),
dispatch=''
),
)
# Intended use is as {ajax_url}/{dispatch_command}, so get rid of the trailing slash. # Intended use is as {ajax_url}/{dispatch_command}, so get rid of the trailing slash.
ajax_url = ajax_url.rstrip('/') ajax_url = ajax_url.rstrip('/')
def make_xqueue_callback(dispatch='score_update'): def make_xqueue_callback(dispatch='score_update'):
# Fully qualified callback URL for external queueing system # Fully qualified callback URL for external queueing system
relative_xqueue_callback_url = reverse('xqueue_callback', relative_xqueue_callback_url = reverse(
kwargs=dict(course_id=course_id, 'xqueue_callback',
userid=str(user.id), kwargs=dict(
mod_id=descriptor.location.url(), course_id=course_id,
dispatch=dispatch), userid=str(user.id),
) mod_id=descriptor.location.url(),
dispatch=dispatch
),
)
return xqueue_callback_url_prefix + relative_xqueue_callback_url return xqueue_callback_url_prefix + relative_xqueue_callback_url
# Default queuename is course-specific and is derived from the course that # Default queuename is course-specific and is derived from the course that
...@@ -313,10 +319,12 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours ...@@ -313,10 +319,12 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours
score_bucket = get_score_bucket(student_module.grade, student_module.max_grade) score_bucket = get_score_bucket(student_module.grade, student_module.max_grade)
org, course_num, run = course_id.split("/") org, course_num, run = course_id.split("/")
tags = ["org:{0}".format(org), tags = [
"course:{0}".format(course_num), "org:{0}".format(org),
"run:{0}".format(run), "course:{0}".format(course_num),
"score_bucket:{0}".format(score_bucket)] "run:{0}".format(run),
"score_bucket:{0}".format(score_bucket)
]
if grade_bucket_type is not None: if grade_bucket_type is not None:
tags.append('type:%s' % grade_bucket_type) tags.append('type:%s' % grade_bucket_type)
...@@ -326,38 +334,41 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours ...@@ -326,38 +334,41 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours
# TODO (cpennington): When modules are shared between courses, the static # TODO (cpennington): When modules are shared between courses, the static
# prefix is going to have to be specific to the module, not the directory # prefix is going to have to be specific to the module, not the directory
# that the xml was loaded from # that the xml was loaded from
system = ModuleSystem(track_function=track_function, system = ModuleSystem(
render_template=render_to_string, track_function=track_function,
ajax_url=ajax_url, render_template=render_to_string,
xqueue=xqueue, ajax_url=ajax_url,
# TODO (cpennington): Figure out how to share info between systems xqueue=xqueue,
filestore=descriptor.system.resources_fs, # TODO (cpennington): Figure out how to share info between systems
get_module=inner_get_module, filestore=descriptor.system.resources_fs,
user=user, get_module=inner_get_module,
# TODO (cpennington): This should be removed when all html from user=user,
# a module is coming through get_html and is therefore covered # TODO (cpennington): This should be removed when all html from
# by the replace_static_urls code below # a module is coming through get_html and is therefore covered
replace_urls=partial( # by the replace_static_urls code below
static_replace.replace_static_urls, replace_urls=partial(
data_directory=getattr(descriptor, 'data_dir', None), static_replace.replace_static_urls,
course_namespace=descriptor.location._replace(category=None, name=None), data_directory=getattr(descriptor, 'data_dir', None),
), course_namespace=descriptor.location._replace(category=None, name=None),
node_path=settings.NODE_PATH, ),
xblock_model_data=xblock_model_data, node_path=settings.NODE_PATH,
publish=publish, xblock_model_data=xblock_model_data,
anonymous_student_id=unique_id_for_user(user), publish=publish,
course_id=course_id, anonymous_student_id=unique_id_for_user(user),
open_ended_grading_interface=open_ended_grading_interface, course_id=course_id,
s3_interface=s3_interface, open_ended_grading_interface=open_ended_grading_interface,
cache=cache, s3_interface=s3_interface,
can_execute_unsafe_code=(lambda: can_execute_unsafe_code(course_id)), cache=cache,
) can_execute_unsafe_code=(lambda: can_execute_unsafe_code(course_id)),
)
# pass position specified in URL to module through ModuleSystem # pass position specified in URL to module through ModuleSystem
system.set('position', position) system.set('position', position)
system.set('DEBUG', settings.DEBUG) system.set('DEBUG', settings.DEBUG)
if settings.MITX_FEATURES.get('ENABLE_PSYCHOMETRICS'): if settings.MITX_FEATURES.get('ENABLE_PSYCHOMETRICS'):
system.set('psychometrics_handler', # set callback for updating PsychometricsData system.set(
make_psychometrics_data_update_handler(course_id, user, descriptor.location.url())) 'psychometrics_handler', # set callback for updating PsychometricsData
make_psychometrics_data_update_handler(course_id, user, descriptor.location.url())
)
try: try:
module = descriptor.xmodule(system) module = descriptor.xmodule(system)
...@@ -381,13 +392,14 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours ...@@ -381,13 +392,14 @@ def get_module_for_descriptor_internal(user, descriptor, model_data_cache, cours
system.set('user_is_staff', has_access(user, descriptor.location, 'staff', course_id)) system.set('user_is_staff', has_access(user, descriptor.location, 'staff', course_id))
_get_html = module.get_html _get_html = module.get_html
if wrap_xmodule_display == True: if wrap_xmodule_display is True:
_get_html = wrap_xmodule(module.get_html, module, 'xmodule_display.html') _get_html = wrap_xmodule(module.get_html, module, 'xmodule_display.html')
module.get_html = replace_static_urls( module.get_html = replace_static_urls(
_get_html, _get_html,
getattr(descriptor, 'data_dir', None), getattr(descriptor, 'data_dir', None),
course_namespace=module.location._replace(category=None, name=None)) course_namespace=module.location._replace(category=None, name=None)
)
# Allow URLs of the form '/course/' refer to the root of multicourse directory # Allow URLs of the form '/course/' refer to the root of multicourse directory
# hierarchy of this course # hierarchy of this course
......
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