1

I have a Photo-Model that helps me achieve storing each image as a thumbnail aswell:

class Photo(models.Model):
    image = models.ImageField(upload_to=upload_path, default=default_image)
    thumbnail = models.ImageField(upload_to=upload_path_2, editable=False, default=default_image_2)
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

    class Meta:
        abstract = True

Now I have another Model, lets call it User, which inherits from Photo:

class User(Photo):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)

Now lets say there are multiple classes inheriting from Photo and depending on the inheriting class, I want to set another upload_path and default_image. How Do I achieve that? Can I somehow use the constructor?

Thanks in Advance!

3
  • Speaking from experience, inheriting from models seems like a good idea but it generally isn't. If you want to query all models which inherit from Photo django will either be very inefficient or only provide you with the basemodel references (which you'll need to resolved 1 by 1). I urge you to reconsider inheritance and/or test thoroughly before continuing Commented Sep 14, 2020 at 15:28
  • Alternatively you can make the models abstract = True. This might be more what you are looking for. This won't allow you to query all Photo's but it will allow you to re-use code between models Commented Sep 14, 2020 at 15:30
  • @Exelian Thank you very much. I forgot to add the abstract = True-Line in this post, I already used it. But I still dont know how to go on, could you help me further? Commented Sep 15, 2020 at 10:09

1 Answer 1

1

I'd say that the best way to handle your use-case is slightly different. You can pass a function to upload_to. This function will be provided the signature instance and filename of the uploaded file (docs).

You can check class of the instance with isinstance or something similar and change the output accordingly.

def upload_path(instance, filename):
    if isinstance(instance, User):
        return 'user_{0}/{1}'.format(instance.user.id, filename)
    return 'photo/{1}'.format(filename)

Doing the same for default is a little bit harder. The default function won't be passed any reference to the model or field which will make it harder to override it based on model. You could simply add an image field to each of the concrete models, but I don't know if that would be appropriate.

Sign up to request clarification or add additional context in comments.

1 Comment

While implementing your solution, I stumbled upon another problem. In the upload_path()-method I want to see which class called or inherited from PhotoModel. Do you know, how I get this information?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.