orm(object relational mapping):对象关系映射。
python面向对象,而数据库是关系型。
orm是将数据库关系映射为Python中的对象,不用直接写SQL。
缺点是性能略差。
通过sessionmaker,我们得到一个类,一个能产生session的工厂。
我们可以用这个类的对象来操作数据库。example:
from sqlalchemy import create_engine from sqlalchemy.orm import sessionmaker # an Engine, which the Session will use for connection # resources some_engine = create_engine('postgresql://scott:tiger@localhost/') # create a configured "Session" class Session = sessionmaker(bind=some_engine) # create a Session session = Session() # work with sess myobject = MyObject('foo', 'bar') session.add(myobject) session.commit()
然而,此时如果我们再创建一个Session对象的时候,新的对象和原来的对象是不同的:
...... >>> session1 = Session() >>> session2 = Session() >>> session1 is session2 False
而使用scoped_session的目的主要是为了线程安全。
scoped_session类似单例模式,当我们调用使用的时候,会先在Registry里找找之前是否已经创建session了。
要是有,就把这个session返回。
要是没有,就创建新的session,注册到Registry中以便下次返回给调用者。
这样就实现了这样一个目的:在同一个线程中,call scoped_session 的时候,返回的是同一个对象:
>>> from sqlalchemy.orm import scoped_session >>> from sqlalchemy.orm import sessionmaker >>> session_factory = sessionmaker(bind=some_engine) >>> Session = scoped_session(session_factory) >>> some_session = Session() >>> some_other_session = Session() >>> some_session is some_other_session True
scoped_session实现了代理模式。能够将操作转发到代理的对象中去执行:
Session = scoped_session(some_factory) # equivalent to: # # session = Session() # print(session.query(MyClass).all()) # print(Session.query(MyClass).all())
scoped_session的实现使用了thread local storage技术,使session实现了线程隔离。这样我们就只能看见本线程的session。
ref:http://docs.sqlalchemy.org/en/latest/orm/contextual.html#unitofwork-contextual
https://farer.org/2017/10/28/sqlalchemy_scoped_session/
http://docs.sqlalchemy.org/en/latest/orm/session_basics.html#session-faq-whentocreate
http://hshsh.me/post/2016-04-10-python-proxy-class-examples/