if ($payable == 0) {
    $order->status = 'paid';
    $order->paid_at = date('Y-m-d H:i:s');
    // 写一条 channel=points 的支付流水
}

订单用积分全额抵扣,应付 0.00,点支付直接弹「金额不能为空或小于 0.01」。订单一直卡在待付款,超时后被自动关闭。先别急着动参数,把报错原文和时间点记下来,顺序反了容易白折腾。

原因不复杂,收银台只走渠道下单,渠道对 0 元交易一律拒绝,代码没有为零元单独开一条完成路径。金额校验又写在下单之前,0 被当成非法值拦掉。

「零元订单支付」改完先别急着全量,挑一台机器放半天,真有问题这段时间就能看出来。动手前把原文件复制一份带时间戳,出问题立刻换回去,比现场分析快得多。

处理上按这个顺序:结算时先判断应付是否为零,为零就直接标记已支付并写一条支付流水,不走渠道;支付流水里 channel 记成 points 或者 balance,方便财务区分;金额校验从大于零改成大于等于零,零元单独走免支付分支。

改完只确认一件事:积分全额抵扣的订单提交后直接变成已付款,页面跳到成功页,不再被超时关闭。

作者 9823189