0

私は現在、ECショッピングサイトで働いています。ユーザーがいつでもどこからでも注文を送信できることを説明する必要はまったくありません。

MySql データベースには 2 つのテーブルがorderありorder_details(他にもあります)、簡単に想像できる注文の詳細を維持するため、両方のテーブルの構造全体を説明する必要はないと思います。

orderテーブルには基本的にorder_id、自動インクリメントされた主キーなどのフィールドとorder_dateorder_statusこのコンテキストでは必要のないその他のフィールドが含まれています。

order_detailsテーブルには基本的に、テーブルの外部キーなどのフィールドが含まれてorder_idますorderproduct_nameproduct_price

顧客が注文を送信すると、作成される最初のエントリがテーブルにあり、このテーブルorderに基づいて、order_idこの注文の詳細がテーブルに挿入されorder_detailsます。

テーブルに挿入するには、注文order_detailsテーブルから適切なorder_idものをフェッチする必要があります (これは自動インクリメントされるため、事前に取得することはできません)。私は現在、このようなテーブルからこれを取得しています。order_idorder

select max(order_id) from order;

この SQL ステートメントはテーブルorder_idから最新order情報を取得し、この値を使用して、特定の注文の詳細をテーブルに挿入できorder_detailsます。

ここで、現在、ショッピング カートにいくつかの製品を含む注文を送信しているとします。私の注文はorderテーブルに正常に挿入されましたが、テーブルに挿入する前 (およびテーブルから最大値order_detailsを取得する前) に、何らかの理由でサーバー上のオペレーティング システム スケジューラによってこのプロセスが切り替えられ、別の顧客の注文とその処理が実行されます。別の顧客の注文が完全に完了します (との両方のテーブルに挿入されます)。 order_idorderorderorder_details

この注文処理 (別の顧客の注文) が完了した後、まだ保留中の注文が実行を開始し、テーブルから最大値を取得する前に切り替えられました。 上記の SQL ステートメントが実行されると、別の顧客の注文に関連し、私のものには関連しないテーブルからがフェッチされ、トランザクションが矛盾した状態になります!order_idordermax order_idorder

私が聞きたいのは、常に特定の注文に関連し、トランザクションがいつでも一貫性のない状態で終了しないことを保証する適切なものをテーブルorder_idから正しくフェッチする方法です。そうする正しい方法は何ですか?order

4

1 に答える 1

1

MySQL の関数は、現在の接続LAST_INSERT_ID()での最後の操作の最初の成功した挿入から自動インクリメントされた値を返します。INSERT

通常、MySQL API は、この関数呼び出しの周りに何らかのラッパーを提供しますmysql_insert_id()(PHP など)。

于 2012-05-09T15:08:09.530 に答える