本文介绍了Collectstatic创建空文件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试将应用程序升级到Django 1.11,但是遇到collectstatic的问题.

I'm trying to upgrade an app to Django 1.11, but experience issues with collectstatic.

旧版本:

django 1.8.17 
django-storages 1.5.1

新版本:

django 1.11.12
django-storages 1.6.6

存储空间:

class StaticS3BotoStorage(ManifestFilesMixin, S3BotoStorage):
    location = 'static'
    file_overwrite = True
    preload_metadata = True

class StaticS3BotoStorage(CachedFilesMixin, S3BotoStorage):
    location = 'static'
    file_overwrite = True
    preload_metadata = True

对于旧版本,collectstatic可以很好地工作,包括collectstatic --clear.

With the old versions, collectstatic worked fine, including collectstatic --clear.

升级后,collectstatic --clear失败(不删除任何文件).collectstatic确实会复制文件,但是,有时它会创建同一文件的两个版本.在此特定示例中,我得到了base.hash1.cssbase.hash2.css. base.hash2.css为空,因此页面打开,但显示不正确.

After the upgrade, collectstatic --clear fails (no files are deleted).collectstatic does copy files, however, sometimes it creates two versions of the same file. In this particular example, I get base.hash1.css and base.hash2.css. base.hash2.css is empty, so the pages open, but do not render correctly.

如果我不使用CachedFilesMixinManifestFilesMixin,则collectstatic可以正常工作,但清除仍然失败.

If I don't use CachedFilesMixin or ManifestFilesMixin, collectstatic works fine, but clear still fails.

我测试了django 1.11和django-storages的不同组合,但是它们的表现似乎都相同.

I tested different combinations of django 1.11 and django-storages, but they all seem to behave the same.

其他人也遇到过类似的问题吗?

Did someone else experience a similar issue?

推荐答案

我们遇到了相同的问题.

We've encountered the same issue.

我认为潜在的问题有多个问题/来源:

The underlying problem, I think, has multiple issues / sources:

  • ManifestFilesMixin使用并重用ContentFile对象来生成散列文件并将其保存多次.无需重置ContentFile对象(通过对它们调用.seek(0)).
  • S3BotoStorage保存这些文件,而不检查它们是否在正确的位置.将此与FileSystemStorage进行比较:始终通过迭代文件的.chuncks()从头开始读取文件.

我们通过像这样覆盖S3BotoStorage来解决空文件问题:

We worked around the empty-file-issue by overriding S3BotoStorage like this:

class PatchedS3StaticStorage(S3BotoStorage):
    def _save(self, name, content):
        if hasattr(content, 'seek') and hasattr(content, 'seekable') and content.seekable():
            content.seek(0)
        return super()._save(name, content)

简而言之,我们在保存文件之前先查找文件的开头.

In short, we seek to the beginning of the file before saving it.

这篇关于Collectstatic创建空文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-23 09:07