Search code examples
djangoamazon-s3django-modelsboto3python-django-storages

django-storages + private S3 bucket - How can I make a username the folder name?


I'm using django-storages and a private S3 bucket to store user uploads. I would like the following folder structure:

/uploads/someuser321/20190112-123456/

I obviously know how to do the timestamp (2019-01-12 at 12:34:56), but how do I get the user's username into the path? My model currently looks like this:

user_file = models.FileField(
    upload_to="uploads", 
    storage=PrivateMediaStorage(), 
    null=True, blank=True)

I can just add an f-string for the datetime/timestamp. I understand that and I know how to do it. But how can I add the user's username as a folder as well? I would need to somehow access this from the view, so that I know who the request.user is, but how would I even do that?


Solution

  • You need to make a function call inside upload_to. Here's a function that will get you the path:

    def get_file_path(instance, filename):
        today = localtime(now()).date()
        return '{0}/uploads/{1}/{2}'.format(instance.user.username, today.strftime('%Y/%m/%d'), filename)
    

    Then you need to call it like this inside your model:

    user_file = models.FileField(
        upload_to=get_file_path, 
        storage=PrivateMediaStorage(), 
        null=True, blank=True)
    

    You need to fix that return statement to get the desired format, but that will do it. Django will automatically pass an instance to your function and the filename.

    I hope that helps!