skip to navigation
skip to content

Not Logged In

Alchemyware 0.6

WSGI middleware for SQLAlchemy.

Warning: We are not sure whether the use of SessionContext is appropriate or if using plain Sessions is good enough given that we create a new Session for each request. Feedback much appreciated.

Alchemyware is a piece of WSGI middleware for incorporating SQLAlchemy into your WSGI stack of middleware/applications. It works by setting an 'alchemyware' environ key that holds a mapping of engine identifiers (any name you decide to call your engine(s)) to SQLAlchemy session objects (one for each engine). The subsequent WSGI middlware/apps can then use these session objects for DB access by referencing that environ key. You get a fresh SQLAlchemy session object per engine with every HTTP request. Also, a helper class called AlchemyEngines is available for use outside a WSGI web context.

You must initialise Alchemyware with a dictionary where each key is an engine identifier and its value is a dictionary with an 'engine' and (optionally) a 'model_init' key. The 'engine' key holds a dictionary of SQLAlchemy create_engine() parameters, such as 'dburi' and 'echo', while the 'model_init' key holds a string which is the module path to a model initialiasation function. For example, in the file where middleware is wrapped:

import Alchemyware
params = {'eng1': {'engine': {'dburi': 'sqlite://', 'echo': True},
                   'model_init': 'myapp.models.model.initialise'},
          'eng2': {'engine': {'dburi': 'sqlite://'}}}
app = Alchemyware(app, params)

In the above example we create two sqlite engines, one called 'eng1', the other called 'eng2'. For 'eng1', we also pass the path to a function that initialises a model. Alchemyware will do the initialisation at __init__() time and the mapping will be available through out the life of the application. The myapp/models/model.py file looks like:

# Main class used by everyone.
class Companies(object):
    pass

# initialise() function takes a metadata object and an engine identifier,like
# 'eng1'.
def initialise(metadata, db_key):
    companies = Table('companies', metadata,
                      Column('co_id',String(12), primary_key=True),
                      Column('postcode',String(15)))
    mapper(Companies, companies, primary_key=[companies.c.co_id])

The resulting environ['alchemyware'] dictionary looks like:

{'eng1': {'session': <sqlalchemy.orm.session.Session object at 0xb30ed06c>},
 'eng2': {'session': <sqlalchemy.orm.session.Session object at 0xb30ed10c>}}

Last, the AlchemyEngines class can be used for testing outside a WSGI web context:

>>> from alchemyware import AlchemyEngines
>>> params = {'eng1': {'engine': {'dburi': 'sqlite://'}}}
>>> engines = AlchemyEngines(params)
>>> engines.get_engine('eng1')
<sqlalchemy.engine.base.Engine object at ...>
File Type Py Version Size # downloads
Alchemyware-0.6.tar.gz (md5) Source 6KB 357