package that works inside and outside django. Is this a good design?
Question: I'm relative new to django and in generall to the python world. But I have
experience with ruby (been working with rails for 2 years) so many concepts of
python/django are not that new to me.

Anyway, I am writing an small package in python that will have a database
connection and I want to use this package inside django but also in the
feature outside django. So I decided take advantage of **django.db** and not
worry about writing any database connection and managment stuff.

So I started writing my first models and wanted to make a first test outside
of a django environment and I'm finding myself with some difficulties.

I thought about having the same configuration mechanism for my package as for
any django application (I mean the settings.py file). I wrote a file (called
nodjango_settings.py as a template) that only contains the DATABASES
dictionary and added two custom variables to it:

    
    
    MYAPP_DB_ID   = "myappdb"
    MYAPP_DB_PREFIX = "myapp_"
    DATABASES = {
      MYAPP_DB_ID: {
        'ENGINE': 'django.db.backends.postgresql_psycopg2',
        'NAME':   'myappdb',
      }
    }
    

The directory structure of my package is:

    
    
    .
    |-- README.txt
    |-- doc
    |   `-- db.txt
    |-- setup.py
    |-- src
    |   |-- __init__.py
    |   `-- myapp
    |       |-- __init__.py
    |       |-- exceptions.py
    |       |-- models.py
    |       |-- nodjango_settings.py
    |       `-- nodjango_settings.pyc
    `-- test
        `-- test.py
    

I was reading a little bit of djangos own code to see how to handle the
DJANGO_SETTINGS_MODULE environment variable and read the configuration file,
so added the following code to `myapp/__init__py`.

    
    
    import os
    
    # try to look after the DJANGO_SETTINGS_MODULE environment variable
    # if not present raise an import error
    
    # code abstract from python2.6/site-packages/django/conf/__init__.py
    try:
        settings_module = os.environ["DJANGO_SETTINGS_MODULE"]
        if not settings_module: # If it's set but is an empty string.
            raise KeyError
    except KeyError:
        raise ImportError("The DJANGO_SETTINGS_MODULE environment variable is not present.")
    
    
    # TODO: look at python2.6/site-packages/django/conf/__init__.py +93
    # if you print sys.path then the project directory gets added
    # in django/core/management/__init__.py with sys.path.append
    from django.utils import importlib
    
    p = importlib.import_module(settings_module)
    
    print p.MYAPP_DB_ID
    

I wanted to test that `__init__.py` works as intended so on the root directory
of my package I ran:

    
    
    $ DJANGO_SETTINGS_MODULE="src.myapp.nodjango_settings" python src/myapp/__init__.py
    
    
    Traceback (most recent call last):
      File "src/myapp/__init__.py", line 22, in <module>
        p = importlib.import_module(settings_module)
      File "/home/yanez/devpython/lib/python2.6/site-packages/django/utils/importlib.py",   line 35, in import_module
        __import__(name)
    ImportError: No module named src.myapp.nodjango_settings
    

I didn't expect that. When you create a new django application a `manage.py`
file is created. And this file sets `DJANGO_SETTINGS_MODULE` the variable to
the settings.py file from the perspective of the root directory of the
application.

I read more code of django and realized that in
`django/core/management/__init__.py` the root directory of the application is
added to `sys.path`. This could also be the solution to my problem but I'm not
quite sure whether it's a good idea to mess with `sys.path` or not.

I'm not quite sure whether my idea is a good one or a bad one. I'd like to
know what you think about it and where/how I can improve it. Beside, if I
stick to my idea, how can I read my custom varaibles in `settings.py` without
having to reimport the settings module over and over?

Thanks


Answer: When deploying a django project with mod_wsgi, one have to write a wsgi
(python) script, that does the "sys.path" dance and sets the
DJANGO_SETTINGS_MODULE environment variable, then create the wsgi application
object etc.

Why do I mention this ? Because, IMHO, you should not try to handle this part
of the problem within "myapp", but from a distinct python script that would be
the application entry point when using your app outside a django project
context, and keep "myapp" as a pure library package. This launcher script
would then take care of setting up the correct environement (sys.path,
settings, whatever). For the record, the settings module is just a Python
module, which at runtime is an ordinary python object (instance of class
"module"), and there are quite a few ways (other than the default import
mechanism) to create a module instance and add it to sys.modules (which is the
important point here).

As a side note, having the settings in the packages doesn't make sense IMHO,
it's a configuration file.

Edit : well, I knew there was something about using part of django standalone,
and here it is: <https://docs.djangoproject.com/en/dev/topics/settings/#using-
settings-without-setting-django-settings-module>

