質問内容は見出しの通りです。
例えば、あるサイトにアクセスがあるたびにあるデータベースに含まれる数値型の値に1を足していくという実装があるとします。もしそのサイトに全く同タイミングでアクセスがあると、同時に値を参照しそれに1を足すわけですから本来<元の数>+2
になるべきであるところ結果<元の数>+1
になると思います。
こういう問題は一般的に何という名称がつけられていますか?また、整合性を保つには一般的にどのような対策が取られているのでしょうか?
気になる質問をクリップする
クリップした質問は、後からいつでもMYページで確認できます。
またクリップした質問に回答があった際、通知やメールを受け取ることができます。
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
回答4件
0
ベストアンサー
こういう問題は一般的に何という名称がつけられていますか?
単に排他制御不備でもよいですが、TOCTOU競合と呼ばれます。
Time of check to time of use - Wikipedia
また、整合性を保つには一般的にどのような対策が取られているのでしょうか?
一般的にということであれば、排他制御です。
ただ、特定の列を +1 するだけであれば、以下のように単一のSQL文で実行すれば問題ないと思います。
UPDATE table1 SET columX = columX + 1 WHERE -- 以下略
データの取得と+1を別のSQL文で実行する場合は、トランザクションと当該行のロックで対応します。
投稿2021/08/16 06:26
総合スコア11705
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
0
全く同タイミングでアクセス
厳密にいえば全く同じタイミングというのはありません。
処理Aが参照中に処理Bが発生する可能性はありますが
トランザクションで処理をすればある程度競合を防げますが
可能であればテーブル側にユニーク制限をかけておくことです
またインクリメントだけを目的としたカラムは
途中でデータ修正や削除があった場合に競合や欠番が発生する
可能性があるためあまり現実的ではないので、
auto_incrementなどで順番を確保した上でランク付け関数などで
都度計算するほうが現実的です
投稿2021/08/16 04:53
総合スコア116724
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
0
DB側の仕組みでオートインクリメントをするとか
DB側でシーケンス払い出すとか
具体的な対策はDBによります。
そもそも重複する可能性のある実装になってしまっている時点で設計の考慮不足です。
こういう問題は一般的に何という名称がつけられていますか?
問題も何も実装の通り動いているのでバグでも何でもありません。
名前も付けようがないのでは(あったとしても先の通り設計考慮不足の実装なので何とも)
「キーが重複するような実装になっている(duplicate key)」とそのままです。
投稿2021/08/16 04:37
編集2021/08/16 04:44総合スコア80875
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2021/08/17 11:49
2021/08/17 12:08
2021/08/17 12:22
2021/08/17 12:31 編集
0
レコードに対する排他制御で処理します。
例えば、連番を採番したい場合。
テーブルに採番用のレコードを1件作成し、これに番号項目を設けます。
1回目→値:1。レコード確保、1番を取得し、次アクセス用に+1でUpdate、開放
2回目→値:2。レコード確保、2番を取得し、次アクセス用に+1でUpdate、開放
3回目→値:3。レコード確保、3番を取得し、次アクセス用に+1でUpdate、開放
同時に、アクセスあった場合には、データベースが自動的に優先順位を付けて、順次処理します。後回しになったアクセス処理は、前の処理が終了するまで、待ち合わせがされます。この部分の制御も、データベースが全て自動で管理してくれます。
一定時間待ち合わせても、レコードの開放が成されずに、使用する事が出来なかった場合には、使用中でタイムアウトエラーとなります。
投稿2021/08/16 07:02
編集2021/08/16 07:03総合スコア553
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
あなたの回答
tips
太字
斜体
打ち消し線
見出し
引用テキストの挿入
コードの挿入
リンクの挿入
リストの挿入
番号リストの挿入
表の挿入
水平線の挿入
プレビュー
質問の解決につながる回答をしましょう。 サンプルコードなど、より具体的な説明があると質問者の理解の助けになります。 また、読む側のことを考えた、分かりやすい文章を心がけましょう。