Ответ 1
Недавно я столкнулся с этой проблемой на heroku, и запуск последней версии django-compressor (1.3) не решает проблему. Я предоставлю решение, которое я использую, а также объяснение проблем, с которыми я столкнулся на пути.
Решение
Я создал свой собственный "CssAbsoluteFilter", который удаляет настройки. DEBUG проверяет метод "Найти" следующим образом:
# compress_filters.py
from compressor.filters.css_default import CssAbsoluteFilter
from compressor.utils import staticfiles
class CustomCssAbsoluteFilter(CssAbsoluteFilter):
def find(self, basename):
# The line below is the original line. I removed settings.DEBUG.
# if settings.DEBUG and basename and staticfiles.finders:
if basename and staticfiles.finders:
return staticfiles.finders.find(basename)
# settings.py
COMPRESS_CSS_FILTERS = [
# 'compressor.filters.css_default.CssAbsoluteFilter',
'app.compress_filters.CustomCssAbsoluteFilter',
'compressor.filters.cssmin.CSSMinFilter',
]
Абсолютные URL теперь всегда работают для меня независимо от того, является ли DEBUG = True или False.
Проблема
Проблема связана с параметром "compressor.filters.css_default.CssAbsoluteFilter", вашим параметром DEBUG и тем фактом, что у heroku есть файловая система только для чтения и перезаписывает файлы приложений каждый раз при развертывании.
Причина, по которой сбой работает правильно на вашем сервере разработки, заключается в том, что CssAbsoluteFilter всегда будет находить ваши статические файлы, когда DEBUG = True, даже если вы никогда не запускаете "collectstatic". Он ищет их в STATICFILES_DIRS.
Когда DEBUG = False на вашем рабочем сервере, CssAbsoluteFilter предполагает, что статические файлы уже собраны в ваш COMPRESS_ROOT и не будут применять абсолютный фильтр, если он не может найти файлы.
Jerdez, автор django-compressor, объясняет это следующим образом:
CssAbsoluteFilter работает с DEBUG = False, если вы успешно предоставили файлы для работы. Во время разработки компрессоры используют статический поиск файлов как удобство, поэтому вам не нужно постоянно запускать коллекцию.
Теперь для героку. Несмотря на то, что вы сохраняете свои статические файлы на S3, вам также нужно хранить их на герою (с помощью CachedS3BotoStorage). Поскольку heroku является файловой системой только для чтения, единственный способ сделать это - позволить героку автоматически собирать ваши статические файлы во время развертывания (см. https://devcenter.heroku.com/articles/django-assets).
По моему опыту, запуск "heroku run python manage.py collectstatic --noinput" вручную или даже в вашем Procfile будет загружать файлы на S3, но он НЕ будет сохранять файлы в вашем каталоге STATIC_ROOT (какой компрессор использует по умолчанию как COMPRESS_ROOT). Вы можете подтвердить, что ваши статические файлы были собраны на герою, используя "heroku run ls path/to/gather".
Если ваши файлы были собраны на геройку успешно, вы также сможете сжать ваши файлы, без решения, которое я предоставил выше.
Однако, похоже, герой будет собирать только статические файлы, если вы внесли изменения в свои статические файлы с момента последнего развертывания. Если в ваши статические файлы не были внесены изменения, вы увидите что-то вроде "0 из 250 статических файлов, скопированных". Это проблема, потому что heroku полностью заменяет ваше содержимое приложения при развертывании, поэтому вы теряете все статические файлы, которые ранее были собраны в COMPRESS_ROOT/STATIC_ROOT. Если вы попытаетесь сжать ваши файлы после того, как собранные файлы больше не существуют на heroku, а DEBUG = False, CssAbsoluteFilter не заменит относительные URL-адреса с абсолютными URL-адресами.
Мое решение выше избегает проблемы герой в целом и заменяет относительные URL-адреса css абсолютными URL-адресами, даже когда DEBUG = False.
Надеемся, что другие люди также найдут эту информацию полезной.