Question

first some information about the app: I want to be able to upload a pdf file, that pdf file will be converted to images (for every pdf page one image). These images will then be shown on the website and the pdf can be downloaded: So far I have this:

def upload_to(path):
    def upload_callback(instance, filename):
        return '%s' % os.path.join(settings.MEDIA_ROOT, path, str(instance), filename)
    return upload_callback

class Document(models.Model):
    name = models.TextField()
    pdf_file = models.FileField(upload_to=upload_to('pdfs'))
    images = models.ManyToManyField('Image', null=True, blank=True)

class Image(models.Model):
    image = models.ImageField(upload_to='pdfimages')

Now to create the images and the image objects i overwrote the save function of the Document class: I looks like this:

def save(self, *args, **kwargs):
    path = os.path.join(settings.MEDIA_ROOT, 'pdfs', self.name)
    imagepath = os.path.join(settings.MEDIA_ROOT, 'pdfimages')

    if os.path.exists(path):
        for file_ in os.listdir(path):
            if file_ == self.pdf_file.name:
                continue

    super(Document, self).save(*args, **kwargs)

    save_to = os.path.join(path, os.path.splitext(self.pdf_file.name)[0] +
                           '_page.png')
    pdffile = os.path.join(path, self.pdf_file.name)

    args = ['convert', '-density', '100', '-depth', 
            '8', '-quality', '85', pdffile, save_to ]

    subprocess.check_call(args, stdout=sys.stdout, stderr=sys.stderr)
    for file_ in os.listdir(path):
        if file_.endswith('png'):
            try:
                shutil.move((os.path.join(settings.MEDIA_ROOT,
                                          'pdfs', self.name, file_)),
                            imagepath)

            except Exception:
                pass

     for file_ in os.listdir(imagepath):
        i, created = Image.objects.get_or_create(image="pdfimages/%s" % file_)

First that code isn't very nice and second the most important action is still missing. Adding the image to the document meaning updating the m2m relation. Now I have two questions:

  1. Can I write above code nicer? (mostly don't like the

    super(Document, self).save(*args, **kwargs) in the middle of the code.

  2. For the m2m update I looked at m2m_changed signal but I honestly don't understand how to use it.
Any help is appreciated.

EDIT:

It's actually quite easy once you understand the parametere, thanks

Was it helpful?

Solution

check this post on usage of m2m signal.

You can move all your post save processing logic to the signal

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top