批发商城APP怎么做:价格引擎、授信台账与资金合规的设计要点

写在前面:批发商城不是零售商城的折扣变体。本文把「批发」工程化为四块设计:价格引擎(等级价/阶梯价/专供价/活动价的优先级叠加)、授信台账(额度占用与释放模型)、单据流(订单→出库→对账→开票)、资金合规(多商户分账与「二清」红线)。附价格计算脚本、授信台账表结构与对账核对清单。适合正在做 B2B 商城立项的技术与业务双方。

写在前面:核心立场与读者对象

核心立场:零售商城卖的是「货」,批发商城卖的是「规则」。批发的预算大头不在页面,在三处看不见的模块:价格引擎(可配置)、授信台账(三数字模型)、单据流(四段闭环)。页面做到「采购员三步复购」即可。

读者对象:

  • 正在做 B2B 批发商城立项的技术负责人
  • 需要把账期、授信、对账规则翻译成系统需求的业务负责人
  • 评估多商户平台资金方案的架构师

先纠正的三个认知:

常见认知 实际情况
批发商城 = 零售商城加个批发价 价格、起订、支付、单据、客户五个维度全部不同
价格引擎是简单计算 是一套带优先级的规则叠加系统,写死 if-else 的项目第二年就开始还债
多商户平台代收货款再分账是常规操作 平台留存商户结算资金自行清算属「二清」,是无证经营支付业务,违规

目录

一、批发与零售的五个差异

维度 零售商城 批发商城
价格 一口价 等级价、阶梯价、专供价、活动价叠加
起订 单件可购 起批量、整箱/整包/整托规则
支付 在线即时付 在线支付 + 对公转账认款 + 账期授信并存
单据 订单 订单、出库单、对账单、发票四段
客户 匿名流量 实名客户资产,绑定业务员归属与提成

客户归属要在需求阶段先定:客户是谁开发的、业绩算谁的、业务员调岗后客户跟着谁走。这三个问题不进需求文档,业务员不会把客户数据放进系统,商城就没有真实的客户数据沉淀。

对公转账认款是批发的真实高频场景:客户汇款后财务要在系统里「认领」这笔款对应哪张订单。回款认领模型需要支持:金额部分匹配、一笔款对应多张订单、按账期先到先冲或指定冲销。

二、价格引擎:优先级叠加模型

价格引擎回答一个问题:这个客户、这个商品、这个数量、今天下单,单价是多少。

常见的价格层级与优先级(高优先在前):

优先级 价格类型 生效条件 典型配置项
1 专供价 客户×单品维度协议 有效期、是否可叠加活动
2 活动价 时间维度全场或类目 可否与阶梯价同享、封顶价
3 阶梯价 单品×数量区间 含税/不含税口径、区间边界归属
4 等级价 客户等级×类目或单品 等级评定规则
5 零售指导价 兜底 ---

设计要点:规则类型、优先级、生效条件全部数据化,运营可配置;新增规则不改代码。验收方式------现场演示新增一条「周三满 30 件每件减 2 元」规则而不发版。

数量区间的边界归属要提前定:买 50 件触发「50---99 件档」还是「10---49 件档」,阶梯边界属于上档还是下档,各行业习惯不同,写进需求文档。

三、授信台账:三数字模型

账期授信的系统化模型围绕三个数字:信用额度、已用额度、可用额度。

动作 对已用额度的影响 说明
下单(账期支付) 占用 按订单金额全额占用
出库 调整 按实际出库金额重算,差异部分释放
退货 释放或挂起 规则需提前定义,常见先挂起待入库确认
部分退款 部分释放 按退款单金额
回款到账 释放 冲销顺序:指定冲销优先,默认按账龄先到先冲
超控单 审批后占用 可用额度不足时走审批流

额度评定建议数据化:以客户过去 N 个月月均采购额 × 账期月数为基数,按合作年限上下浮动,审批留痕(谁批、何时批、额度水位预警阈值)。

四、资金合规:多商户与二清红线

中国人民银行在非银行支付机构风险专项整治中明确了口径:无证机构以平台对接或「大商户」模式接入持证支付机构,留存商户结算资金并自行开展商户资金清算,即「二清」,属无证经营支付业务;用户资金先划转至平台账户、再由平台结算给下挂商户的「大商户结算」模式同样在整治范围内。

落地原则一句话:**平台撮合交易,不碰货款。**买家资金由持牌支付机构直接清分至商户,平台只收取技术服务费。

多商户分账产品选型看三点:

考察点 关键问题 影响
分账时效 T+1 还是 T+7 批发商现金流敏感度高于费率
规则变更 分账比例调整是否需重签协议 运营灵活性
退款回退 已分账资金如何回退 客诉集中爆发的源头

自营模式(货款直接进自己公司账户)不涉及此红线;模式中只要存在「他人商户」,即需持牌分账。

五、单据流:订单到开票的四段闭环

批发交易的真实终点是对账平、票开对:

复制代码
订单 → 出库单 → 对账单 → 发票

四段单据各自的角色与关键校验:

单据 角色 关键字段 核心校验
订单 交易起点 商品、数量、成交单价 价格引擎追溯记录完整
出库单 履约凭据 实发数量、批次 与订单差异单据化
对账单 资金口径 应收、已收、未收 三者勾稽平衡
发票 税务凭据 品名、税率、金额 与对账单逐字段一致

各段典型差异与处理:

差异场景 处理要点
订单下了未出全 缺货部分自动转待发或取消,需定义
出库与订单数量不符 破损、赠品单据化,可追溯到人
回款与订单金额不一致 运费、抹零、分批付款认领规则
发票信息与订单不符 商品名、税率、金额字段级校验

发票链路:全面数字化的电子发票(数电发票)自 2024 年 12 月 1 日起在全国正式推广应用(国家税务总局公告 2024 年第 11 号),与纸质发票同等法律效力,税务机关电子发票服务平台提供免费的开票、用票服务。商城系统需完成订单数据与开票系统的字段级对接。

税务口径补充:《印花税法》自 2022 年 7 月 1 日施行,买卖合同(动产,不含个人书立)按价款万分之三缴纳,买卖双方均为纳税人;企业间明确买卖关系的订单、要货单未另立合同的同样属于征收范围。批发的订单台账因此有税务意义,金额字段需准确。

六、价格计算脚本

python 复制代码
# price_engine.py
# 用法: python price_engine.py --base 100 --grade 0.88 --qty 60 --tier "50:0.85" --special 83 --promo 0.02
import argparse


def resolve_price(base, grade_ratio, qty, tiers, special, promo_ratio,
                  promo_stack_tier=True, promo_cap=None):
    """价格优先级: 专供价 > 活动价 > 阶梯价 > 等级价 > 零售指导价"""
    # 阶梯价: tiers 形如 ["50:0.85", "100:0.82"], 闭区间下界
    tier_price = None
    best = 0
    for t in tiers or []:
        low, ratio = t.split(":")
        if qty >= int(low) and int(low) >= best:
            best, tier_price = int(low), base * float(ratio)
    grade_price = base * grade_ratio if grade_ratio else None

    candidates = [("专供价", special), ("活动价", None),
                  ("阶梯价", tier_price), ("等级价", grade_price),
                  ("指导价", base)]
    # 活动价在更优档之上叠加(可与阶梯/等级同享, 不可低于封顶)
    floor_candidates = [p for _, p in candidates if p is not None]
    best_base = min(floor_candidates)
    promo_price = best_base * (1 - promo_ratio) if promo_ratio else best_base
    if promo_cap:
        promo_price = max(promo_price, promo_cap)
    final = promo_price if promo_stack_tier else best_base
    trace = {"best_base": best_base, "promo_applied": bool(promo_ratio),
             "final": round(final, 2)}
    return trace


if __name__ == "__main__":
    p = argparse.ArgumentParser()
    p.add_argument("--base", type=float, required=True, help="零售指导价")
    p.add_argument("--grade", type=float, default=None, help="等级价系数")
    p.add_argument("--qty", type=int, required=True)
    p.add_argument("--tier", nargs="*", default=[], help="阶梯 数量:系数")
    p.add_argument("--special", type=float, default=None, help="专供价")
    p.add_argument("--promo", type=float, default=0, help="活动比例(0.02=减2%)")
    a = p.parse_args()
    print(resolve_price(a.base, a.grade, a.qty, a.tier, a.special, a.promo))

运行示例:--base 100 --grade 0.88 --qty 60 --tier 50:0.85 --special 83 --promo 0.02 输出 final: 81.67。关键是 trace 结构------每一次计算都留下「哪层规则生效」的记录,对账争议时可直接回溯。

七、授信台账表结构

sql 复制代码
-- credit_ledger.sql
CREATE TABLE credit_ledger (
    id            BIGINT PRIMARY KEY AUTO_INCREMENT,
    customer_id   BIGINT        NOT NULL COMMENT '客户',
    order_id      BIGINT        NULL     COMMENT '关联订单',
    biz_type      VARCHAR(16)   NOT NULL COMMENT '类型: occupy/adjust/release',
    amount        DECIMAL(12,2) NOT NULL COMMENT '变动金额(占用为正)',
    balance_after DECIMAL(12,2) NOT NULL COMMENT '变动后已用额度',
    reason        VARCHAR(128)  NULL     COMMENT '原因: 下单/出库调整/退货挂起/回款释放',
    operator_id   BIGINT        NULL     COMMENT '操作人(审批/认款)',
    created_at    DATETIME      NOT NULL DEFAULT CURRENT_TIMESTAMP,
    KEY idx_credit_customer (customer_id, created_at)
);

-- 可用额度 = 信用额度 - SUM(未释放占用)
SELECT customer_id,
       credit_limit,
       credit_limit - COALESCE(SUM(amount), 0) AS available
FROM credit_config c
LEFT JOIN credit_ledger l USING (customer_id)
WHERE c.customer_id = 1001
GROUP BY customer_id, credit_limit;

台账按流水记录每一次额度变动(而不是只存一个余额字段),保证任何时点的额度可回放、可审计------这是授信纠纷仲裁时的原始凭据。

八、对账核对清单

四段单据的核对项配置化,日终跑批校验:

yaml 复制代码
# reconcile_checklist.yaml
version: 1
checks:
  - id: O1
    item: 出库数量合计 ≤ 订单数量
    severity: blocker        # 违反即阻断对账
  - id: O2
    item: 出库金额 + 差异单金额 = 订单金额
    severity: blocker
  - id: P1
    item: 回款认领覆盖率 = 100%(对公未认款挂账清单)
    severity: major
  - id: P2
    item: 冲销顺序符合规则(指定冲销 > 账龄先到先冲)
    severity: major
  - id: I1
    item: 开票金额 = 对账单确认金额
    severity: blocker
  - id: I2
    item: 发票字段校验(品名/税率/金额)通过率 = 100%
    severity: major
  - id: T1
    item: 订单台账金额完整(印花税计税依据可导出)
    severity: minor

blocker 项不过,当天的对账单不允许生成------宁可晚一天出账,不出一笔对不平的账。

九、需求评审清单与常见问答

评审批发商城需求时逐项确认:

# 确认项 未定义的后果
1 价格层级优先级与叠加规则 财务对账口径混乱
2 阶梯区间边界归属 采购员与业务员对归属各执一词
3 起批量与凑单规则 下单流程反复返工
4 对公认款与冲销顺序 回款挂账越积越多
5 授信占用/释放全场景(含退货) 额度形同虚设
6 客户归属与业绩口径 业务员不录客户
7 多商户走持牌分账 触碰二清红线
8 三套收入口径(订单/出库/开票)统一 月底对账变成部门战争

Q1:自营起步,以后要多商户,架构要预留什么?

支付层从一开始就按「持牌通道 + 可配置分账」设计,自营阶段分账对象只有自己;客户、商品模型里预留商户维度。改动成本远低于后期重构。

Q2:价格引擎能不能后期再补?

不建议。订单记录的是成交价,价格引擎缺位的第一年,成交价的计算过程散落在业务员的报价单里,第二年起补录的数据无从校验。

Q3:账期客户也要能在线下单吗?

要,这正是系统化的价值点:在线下单 + 授信实时校验 + 自动占用额度,替代业务员微信接单后手工登记。下单体验对采购员的价值不亚于价格。

Q4:对公转账回款怎么自动认领?

常见方案是回款金额 + 付款方户名模糊匹配候选订单,财务人工确认。全自动匹配在金额有抹零、分批付款时不可靠,人机结合是稳定形态。

Q5:印花税和系统有什么关系?

订单、要货单属于印花税应税凭证范围(万分之三,双方缴纳),系统的订单金额台账就是计税依据来源,字段准确性有税务意义。

Q6:页面要做成什么样?

以「采购员第二次来」为主场景:常购清单、按上次订单一键再下、三步内完成复购。首页营销位的优先级低于购物车效率。

参考资料

  1. 中国人民银行:非银行支付机构风险专项整治工作答记者问(二清口径):https://www.pbc.gov.cn/
  2. 国家税务总局公告 2024 年第 11 号(数电发票全国推广):https://www.chinatax.gov.cn/
  3. 中国政府网:我国将在全国推广应用数电发票:https://www.gov.cn/lianbo/bumen/202411/content_6989158.htm
  4. 《中华人民共和国印花税法》(国家法律法规数据库):https://flk.npc.gov.cn/
  5. 国家税务总局天津市税务局:印花税法规定的买卖合同税率:https://tianjin.chinatax.gov.cn/
  6. 国家税务总局广西壮族自治区税务局:订单要货单印花税口径:https://guangxi.chinatax.gov.cn/
  7. 微信支付服务商产品文档(分账):https://pay.weixin.qq.com/

如内容有错误欢迎评论区指正。

相关推荐
茶底世界之下3 小时前
夜景加胶片颗粒,先看天空:Awaking 两版真实导出
ios
2501_915106324 小时前
iOS 单元测试怎么跑?用 KXApp 在 VS Code 里跑 XCTest 和 Swift Testing
ide·vscode·ios·单元测试·个人开发·swift·敏捷流程
2501_915921434 小时前
iOS 实时日志怎么看?KeyMob 的日志过滤、崩溃报告与符号化
android·ios·小程序·https·uni-app·iphone·webview
天蒙蒙亮4 小时前
打ios app包+“应用商城”发布
ios
小小王app小程序开发4 小时前
教育 AI 小程序玩法开发分析
人工智能·小程序
VicLi1 天前
把常用 iOS 调试操作放进一个 macOS 控制台: iCATBox
ios
茶底世界之下1 天前
雾景需要更强反差吗?用 Awaking 检查树影与雾气的平衡
ios
普通人61 天前
uniapp模版JS
开发语言·javascript·小程序·uni-app·1024程序员节
终端安全笔记1 天前
下一个大版本要动的三处:更新指令、传输要求、策略写法
网络安全·ios·1024程序员节·移动设备管理