django ImageField - 如何自定义名称 +删除旧文件

发布于 2024-10-24 01:34:54 字数 1378 浏览 6 评论 0原文

我有一个带有 ImageField 的模型。我已经设置了 upload_to 并创建了自己的 FileSystemStorage 类来处理使用唯一名称保存文件...但是...

此设置允许我上传并为每个文件保存一个具有唯一名称的文件(这很好),但我还需要它来删除以前存在的文件,例如

我上传 file1.png 并将其另存为 file1_xkdeujg.png (这只是一个随机字符串)

然后我进入 django admin(使用 django 管理界面,因此需要通过模型完成)并将该字段的图像更改为 fileNEW.png

现在需要发生的是:

1)它保存新文件为 fileNEW_fjewiejk.png (每次保存图像时都有唯一的随机字符串) - 完成

2) 它将新文件保存到数据库中 - 完成

3) 它删除旧文件- file1_xkdeuig.png - 来自文件系统 - 未完成

问:任何人都可以帮我解决第 3 点吗?

一些代码:

class Page(models.Model):
    image           = models.ImageField(upload_to='pages/', storage=MyFileSystemStorage())

并且(从其他地方借用了大部分代码。 ..):

class MyFileSystemStorage(FileSystemStorage):

    def get_valid_name(self, name):
            file_root, file_ext = os.path.splitext(name)
            return "%s_%s%s" % (file_root, rand_key(8), file_ext)

    def get_available_name(self, name):
            dir_name, file_name = os.path.split(name)
            file_root, file_ext = os.path.splitext(file_name)
            count = itertools.count(1)
            while self.exists(name):
                    name = os.path.join(dir_name, "%s_%s%s" % (rand_key(32),  count.next(), file_ext))
            return name

I have a model with an ImageField in it. I've already set the upload_to and created my own FileSystemStorage class to deal with saving the file with a unique name... however...

This setup allows me to upload and save a file with a unique name for each file (which is fine), but I also need it to remove the previous file that existed, e.g.

I upload file1.png and it's saved as file1_xkdeujg.png (that's just a random string)

I then go into django admin (using the django admin interface so need to do via the model) and change the image for that field to fileNEW.png

What needs to happen now is:

1) it saves the new file as fileNEW_fjewiejk.png (unique random string each time image saved) - done

2) it saves the new file into the database - done

3) it removes the old file - file1_xkdeuig.png - from the filesystem - not done

Q: Can anyone help me with point 3?

Some code:

class Page(models.Model):
    image           = models.ImageField(upload_to='pages/', storage=MyFileSystemStorage())

And (borrowed the bulk of this code from somewhere else...):

class MyFileSystemStorage(FileSystemStorage):

    def get_valid_name(self, name):
            file_root, file_ext = os.path.splitext(name)
            return "%s_%s%s" % (file_root, rand_key(8), file_ext)

    def get_available_name(self, name):
            dir_name, file_name = os.path.split(name)
            file_root, file_ext = os.path.splitext(file_name)
            count = itertools.count(1)
            while self.exists(name):
                    name = os.path.join(dir_name, "%s_%s%s" % (rand_key(32),  count.next(), file_ext))
            return name

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

傲世九天 2024-10-31 01:34:54

答案来自 StackOverflow 上的类似问题...

基本上,您将原始图像存储在 init 方法中,然后检查它在保存之前是否已更改。

保存后,删除原图片路径下存储的图片。

也请参阅这个答案(乔什的答案是我使用的并且更喜欢的答案,因为它不会访问数据库)。

Django:保存时,你怎么能检查字段是否已更改?

The answer came from a similar question on StackOverflow...

Basically, you store the original image in the init method, and then check to see if it has changed prior to the save.

After the save, delete the image stored at the original image path.

See this answer too (Josh's answer is the one I used and prefer as it doesn't hit the database).

Django: When saving, how can you check if a field has changed?

↙厌世 2024-10-31 01:34:54

如果我理解正确,如果您重命名文件,那么该文件会被复制而不是被移动。重写 Page 类的 save 方法可以让您访问旧实例和 dew 实例。
http://docs.djangoproject.com/en/ dev/topics/db/models/#overriding-model-methods

您需要做的就是将旧文件名存储在变量中,然后在调用 super.save() 之后您可以
os.system("rm "+path_to_file)
在文件更改的情况下。
这有帮助吗?

If i understand correctly, if you rename a file , than the file gets duplicated instead of moved. Overriding the save method for Page class can get you access to the old and dew instance.
http://docs.djangoproject.com/en/dev/topics/db/models/#overriding-model-methods

All you need to do is store the old filename in a variable, then after calling super.save() you can
os.system("rm "+path_to_file)
in the cases when the file changed.
Does this help?

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文