开发文档

鲜花交易系统与鲜花交易平台(PHP / ThinkPHP 版)的研发记录:功能上线、架构演进与实施经验,按发布日期持续更新。

运费模板与履约归属:鲜花供应链最容易算错的一笔钱

运费在鲜花行业不是小数目

鲜花是低货值、高体积、强时效的品类。一扎花的运费可能占到货值的 10%~20%,冷链、泡沫箱、冰袋都要算钱。所以运费不是"订单上的一个字段",而是一套需要建模的规则。

这套系统的做法是三层:模板 → 地区规则 → 履约归属。

第一层:模板负责"怎么算"

运费模板挂在供应商或平台名下,支持四种计价方式:

  • 按件:每件固定金额,适合标准化包装的花材;
  • 按重量:首重 + 续重,适合按公斤计费的干线物流;
  • 按金额:满额包邮、未满额固定运费,适合做促销;
  • 统一运费:一单一价,适合同城配送。

模板可以设置满额包邮门槛。满额包邮的判断基数是商品金额(不含其它费用),避免"运费也算进满额"这种循环计算。

第二层:地区规则负责"发到哪、加多少"

同城 12 元、省内 20 元、偏远地区不发货——这些差异放在地区规则里,一个模板可以挂多条规则,每条规则有三种模式:

  • 独立计价:该地区不使用模板基础价,改用规则自己的价格;
  • 不配送:命中即拦截下单,前端直接提示该地区暂不支持;
  • 固定加价:在模板价格上叠加固定金额,适合偏远地区补贴。

匹配方式是地区名称前缀最长匹配,从省到市到区逐级收窄,保证"云南省"与"云南省大理市"两条规则同时存在时,下单到具体城市会命中更精确的那条。

第三层:履约归属决定这笔钱归谁

这是最容易出错的地方。同一张订单,不同商品的履约方式可能不同:

履约模式谁发货运费归谁结算影响
自主发货供应商供应商计入供应商应付结算单
平台仓发货平台仓平台不计入应付,作为平台收入单独入账

因此订单上必须按供应商分组分别计算运费,再汇总成订单总运费;订单明细层则按各行金额占比分摊运费,尾差归到最后一行,保证明细之和恰好等于订单总额——差一分钱,财务对账就会挂住。

结算侧的口径随之确定:

  • 自主发货部分:结算金额 = 商品原价 + 分摊运费 − 平台佣金 − 退款冲减;
  • 平台仓发货部分:运费不进供应商应付,直接计入平台收入台账,与佣金记在同一本账里。

为什么不在订单上只写一个运费

只写一个总运费会带来三个后果:

  1. 供应商看过结算单会问"这单运费为什么给我算了 8 块",无法解释;
  2. 平台仓发货的运费被误算进供应商应付,等于平台补贴了供应商;
  3. 退款时需要按行退运费,没有分摊依据只能估。

所以运费必须同时存在三个层级:模板层(规则是什么)、订单层(总运费)、明细层(每行分摊多少)。三者可由同一套规则推导,也必须能互相校验。

两个工程细节

  • 重量必须必填。按重量计价的模板,如果商品没有重量就会算出 0 元运费——这不是"容错",是资损。我们在商品与 SKU 上把重量设为计价前置条件,缺失时直接拒绝下单而不是静默按 0 处理。
  • 模板与地区规则都要能停用。历史订单引用了模板业务号做快照,物理删除会让记录变成孤儿,改为软下线。

运算是死的,归属是活的。把运费的"怎么算"与"归谁"分开建模,这套系统才能在混发场景下算得清、退得掉、对得上。

本文属于「开发文档」系列,记录鲜花交易系统(PHP + ThinkPHP 8 + MySQL 8)的实际研发进展。想了解功能清单与报价,可前往系统报价或联系我们。