Подтвердить что ты не робот

Использовать уникальные имена файлов для загрузки с помощью django?

Какой лучший способ переименовать фотографии с уникальным именем на сервере при их загрузке, используя django? Я хочу, чтобы каждое имя использовалось только один раз. Есть ли какие-нибудь приложения-синтаксисы, которые могут это сделать, возможно, с GUID?

4b9b3361

Ответ 1

Используйте uuid. Чтобы связать это с вашей моделью, см. документацию Django для FileField upload_to.

Например, в ваших models.py определите следующую функцию:

import uuid
import os

def get_file_path(instance, filename):
    ext = filename.split('.')[-1]
    filename = "%s.%s" % (uuid.uuid4(), ext)
    return os.path.join('uploads/logos', filename)

Затем, определяя свой FileField/ImageField, укажите get_file_path как значение upload_to.

file = models.FileField(upload_to=get_file_path,
                        null=True,
                        blank=True,
                        verbose_name=_(u'Contact list'))

Ответ 2

До Django 1.6.6, 1.5.9 и 1.4.14 функция get_avaialable_name автоматически предоставит файлы уникальным имя, добавив подчеркивание. Так, например, если вы сохраните один файл "test.jpg", а затем еще один файл "test.jpg" на ваш сервер, первый будет называться test.jpg, а второй будет называться test_1.jpg.

Увы, это оказывается вектором DDOSing машины, посылая ему тысячи файлов с нулевым байтом для хранения, каждый из которых проверяет тысячи предыдущих файлов, чтобы узнать, как его имя должно быть.

Как вы см. в документах, новая система добавляет семь случайных цифр после подчеркивания, чтобы исправить эту проблему.

Ответ 3

Лучше всего использовать общий класс в вашем helpers.py. Таким образом, вы можете повторно использовать генератор случайных файлов в своих приложениях.

В вашем helpers.py:

import os
import uuid
from django.utils.deconstruct import deconstructible


@deconstructible
class RandomFileName(object):
    def __init__(self, path):
        self.path = os.path.join(path, "%s%s")

    def __call__(self, _, filename):
        # @note It up to the validators to check if it the correct file type in name or if one even exist.
        extension = os.path.splitext(filename)[1]
        return self.path % (uuid.uuid4(), extension)

И затем в вашей модели просто импортируйте вспомогательный класс:

from mymodule.helpers import RandomFileName 

И затем используйте его:

logo = models.ImageField(upload_to=RandomFileName('logos'))

Ссылка: https://coderwall.com/p/hfgoiw/give-imagefield-uploads-a-unique-name-to-avoid-file-overwrites

Ответ 4

Как связать имя файла с датой/временем, когда была загружена фотография, а затем с помощью hashlib, чтобы создать дайджест сообщений? Это должно дать вам уникальные имена файлов.

В качестве альтернативы вы можете повторно использовать аккуратный маленький фрагмент, который создает уникальные имена файлов, а затем использует полный путь к этому файлу в качестве входа в ваш хеш-вызов. Это дает вам уникальные строки постоянной длины, которые вы можете сопоставить с вашими файлами.

Ответ 5

С момента написания этого ответа кажется, что вам больше не нужно делать ничего особенного, чтобы это произошло. Если вы настроили FileField со статическим свойством upload_to, система хранения Django автоматически будет управлять именованием, чтобы при загрузке дублированного имени файла Django будет произвольно генерировать новое уникальное имя файла для дубликата.

Работает на Django 1.10.