django-compressor: изображения CSS с путем относительно папки

Я использую django-compresor для приложения, развернутого на героку, с amazon S3, обслуживающим статические файлы. Все работает нормально, за исключением того, что изображения в моем css, на которые есть ссылки в background-image: url(), не отображаются с правильным путем.

Мои статические файлы организованы в следующую структуру каталогов:

-static
    -myapp
        -js
        -css
        -img
    -bootstrap
        -js
        -css
        -img
    -othervendor
        -js
        -css
        -img

Поэтому путь, который я использую в url(), относится к файлу css:

url("../img/icon.png")

Все мои файлы css сжимаются и перемещаются в папку CACHE в моем статическом каталоге, а URL-адрес каталога CACHE отображается правильно:

https://mybucket.s3.amazonaws.com/static/CACHE/css/somehash.css

Проблема в том, что изображения в файлах css url() отображаются как:

https://mybucket.s3.amazonaws.com/static/CACHE/img/imagefile.png

и это должно быть:

https://mybucket.s3.amazonaws.com/static/myapp/img/imagefile.png

или если изображения были скопированы в каталог CACHE, это сработает:

https://mybucket.s3.amazonaws.com/static/CACHE/img/imagefile.png

Мое временное исправление состоит в том, чтобы изменить пути изображений в моем css на следующее, и оно работает:

url("/static/foldername/img/icon.png")

Я новичок в django и компрессоре, поэтому я не уверен, каким должно быть правильное поведение, но это не похоже на правильное. Как я это вижу, проблема может быть решена, если я смогу заставить компрессор django сделать одну из двух вещей: 1) скопировать все изображения, на которые есть ссылки в css url(), в каталог CASHE/img ИЛИ 2) отобразить правильный URL-адрес, представленный ../ Вот моя установка:

Файлы css в моем шаблоне находятся в блоке {% Compress css %}.

s3utils.py (используется для создания отдельных медиа- и статических каталогов в моей корзине)

from storages.backends.s3boto import S3BotoStorage

StaticS3BotoStorage = lambda: S3BotoStorage(location='static')
StaticRootS3BotoStorage = lambda: S3BotoStorage(location='static')
MediaS3BotoStorage = lambda: S3BotoStorage(location='media')
MediaRootS3BotoStorage = lambda: S3BotoStorage(location='media')

settings.py

DEFAULT_FILE_STORAGE = 'myapp.settings.s3utils.MediaRootS3BotoStorage'
STATICFILES_STORAGE = 'myapp.settings.s3utils.StaticRootS3BotoStorage'

AWS_ACCESS_KEY_ID = os.environ.get('AWS_ACCESS_KEY_ID')
AWS_SECRET_ACCESS_KEY = os.environ.get('AWS_SECRET_ACCESS_KEY')
AWS_STORAGE_BUCKET_NAME = os.environ.get('AWS_STORAGE_BUCKET_NAME')

S3_URL = 'http://%s.s3.amazonaws.com/' % AWS_STORAGE_BUCKET_NAME
MEDIA_URL = S3_URL+'media/'
MEDIA_ROOT = S3_URL+'media/'
STATIC_URL = S3_URL+'static/'
STATIC_ROOT = S3_URL+'static/'

COMPRESS_STORAGE = STATICFILES_STORAGE 
COMPRESS_URL = STATIC_URL
COMPRESS_ROOT = STATIC_ROOT

Я думаю, что должна быть какая-то настройка, которая говорит компрессору копировать URL css("../img/image.png") в каталог CACHE/img???


person Arctelix    schedule 12.03.2013    source источник


Ответы (3)


У меня была такая же проблема!

для меня сначала казалось, что это проблема с компрессором. Я изменил префикс S3Storage Backend с

StaticS3Backend = lambda: S3BotoStorage(location='static')

to

class StaticS3Backend(S3BotoStorage):
    location = 'static'

потому что другой метод не установил правильное значение местоположения (оно осталось пустым)

Это решило проблему для меня.

person rosner    schedule 26.03.2013
comment
спасибо, я изучу это и дам вам знать, если у меня будут такие же результаты. - person Arctelix; 04.04.2013
comment
FWIW, этот метод не работал для меня. Мне пришлось вернуться к лямбда-методу, потому что он хотя бы частично сработал. Я использую django-compressor==1.3, django-storages==1.1.4 и boto==2.8.0. - person Brent O'Connor; 23.04.2013

Я вообще не нашел хорошего решения. Несколько хороших обсуждений здесь https://github.com/jezdez/django_compressor/issues/226

В вашем файле CSS используйте абсолютный путь, который указывает на URL-адрес изображения на вашем Amazon S3, и это заставит его работать. Но без слов, это глупо. Почему я хочу, чтобы моя локальная среда разработки и тестирования использовала образ из продукта? Иногда это даже неприемлемо. Скажем, вы хотите изменить изображение и протестировать его некоторое время. (Вы можете вручную загрузить новое изображение на s3 и вручную изменить все тысячи ссылок css на это изображение на новый URL-адрес. Опять же, глупо.)

Чуть лучше использовать {{STATIC_URL}} в вашем css для создания абсолютного пути вместо относительного пути. Да, вы можете использовать {{STATIC_URL}}, если добавите компрессор.filters.template.TemplateFilter, упомянутый здесь https://django_compressor.readthedocs.org/en/1.3/settings/#base-settings. Это решает многоступенчатую проблему. Но это не работает для локальной разработки, потому что вы не сжимаете здесь, и если вы это сделаете, вам будет сложно отладить.

Лично я считаю, что компрессор.filters.template.TemplateFilter внутри django-compressor неверен. Это должно быть частью django. Необязательный процесс, который вы можете включить для css и js.

person Gordon Sun    schedule 10.09.2013

Недавно я столкнулся с этим и решил это, установив COMPRESS_OUTPUT_DIR = ''. Это привело к тому, что сжатые файлы были сохранены в статическом корневом каталоге вместо каталога CACHE по умолчанию в статическом каталоге.

person Shoan    schedule 06.02.2018