You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

CodeIgniter中基于FIFO的库存盘亏弃置表更新问题求助

CodeIgniter FIFO规则更新弃置表逻辑修正

核心逻辑梳理

要实现FIFO扣减,需按最早批次优先扣至0,剩余扣减额顺延至下一批次的规则执行,步骤如下:

  1. 计算需扣减的总量:deduct_total = 系统库存数 - 实物盘点数(仅当deduct_total > 0时执行后续操作)
  2. 按FIFO顺序(如批次创建时间升序/批次号升序)查询该商品的有效弃置批次(数量>0的记录)
  3. 遍历批次记录,逐次扣减:
    • 若当前批次数量 ≤ 剩余扣减额:将该批次数量置为0,剩余扣减额减去当前批次数量
    • 若当前批次数量 > 剩余扣减额:将该批次数量减去剩余扣减额,剩余扣减额置0,终止循环
  4. 批量更新弃置表,同时开启事务保证数据一致性

修正后的update_complete函数示例(CodeIgniter模型方法)

public function update_complete($item_id, $system_qty, $actual_qty)
{
    // 计算需扣减的总量
    $deduct_total = $system_qty - $actual_qty;
    if ($deduct_total <= 0) {
        return true; // 无需扣减,直接返回
    }

    // 开启数据库事务
    $this->db->trans_start();

    // 1. 更新库存表(你已完成的逻辑,保留示意)
    $this->db->set('stock_qty', $actual_qty)
             ->where('item_id', $item_id)
             ->update('inventory_table');

    // 2. 按FIFO顺序获取需扣减的弃置批次(按created_at升序确保最早批次优先)
    $batches = $this->db->select('id, qty')
                        ->where('item_id', $item_id)
                        ->where('qty >', 0)
                        ->order_by('created_at', 'ASC')
                        ->get('disposal_table')
                        ->result_array();

    $remaining_deduct = $deduct_total;
    $update_data = [];

    foreach ($batches as $batch) {
        if ($remaining_deduct <= 0) {
            break; // 扣减完成,终止循环
        }

        $batch_id = $batch['id'];
        $current_qty = $batch['qty'];

        if ($current_qty <= $remaining_deduct) {
            // 该批次全部扣完,数量置0
            $update_data[] = [
                'id' => $batch_id,
                'qty' => 0
            ];
            $remaining_deduct -= $current_qty;
        } else {
            // 该批次扣减剩余额度,更新剩余数量
            $update_data[] = [
                'id' => $batch_id,
                'qty' => $current_qty - $remaining_deduct
            ];
            $remaining_deduct = 0;
        }
    }

    // 批量更新弃置表
    if (!empty($update_data)) {
        $this->db->update_batch('disposal_table', $update_data, 'id');
    }

    // 提交事务
    $this->db->trans_complete();

    // 检查事务是否成功
    if ($this->db->trans_status() === false) {
        return false;
    }

    return true;
}

关键注意事项

  • 事务控制:必须开启事务,避免库存表更新成功但弃置表更新失败导致数据不一致
  • 排序规则:务必确保批次查询的排序是严格的FIFO顺序(比如用created_at或batch_no升序,根据你的表结构调整)
  • 边界判断:要处理deduct_total为0或负数的情况,避免无效操作
  • 批量更新:使用update_batch比逐个更新更高效,减少数据库请求次数

内容的提问来源于stack exchange,提问作者CodeLearner

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.21 18:42:41