Я перемещаю веб-приложение из среды Windows в CentOS 5.11 и Apache, и со всем установленным я получаю 500
, когда пытаюсь загрузить сайт. Журнал ошибок показывает это:
mod_wsgi (pid=5461): Target WSGI script '/usr/local/treehouse/wsgi/index.wsgi' cannot be loaded as Python module.
mod_wsgi (pid=5461): Exception occurred processing WSGI script '/usr/local/treehouse/wsgi/index.wsgi'.
Traceback (most recent call last):
File "/usr/local/treehouse/wsgi/index.wsgi", line 11, in <module>
from django.core.wsgi import get_wsgi_application
ImportError: No module named 'django.core.wsgi'
Я нашел этот вопрос (и связанные с ним), который кажется похожим, но ни один из ответов не устраняет проблему. Я не работаю в virtualenv
, и django, кажется, установлен правильно, так как я могу запустить оскорбительный оператор:
>>> from django.core.wsgi import get_wsgi_application
в интерактивном интерпретаторе Python, и он работает отлично. Здесь script вызывает ошибку (это просто значение по умолчанию index.wsgi
, которое вы видите везде, где вы ищете этот материал):
import os, sys
sys.path.append('/usr/local/treehouse/apple')
sys.path.append('/usr/local/treehouse/apple/apple')
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "apple.settings")
from django.core.wsgi import get_wsgi_application application = get_wsgi_application()
Очевидно, последняя строка вызывает ошибку, но здесь интересная часть: последняя строка остается проблемой, даже если я добавляю ее чуть выше:
import django.core
import django.core.handlers
Оба базовых пакета импорта без заминки (django.core.wsgi
- это всего лишь тонкая оболочка вокруг некоторой функциональности в django.core.handlers.wsgi
). Это происходит только тогда, когда я пытаюсь получить доступ к пакетам wsgi
, с которыми возникают проблемы. Проверка sys.path
внутри этого script показывает все правильные каталоги (/usr/local/lib/python3.4/site-packages
и т.д.). И опять же, запуск того же кода из интерактивного интерпретатора не вызывает ошибок.
Я попробовал удалить/переустановить django (pip install django==1.6.5
), затем я reset виртуальную машину на полностью чистый моментальный снимок и перестроить/переустановить все, и все же я получаю то же самое поведение.
Что происходит?
Некоторые из исходных файлов django, спрятанные на pip
, сохраняются с окончанием строки Windows: они заканчиваются на \r\n
, а не \n
. В системах * nix это приводит к нарушению импорта в затронутых файлах, потому что вместо поиска django.core.wsgi
он пытается импортировать django.core.wsgi\r
.
Вот почему django.core.handlers
все еще можно импортировать: файл __init__.py
пуст, поэтому нет окончаний строк для коррумпирования.
Чтобы исправить это, запустите dos2unix
в затронутых файлах. Я не уверен, сколько файлов действительно затронуто (за исключением того, что многие из них), поэтому я просто ударил их из Python script из интерпретатора:
import os
from os.path import abspath, join
for root, _, files in os.walk('/usr/local/lib/python3.4/site-packages/django'):
for f in files:
os.system('dos2unix %s' % abspath(join(root, f)))
Et voilà, больше ошибок импорта!
Я наткнулся на эту проблему после того, как я начал взламывать исходные файлы django
в отчаянии. Я отредактировал django/core/__init__.py
(обычно пустой), добавив следующее:
from . import wsgi
Я изменил index.wsgi
, чтобы включить это:
import django.core
django.core.wsgi # no-op to see if we can access it
и закончилась увлекательной новой ошибкой:
Traceback (most recent call last):
File "/usr/local/treehouse/wsgi/index.wsgi", line 11, in <module>
import django.core
File "/usr/local/lib/python3.4/site-packages/django/core/__init__.py", line 1, in <module>
from . import wsgi
File "/usr/local/lib/python3.4/site-packages/django/core/wsgi.py", line 1, in <module>
from django.core.handlers.wsgi import WSGIHandler
ImportError: No module named 'django.core.handlers.wsgi'
Итак, из django/core/__init__.py
я могу получить доступ к django/core/wsgi.py
. Но django.core.handlers.wsgi
находится вне досягаемости. Я удалил изменения, чтобы воспроизвести исходную ошибку, но ошибка изменилась. Теперь я получал No module named 'django.core.handlers.wsgi'
даже без явного относительного импорта.
Это было, когда он ударил меня. Я открыл django/core/handlers/wsgi.py
в gedit, нажал на конец строки, нажал пробел, удалил вставку и сохранил файл. Это должно было быть не-op. Но когда я перезапустил сервер, вдруг ошибка импорта переместилась на другой импорт django. Единственным логическим объяснением было то, что окончание строк было неправильным, и, повторно сохраняя файл в gedit, я молча их исправлял.