はじめに
ECCUBEに限ってではありませんが、よくECシステム側の在庫数が合わないと聞きます。
ECCUBEでは2,3,4系のどのバージョンすべてですが、どのバージョンでも、特定の条件のみズレます。特にECCUBEはキャンセルでも在庫を戻さないのでズレという認識になります、ECCUBEの場合、キャンセルを追加するには、別途プラグインなどの導入を検討する必要があります。
CS-CART v4.3系でも同様の現象があります。ただしCS-CARTではキャンセル等では在庫が戻ります。最新バージョンは調べてません・・ごめんなさい。
よく、私がお客さんに話すのは、販売可能な在庫であって、実在庫として管理できませんよと。
発生状況
- 1つの商品を同一時刻でとりあうアクセス集中するケース、期間限定での初日・最終日、タイムセール、某有名ゲーム機、在庫限定商品、ローバランサを使用している、今年でいえばマスク
- 管理画面による在庫修正・CSV一括取り込み・常時基幹連動する場合など
- ECCUBEの場合、キャンセル時
なぜおきるのか?
データベースのロストアップデートの状態になるケース
これは、1つのレコードで同時刻に、書き込みを行った場合、最後に書いた内容にもどってしまう現象
仮にAさんが8個とか購入していた場合、大幅に在庫がズレます。
おきないケース
これは、在庫を取り合わないケースとデータベースのトランザクションのロック機能を使った場合
トランザクションのロック機能を使用した場合、Bさんは赤矢印のプログラム等でかかる時間分待ちの状態になります。サーバーに負荷がかかっている場合は、サーバーの処理も遅いのでまちまち・・
トランザクションロック機能時のSQLコードの例
トランザクション機能でSelect for update を使う、MYSQL InnoDB AUTOCOMMIT 0の場合
$cart_quantity = 1 購入数量
BEGIN
SELECT quantity FROM stocks WHERE id = 1 for update 残り在庫数を確認する 注 for update
UPDATE stocks SET quantity = selectquantity - $cart_quantity WHERE id = 1;
COMMIT
実際に、処理するにあたっては、上記、以外に多くのコードが組み込まれます。
あと、カートに入れたときに、在庫計算するのか?決済完了後に行うのか?によって処理も変わるかと思います。カートに入れたときに問題になるのが在庫の独占、そのまま決済されず、放置された場合、ロスになります。決済完了時は、リンクタイプ、カード入力などあり、ロックの問題など。
これは、1人目が正しく現在の在庫を読む、在庫の計算をする、計算した在庫を書くといった一連の流れが完了するまで、該当の商品レコードを読み取り・書き込み不可にします。
したがって2人目はこれが、完了するまで処理できません。3人目もそうです・・4人・・・、待ち行列です。
データベースには、待ち時間の最大値があります。30秒とか、では待っている人がタイムアウトしてしまった人は(かご落ち)・・・、といろいろ考えると複雑なシステムになります。
ただ、アクセスが集中しないサイトであれば、どちらも問題にはなりません。ただ管理画面等、一括在庫編集などする場合は、必ずメンテナンス中などにすることで回避できます。
ロックしない場合は、ストレスなく待ち時間もなく購入ができ、待ち時間がない分より販売数があがります。ただ在庫がおかしくなる可能性が・・
どうすればよいの?
多くのECパッケージでは、トランザクションのロック機能ような対応がされていません。ASPなどのサービスは不明です。これはプラグインなどの拡張性、決済の種類など汎用性の兼ね合いかとおもいますが。
ECサイト側では、在庫の管理は行わず、別のバックボーン(基幹・配送システム連携)で行う。
在庫処分セールなど、メールマガジン等で配信する場合、数回に在庫を分け、それに合わせて配信するユーザー数を分けてメール配信するなど。工夫できます。
配送業務時等、実在庫を確認して、在庫があれば、配送、在庫なければキャンセル・もしくは、配達を遅らすという流れ。その後、現在の在庫をECシステムへ登録する。
カード決済の場合は、カードの与信だけとっておき、在庫確認後、カート引き落としを行います。
なのでECサイト側は、あくまでも販売可能在庫という概念。注文受付のみのイメージで考える。
いつでも発注できる商品であれば、特に在庫を設定せず、在庫無限で設定しておき、在庫がない場合、販売停止などの運用であれば、手間はないかもしれません。
某大手でも、コンビニ前払いなど頼んでみるとわかりますが、注文確認後、在庫確認中になります。在庫が準備されると、振込みコードが送られてきます。在庫がない場合。申し訳ございませんとメールがきます。
多くの場合が、自社ECサイトだけではなく、Yahoo、楽天なども展開しているかと思います。その場合、配送・在庫管理システムASPなどを使用すると思います。そういったことを含めた運用を考えたほうがよいかもしれませんね。。