问题描述
我正在尝试将应用程序升级到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.css
和base.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.
如果我不使用CachedFilesMixin
或ManifestFilesMixin
,则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创建空文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!