2016-10-30 9 views
0

私はsqlalchemyを初めて使用しています。私はsqlalchemyを使用して、マルチスレッドWebアプリケーションでのDBの対話を処理したいと考えています。SQLAlchemy:スコープ付きセッションをリクエストにバインドする方法

だから、私は要求を処理MoinMoin Wikiを使用するので、私は要求を含むオブジェクトmacro.requestを持って

import sqlalchemy 
from sqlalchemy     import create_engine 
from sqlalchemy.orm    import sessionmaker, scoped_session 

engine   = create_engine('mysql://mydb') 
session_factory = sessionmaker(autocommit = False, 
           autoflush = False, 
           bind  = engine) 
Session   = scoped_session(session_factory) 

で始まります。

私は今、いくつかのクラスにメソッドを持って、

def do_sth(): 
    session = Session() 
    # use the session to get some data from the db 

どこで、どのように私はそれを要求Sessionオブジェクトがリンクしている伝えないと言いますか?

Multi-threaded use of SQLAlchemyを読む

、単一のセッションがScopedSessionレジストリ要請するすべての人のために維持されるように、それは、ストレージとしてデフォルトの用途[threading.local()]によるScopedSessionオブジェクト

を言いますが、単一スレッドのスコープ内でのみ実行できます。別のスレッドでレジストリを呼び出す呼び出し元は、そのスレッドにローカルなSessionインスタンスを取得します。

"レジストリを別のスレッドで呼び出す呼び出し元は、他のスレッドのローカルなSessionインスタンスを取得します。"

セッションインスタンスは、どのリクエストにリンクされているかを一度も伝えていないと、どのようにローカルになりますか?

答えて

0

SQLAlchemy documentationだから同じSessionオブジェクトを複数の呼び出しにわたって維持されているscoped_sessionの使用状況、当社の上記の例は、いくつかのプロセスがmutltipleは多くのスレッドで呼び出すような場所であることが必要であることを示唆している

を語ります実際には同じセッションのハンドルを取得しないでください。この概念をスレッドローカルストレージと呼びます。つまり、各アプリケーションスレッドごとに異なるオブジェクトを保持する特別なオブジェクトが使用されます。 Pythonはthreading.local()を使ってこれを提供します。

私は現在のスレッドのpid与えられたセッションからを取得する方法を考え出したていないにもかかわらずだから、threadingモジュールがスレッドにセッションをリンクするために使用されます。特に、1は、両方が同じスレッドで行われた場合だけSession()が2回の呼び出しで同じセッションを提供することをテストするために、問題の例では、セッションのhash key

session.hash_key 

を確認することができます。

要約すると、すべてのリクエストがスレッドによって処理される限り、セッションはリクエストに適切にリンクされます。

関連する問題