From fcaf3e6329f464e4a5f82168b65ee4e3b289eead Mon Sep 17 00:00:00 2001 From: Chris Dodge Date: Mon, 5 Aug 2013 23:08:35 -0400 Subject: [PATCH] give some debug message regarding why export might fail --- cms/djangoapps/contentstore/views/assets.py | 31 +++++++++++++++++---- cms/templates/export.html | 19 +++++++++++++ common/lib/xmodule/xmodule/exceptions.py | 10 +++++++ common/lib/xmodule/xmodule/raw_module.py | 5 ++-- 4 files changed, 57 insertions(+), 8 deletions(-) diff --git a/cms/djangoapps/contentstore/views/assets.py b/cms/djangoapps/contentstore/views/assets.py index 1c22114d76..252f36e392 100644 --- a/cms/djangoapps/contentstore/views/assets.py +++ b/cms/djangoapps/contentstore/views/assets.py @@ -3,6 +3,7 @@ import json import os import tarfile import shutil +import cgi from tempfile import mkdtemp from path import path @@ -27,7 +28,7 @@ from xmodule.modulestore import Location from xmodule.contentstore.content import StaticContent from xmodule.util.date_utils import get_default_time_display from xmodule.modulestore import InvalidLocationError -from xmodule.exceptions import NotFoundError +from xmodule.exceptions import NotFoundError, SerializationError from .access import get_location_and_verify_access from util.json_request import JsonResponse @@ -336,16 +337,34 @@ def generate_export_course(request, org, course, name): the course """ location = get_location_and_verify_access(request, org, course, name) - + course_module = modulestore().get_item(location) loc = Location(location) export_file = NamedTemporaryFile(prefix=name + '.', suffix=".tar.gz") root_dir = path(mkdtemp()) - # export out to a tempdir - logging.debug('root = {0}'.format(root_dir)) - - export_to_xml(modulestore('direct'), contentstore(), loc, root_dir, name, modulestore()) + try: + export_to_xml(modulestore('direct'), contentstore(), loc, root_dir, name, modulestore()) + except SerializationError, e: + failed_item = modulestore().get_item(e.location) + parent_locs = modulestore().get_parent_locations(failed_item.location, None) + if len(parent_locs) > 0: + parent = modulestore().get_item(parent_locs[0]) + parent_info = "Parent Display Name: {0}
Parent Identifier: {1}".format(parent.display_name, parent.location.name) + else: + parent_info = '' + return render_to_response('export.html', { + 'context_course': course_module, + 'successful_import_redirect_url': '', + 'err_msg': "A courseware module has failed to convert to XML. Details:
Module Type: {0}
Display Name: {1}
Identifier: {2}
{3}". + format(failed_item.location.category, failed_item.display_name, failed_item.location.name, parent_info) + }) + except Exception, e: + return render_to_response('export.html', { + 'context_course': course_module, + 'successful_import_redirect_url': '', + 'err_msg': str(e) + }) logging.debug('tar file being generated at {0}'.format(export_file.name)) tar_file = tarfile.open(name=export_file.name, mode='w:gz') diff --git a/cms/templates/export.html b/cms/templates/export.html index 593cf3dd6e..0cc67a7b5a 100644 --- a/cms/templates/export.html +++ b/cms/templates/export.html @@ -6,6 +6,24 @@ <%block name="title">${_("Course Export")} <%block name="bodyclass">is-signedin course tools export +<%block name="jsextra"> + % if err_msg: + + %endif + + <%block name="content">
@@ -18,6 +36,7 @@
+

${_("About Exporting Courses")}

diff --git a/common/lib/xmodule/xmodule/exceptions.py b/common/lib/xmodule/xmodule/exceptions.py index d0a8e76557..48c083cbf1 100644 --- a/common/lib/xmodule/xmodule/exceptions.py +++ b/common/lib/xmodule/xmodule/exceptions.py @@ -13,6 +13,7 @@ class ProcessingError(Exception): ''' pass + class InvalidVersionError(Exception): """ Tried to save an item with a location that a store cannot support (e.g., draft version @@ -21,3 +22,12 @@ class InvalidVersionError(Exception): def __init__(self, location): super(InvalidVersionError, self).__init__() self.location = location + + +class SerializationError(Exception): + """ + Thrown when a module cannot be exported to XML + """ + def __init__(self, location, msg): + super(SerializationError, self).__init__(msg) + self.location = location diff --git a/common/lib/xmodule/xmodule/raw_module.py b/common/lib/xmodule/xmodule/raw_module.py index b972d7c8eb..4c6ddb5b51 100644 --- a/common/lib/xmodule/xmodule/raw_module.py +++ b/common/lib/xmodule/xmodule/raw_module.py @@ -4,6 +4,7 @@ from xmodule.xml_module import XmlDescriptor import logging import sys from xblock.core import String, Scope +from exceptions import SerializationError log = logging.getLogger(__name__) @@ -27,11 +28,11 @@ class RawDescriptor(XmlDescriptor, XMLEditingDescriptor): # re-raise lines = self.data.split('\n') line, offset = err.position - msg = ("Unable to create xml for problem {loc}. " + msg = ("Unable to create xml for module {loc}. " "Context: '{context}'".format( context=lines[line - 1][offset - 40:offset + 40], loc=self.location)) - raise Exception, msg, sys.exc_info()[2] + raise SerializationError(self.location, msg) class EmptyDataRawDescriptor(XmlDescriptor, XMLEditingDescriptor):