hide banner
[edumed.git] / catalogue / publish.py
index cca25de..293b89e 100755 (executable)
@@ -1,10 +1,10 @@
 # -*- coding: utf-8
 # -*- coding: utf-8
-from django.core.files.base import ContentFile
 from django.core.files import File
 from django.core.urlresolvers import reverse
 from librarian import DocProvider, IOFile
 from librarian.pyhtml import EduModuleFormat
 from librarian.pypdf import EduModulePDFFormat
 from django.core.files import File
 from django.core.urlresolvers import reverse
 from librarian import DocProvider, IOFile
 from librarian.pyhtml import EduModuleFormat
 from librarian.pypdf import EduModulePDFFormat
+from librarian.pdf_from_html import EduModulePdfFromHtmlFormat
 from .models import Lesson, Attachment
 from fnpdjango.utils.text.slughifi import slughifi
 
 from .models import Lesson, Attachment
 from fnpdjango.utils.text.slughifi import slughifi
 
@@ -12,15 +12,14 @@ from fnpdjango.utils.text.slughifi import slughifi
 # TODO: Using sorl.thumbnail for now,
 # but this should be done in Librarian,
 # directly using convert or PIL as a fallback.
 # TODO: Using sorl.thumbnail for now,
 # but this should be done in Librarian,
 # directly using convert or PIL as a fallback.
-def get_image(src_img_path, width=None,
-        default_width=1600, formats=('PNG', 'JPEG', 'GIF')):
+def get_image(src_img_path, width=None, default_width=1600, formats=('PNG', 'JPEG', 'GIF')):
     """ Returns an object with `url` and `storage` attributes,
         or None if using the original image is OK.
     """
     """ Returns an object with `url` and `storage` attributes,
         or None if using the original image is OK.
     """
-    
+
     from PIL import Image
     from sorl.thumbnail import get_thumbnail
     from PIL import Image
     from sorl.thumbnail import get_thumbnail
-    
+
     # Does it need converting?
     # Yes, if width is given explicitly.
     convert = width is not None
     # Does it need converting?
     # Yes, if width is given explicitly.
     convert = width is not None
@@ -42,7 +41,11 @@ def get_image(src_img_path, width=None,
     if convert:
         if width is None:
             width = default_width
     if convert:
         if width is None:
             width = default_width
-        return get_thumbnail(src_img_path, '%sx%s' % (width, 10*width))
+        try:
+            return get_thumbnail(src_img_path, '%sx%s' % (width, 10*width))
+        except:
+            # hard to predict what solr raises on invalid image
+            return None
     else:
         return None
 
     else:
         return None
 
@@ -81,8 +84,7 @@ class HtmlFormat(EduModuleFormat):
             src_img = self.find_attachment(slug, fmt).file
         except self.MaterialNotFound:
             return ''
             src_img = self.find_attachment(slug, fmt).file
         except self.MaterialNotFound:
             return ''
-        img = get_image(src_img.path, width,
-            self.DEFAULT_IMAGE_WIDTH, self.IMAGE_FORMATS)
+        img = get_image(src_img.path, width, self.DEFAULT_IMAGE_WIDTH, self.IMAGE_FORMATS)
         return (img or src_img).url
 
     def text_to_anchor(self, text):
         return (img or src_img).url
 
     def text_to_anchor(self, text):
@@ -108,16 +110,64 @@ class PdfFormat(EduModulePDFFormat):
 
     def get_image(self, name):
         src_img = super(PdfFormat, self).get_image(name)
 
     def get_image(self, name):
         src_img = super(PdfFormat, self).get_image(name)
-        img = get_image(src_img.get_filename(),
-                default_width=self.DEFAULT_IMAGE_WIDTH,
-                formats=self.IMAGE_FORMATS
-            )
+        img = get_image(
+            src_img.get_filename(),
+            default_width=self.DEFAULT_IMAGE_WIDTH,
+            formats=self.IMAGE_FORMATS)
         if img:
             return IOFile.from_filename(img.storage.path(img))
         else:
             return src_img
 
 
         if img:
             return IOFile.from_filename(img.storage.path(img))
         else:
             return src_img
 
 
+class PdfFromHtmlFormat(EduModulePdfFromHtmlFormat):
+    IMAGE_FORMATS = ('PNG', 'JPEG', 'GIF')
+    DEFAULT_IMAGE_WIDTH = 1600
+
+    def find_attachment(self, slug, fmt):
+        lesson_slug = self.wldoc.book_info.url.slug
+        try:
+            # If already saved, use it.
+            att = Attachment.objects.get(lesson__slug=lesson_slug,
+                                         slug=slug, ext=fmt)
+        except Attachment.DoesNotExist, e:
+            # If attached to source IOFile, save now.
+            att_name = "%s.%s" % (slug, fmt)
+            try:
+                att_file = self.wldoc.source.attachments[att_name]
+            except KeyError:
+                print u"ATTACHMENT MISSING:", att_name
+                raise self.MaterialNotFound()
+            else:
+                lesson = Lesson.objects.get(slug=lesson_slug)
+                att = lesson.attachment_set.create(slug=slug, ext=fmt)
+                att.file.save(att_name, File(att_file.get_file()))
+                return att
+        else:
+            return att
+
+    def url_for_material(self, slug, fmt):
+        return self.find_attachment(slug, fmt).file.url
+
+    def image(self, slug, fmt, width=None):
+        try:
+            src_img = self.find_attachment(slug, fmt).file
+        except self.MaterialNotFound:
+            return None
+        img = get_image(src_img.path, width, self.DEFAULT_IMAGE_WIDTH, self.IMAGE_FORMATS)
+        return img or src_img
+
+    def url_for_image(self, slug, fmt, image=None, **kwargs):
+        img = image or self.image(slug, fmt, **kwargs)
+        if img:
+            return img.url
+        else:
+            return ''
+
+    def text_to_anchor(self, text):
+        return slughifi(text)
+
+
 class OrmDocProvider(DocProvider):
     def by_slug(self, slug):
         """Should return a file-like object with a WL document XML."""
 class OrmDocProvider(DocProvider):
     def by_slug(self, slug):
         """Should return a file-like object with a WL document XML."""