16

重複する行をデータベースに挿入する可能性のある複数のプロセスがあります。これらの挿入は頻繁に (1 時間ごとに数回) 発生するわけではないため、パフォーマンスは重要ではありません。

次のように、挿入を行う前に存在チェックを試みました。

#Assume we're inserting a camera object, that's a valid SQLAlchemy ORM object that inherits from declarative_base...
try:
  stmt = exists().where(Camera.id == camera_id)
  exists_result = session.query(Camera).with_lockmode("update").filter(stmt).first()

  if exists_result is None:
    session.add(Camera(...)) #Lots of parameters, just assume it works
    session.commit()
except IntegrityError as e:
  session.rollback()

私が直面している問題は、exist()チェックがテーブルをロックしないため、複数のプロセスが同じオブジェクトを同時に挿入しようとする可能性があることです。このようなシナリオでは、1 つのプロセスが挿入に成功し、他のプロセスは IntegrityError 例外で失敗します。これは機能しますが、私には「きれい」ではありません。

exists()チェックを行う前にカメラテーブルをロックする方法が本当に欲しいです。

4

1 に答える 1

8

おそらくこれはあなたにとって興味深いかもしれません:

https://groups.google.com/forum/?fromgroups=#!topic/sqlalchemy/8WLhbsp2nls

SQL を直接実行することにより、テーブルをロックできます。Elixir でそれがどのように見えるかはわかりませんが、単純な SA では次のようになります。

conn = engine.connect()
 conn.execute("LOCK TABLES ポインター書き込み")
 #conn で何かをする
 conn.execute("UNLOCK TABLES")

于 2013-01-25T13:08:22.317 に答える