N
N
NerVik2016-08-09 16:51:51
Django
NerVik, 2016-08-09 16:51:51

How not to repeat upload_to function code?

Hello, there is a model:

class Image(models.Model):
    image = models.ImageField(upload_to=image, blank=True)
    image_xs = models.ImageField(upload_to=image_xs, blank=True)
    image_sm = models.ImageField(upload_to=image_sm, blank=True)
    image_md = models.ImageField(upload_to=image_md, blank=True)
    am = models.ForeignKey(AnotherModel)

in the upload_to function:
def image(instance, filename):
    return 'image/{0}/{1}'.format(instance.am_id, filename)


def image_xs(instance, filename):
    return 'image/{0}/xs/{1}'.format(instance.am_id, filename)


def image_sm(instance, filename):
    return 'image/{0}/sm/{1}'.format(instance.am_id, filename)


def image_md(instance, filename):
    return 'image/{0}/md/{1}'.format(instance.am_id, filename)

As you can see, the functions are almost the same, they differ in just a couple of characters.
Question: how to turn 4 functions into one universal one?

Answer the question

In order to leave comments, you need to log in

2 answer(s)
O
Oscar Django, 2016-08-09
@NerVik

def image(instance, filename, image_size_type):
  if image_size_type:
    size = '/{}'.format(image_size_type)
  else:
    size = ''
  return 'image/{0}{1}/{2}'.format(instance.am_id, size, filename)

class MyImageField(ImageField):
  def __init__(self, image_size_type='', **kwargs):
    self.image_size_type = image_size_type
    super().__init__(**kwargs)

  def generate_filename(self, instance, filename):
    if callable(self.upload_to):
      directory_name, filename = os.path.split(self.upload_to(instance, filename, self.image_size_type))
      filename = self.storage.get_valid_name(filename)
      return os.path.normpath(os.path.join(directory_name, filename))

    return os.path.join(self.get_directory_name(), self.get_filename(filename))

class Image(models.Model):
    image = MyImageField(upload_to=image, blank=True)
    image_xs = MyImageField(upload_to=image, blank=True, image_size_type='xs')
    image_sm = MyImageField(upload_to=image, blank=True, image_size_type='sm')
    image_md = MyImageField(upload_to=image, blank=True, image_size_type='md')
    am = models.ForeignKey(AnotherModel)

S
sim3x, 2016-08-09
@sim3x

Use image resizing plugin https://djangopackages.org/grids/g/thumbnails/
Use os.path.join for path

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question