首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >Django -无法为具有动态upload_to值的ImageField创建迁移

Django -无法为具有动态upload_to值的ImageField创建迁移
EN

Stack Overflow用户
提问于 2014-09-10 22:17:07
回答 3查看 8K关注 0票数 34

我刚刚把我的应用升级到了1.7 (实际上还在尝试)。

这是我在models.py中所拥有的:

代码语言:javascript
复制
def path_and_rename(path):
    def wrapper(instance, filename):
        ext = filename.split('.')[-1]
        # set filename as random string
        filename = '{}.{}'.format(uuid4().hex, ext)
        # return the whole path to the file
        return os.path.join(path, filename)
    return wrapper

class UserProfile(AbstractUser):
    #...
    avatar = models.ImageField(upload_to=path_and_rename("avatars/"),
                               null=True, blank=True,
                               default="avatars/none/default.png",
                               height_field="image_height",
                               width_field="image_width")

当我尝试makemigrations时,它抛出:

代码语言:javascript
复制
ValueError: Could not find function wrapper in webapp.models.
Please note that due to Python 2 limitations, you cannot serialize unbound method functions (e.g. a method declared
and used in the same class body). Please move the function into the main module body to use migrations.
EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2014-09-10 22:27:28

我不确定是否可以回答我自己的问题,但我只是想(我想)。

根据this bug report的说法,我编辑了我的代码:

代码语言:javascript
复制
from django.utils.deconstruct import deconstructible

@deconstructible
class PathAndRename(object):

    def __init__(self, sub_path):
        self.path = sub_path

    def __call__(self, instance, filename):
        ext = filename.split('.')[-1]
        # set filename as random string
        filename = '{}.{}'.format(uuid4().hex, ext)
        # return the whole path to the file
        return os.path.join(self.path, filename)

path_and_rename = PathAndRename("/avatars")

然后,在字段定义中:

代码语言:javascript
复制
avatar = models.ImageField(upload_to=path_and_rename,
                               null=True, blank=True,
                               default="avatars/none/default.png",
                               height_field="image_height",
                               width_field="image_width")

这对我很有效。

票数 80
EN

Stack Overflow用户

发布于 2018-10-17 19:35:37

您可以使用kwargs创建函数,如下所示:

代码语言:javascript
复制
def upload_image_location(instance, filename, thumbnail=False):
    name, ext = os.path.splitext(filename)
    path = f'news/{instance.slug}{f"_thumbnail" if thumbnail else ""}{ext}'
    n = 1
    while os.path.exists(path):
        path = f'news/{instance.slug}-{n}{ext}'
        n += 1
    return path

并将此方法与模型中的functools.partial一起使用:

代码语言:javascript
复制
image = models.ImageField(
    upload_to=upload_image_location,
    width_field='image_width',
    height_field='image_height'
)
thumbnail_image = models.ImageField(upload_to=partial(upload_image_location, thumbnail=True), blank=True)

您将获得如下的迁移:

代码语言:javascript
复制
class Migration(migrations.Migration):

    dependencies = [
        ('news', '0001_initial'),
    ]

    operations = [
        migrations.AddField(
            model_name='news',
            name='thumbnail_image',
            field=models.ImageField(blank=True, upload_to=functools.partial(news.models.upload_image_location, *(), **{'thumbnail': True})),
        ),
        migrations.AlterField(
            model_name='news',
            name='image',
            field=models.ImageField(height_field='image_height', upload_to=news.models.upload_image_location, width_field='image_width'),
        ),
    ]
票数 0
EN

Stack Overflow用户

发布于 2022-02-08 07:37:41

代码语言:javascript
复制
field=models.ImageField(blank=True, upload_to="/smth", *(), **{'thumbnail': True})),

而不是

代码语言:javascript
复制
field=models.ImageField(blank=True, upload_to=functools.partial(news.models.upload_image_location, *(), **{'thumbnail': True}))
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/25767787

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档