(Simple) Read-Only SqlAlchemy Sessions
July 16, 2009
The Right Way™ to make database access read-only is to create a read-only user. So, why not just Do It Right™ ?
- Not all databases (eyes at you Sqlite!) support these fancy “users”
- Sometimes creating this second user (and changing configuration files during program invocation) is overkill, or a hassle.
- During development, it’s nice to be able to temporarily make a database read-only, or read-only from a particular session.
- I am very lazy.
In SQLAlchemy, there is a simple solution : monkeypatch the session.flush method.
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
## Based on code by Yannick Gingras
def abort_ro(*args,**kwargs):
''' the terrible consequences for trying
to flush to the db '''
print "No writing allowed, tsk! We're telling mom!"
return
def db_setup(connstring='sqlite:///:memory:',
echo=False, readonly=True):
engine = create_engine(connstring, echo=echo)
Session = sessionmaker(bind=engine, autoflush=False, autocommit=False)
session = Session()
if readonly:
session.flush = abort_ro # now it won't flush!
return session, engine
Session objects are still writable within the session, and this functionality can now be enforced at the session level.