I have the following script and it's meant to be a standalone Django script so I can run python my_script.py
from the command line. It used to work with Django 1.8, after I upgrade to Django 1.11, I'm getting the following error:
Traceback (most recent call last): File "app.py", line 8, in <module> django.setup() File "C:\python27\lib\site-packages\django-1.11.5-py2.7.egg\django\__init__.py", line 22, in setup configure_logging(settings.LOGGING_CONFIG, settings.LOGGING) File "C:\python27\lib\site-packages\django-1.11.5-py2.7.egg\django\conf\__init__.py", line 56, in __getattr__ self._setup(name) File "C:\python27\lib\site-packages\django-1.11.5-py2.7.egg\django\conf\__init__.py", line 41, in _setup self._wrapped = Settings(settings_module) File "C:\python27\lib\site-packages\django-1.11.5-py2.7.egg\django\conf\__init__.py", line 110, in __init__ mod = importlib.import_module(self.SETTINGS_MODULE) File "C:\python27\lib\importlib\__init__.py", line 37, in import_module __import__(name) ImportError: Import by filename is not supported.
This is my python script
# standalone django setup import os, sys, logging, django prj_dir = os.path.abspath(os.path.dirname(os.path.dirname(__file__))) logging.basicConfig(level=logging.INFO) logging.info("PRJ_DIR: %s" % prj_dir) sys.path.append(prj_dir) os.environ.setdefault("DJANGO_SETTINGS_MODULE", "%s.settings" % prj_dir.split("/")[-1]) django.setup() ... ...
6 Answers
Answers 1
It seems you're trying to split a file path by the forward slash /
while running your script on Windows where path separator is the backslash \
. Use os.path.basename
instead of manually dealing with the stings (.split("/")[-1]
):
>>> import os >>> os.path.basename(r'/home/user/project') 'project' >>> os.path.basename(r'c:\users\user\project') 'project'
In comparison:
>>> r'/home/user/project'.split("/")[-1] 'project' # works >>> r'c:\users\user\project'.split("/")[-1] 'c:\\users\\user\\project' # error
Answers 2
Don't reinvent the wheel. There is a cool manage command on django extensions that lets you run scripts on the django context.
https://django-extensions.readthedocs.io/en/latest/runscript.html
Answers 3
Others have pointed out an issue with your path manipulation, however the cause of your actual import exception is that you are setting DJANGO_SETTINGS_MODULE
to the name of a file.
It needs to be the name of a Python module. In other words, your settings file should end in .py
and you should pass the name of it (without .py
), or the importable path to it - exactly as you would type it in an import
statement.
If your settings are in my_settings.py
, then you would set the variable to my_settings
.
Here is a simplified example of a one-page django application taken from the excellent Lightweight Django book's excerpt:
import sys from django.conf import settings settings.configure( DEBUG=True, SECRET_KEY='thisisthesecretkey', ROOT_URLCONF=__name__, MIDDLEWARE_CLASSES=( 'django.middleware.common.CommonMiddleware', 'django.middleware.csrf.CsrfViewMiddleware', 'django.middleware.clickjacking.XFrameOptionsMiddleware', ), ) from django.conf.urls import url from django.http import HttpResponse def index(request): return HttpResponse('Hello World') urlpatterns = ( url(r'^$', index), ) if __name__ == "__main__": from django.core.management import execute_from_command_line execute_from_command_line(sys.argv)
Answers 4
The error is in
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "%s.settings" % prj_dir.split("/")[-1])
If you run this script from the same folder as manage.py, it will return the name of the manage.py folder instead settings.py folder resulting managepy_folder.settings
when it should output settingspy_folder.settings to access the app
Test with :
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "settingspy_folder.settings")
if it that was the problem, if you want use the same algorithm or something similar in multiple projects, you need a pattern to modify the current folder name to indicate the settings.py folders name, using the same folders name in both wouldn't require modification.
if that doesn't fix please post your settings.py file
Answers 5
If your script is in the same folder as settings.py, the code should be like this:
import os, sys, logging, django prj_dir = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) logging.basicConfig(level=logging.INFO) logging.info("PRJ_DIR: %s" % prj_dir) sys.path.append(prj_dir) os.environ.setdefault("DJANGO_SETTINGS_MODULE", "{}.settings".format(os.path.basename(prj_dir))) django.setup()
else, if your script is in the parent folder of settings.py:
import os, sys, logging, django prj_dir = os.path.dirname(os.path.abspath(__file__)) logging.basicConfig(level=logging.INFO) logging.info("PRJ_DIR: %s" % prj_dir) sys.path.append(prj_dir) os.environ.setdefault("DJANGO_SETTINGS_MODULE", "{}.settings".format(os.path.basename(prj_dir))) django.setup()
Answers 6
in the line: os.environ.setdefault( "DJANGO_SETTINGS_MODULE", "myproject.settings") # should be like in import command )
Just use python module path: like "myproject.settings" instead of path like /opt/myproject/settings" or "c:\myproject\settings.py"
0 comments:
Post a Comment