# “一客一价” (客户专属单品折扣) 改造设计方案 ## 1. 背景与业务痛点 * **当前系统瓶颈**:目前系统仅支持“全局统一折扣”或“商品级统一折扣”。也就是说,如果给商品 A 设置了 8 折,那么所有 VIP 卡客户买商品 A 都是 8 折。 * **新业务需求**:为了精细化管理客户(尤其是 B2B 批发客户或核心大客户),需要实现**客户维度与商品维度的交叉定价**。例如:核心客户张三由于拿货量大,商品 A 给他 7.5 折;而普通客户李四拿货少,商品 A 只能给他 9 折;同时,张三买商品 B 可能利润薄,这件只给 95 折。 * **业务目标**:打造千人千面的私有价格体系(一客一价),增强熟客黏性。 --- ## 2. 数据库设计 (Database Schema) 由于需求属于“多对多”(多客户对应多商品,各有独立折扣价),必须引入一张新的映射关联表。 ### 新增关联表:`ml_user_product_discounts` 我们需要在 Supabase 中创建这张记录专属折扣的桥接表。 ```sql CREATE TABLE ml_user_product_discounts ( id UUID DEFAULT uuid_generate_v4() PRIMARY KEY, user_id UUID NOT NULL, -- 关联:客户(买家) ID product_id UUID NOT NULL, -- 关联:商品 ID discount_rate NUMERIC NOT NULL, -- 该客户买该商品的专属折扣率 (例如 0.75) created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(), updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(), UNIQUE(user_id, product_id) -- 核心约束:保证同个客户对同个商品只有一条有效规则 ); -- 出于性能考虑,建议在 `user_id` 和 `product_id` 上添加索引,方便检索某个用户购物车里商品的价格。 CREATE INDEX idx_user_discount_user ON ml_user_product_discounts(user_id); ``` *(附注:该表的数据由**商家端**维护分配,**买家端**在此表面前仅为“只读查询”角色。)* --- ## 3. 商家端 (Merchant App) 功能拆解 系统需要提供给商家的管理入口从“发商品时”转移到“管客户时”。 ### 3.1 【客户分析/管理】入口 * 若当前缺少直接管理消费者的模块,需先建设一个简单的【客户列表页】,加载已在平台注册/下单过的用户。 * 点击具体用户,进入【客户详情管理页】。 ### 3.2 专属商品折扣分配功能 * **功能入口**:在【客户详情页】底部增加按钮或标签卡——「配置专属折扣商品」。 * **交互流程**: 1. 商家调出平台的全量商品列表面板(可能带有搜索与分类)。 2. 商家勾选指定的若干个商品,将它们加入到此客户的“专属打折清单”中。 3. 出现在专属清单中的每一个商品,商家可通过步进器或输入框单独设置对于该客户的**专属折扣率**。 4. 提交保存后,数据 `UPSERT` 存入 `ml_user_product_discounts` 表。 5. 商家也可以随时将某个商品从该客户的专属清单中踢出(删除记录)。 ### 3.3 系统融合建议 * 如果商家发现给每个特定商品设价格太累,仍可以保留“商品通用VIP折扣”作为保底。 --- ## 4. 消费者端 (Consumer App) 核心计价降级逻辑 (重要!) 在价格体系变得复杂后,**消费者渲染的价格、加入购物车的价格、结算付款时的价格**,这三端必须遵循绝对严格的“逐层降级(Fallback)”查询机制。 **价格优先级链条设定如下(权重由高到低):** * **👑 T0 级别(最高):一客一价** - 前端去查当前商品是否在 `ml_user_product_discounts` 里有当前用户的专属记录。如果有,以此为准。(如:张三专属 75 折) * **🥇 T1 级别:单品通用 VIP 折扣** - 如果 T0 没有,接着查 `ml_products` 中该商品的 `is_vip_discount` 是否为 true 且配置了 `vip_discount_rate`。如果有,以此为准。(如:全民VIP买此衣服 8 折) * **🥈 T2 级别:全站全局 VIP 折扣** - 如果 T1 也没有,接着查询该用户绑定等级的全局默认折扣(如:白银会员全场 95 折,如果在历史版本中还在生效的话)。 * **🥉 T3 级别(底线):原价销售** - 兜底机制,以原先的 `base_price`(销售商品原价)售卖。 ### 4.1 查询性能优化 (购物车与订单结算) **防止 N+1 查询问题**:当用户在购物车勾选了 20 个不同商品进行结算时,**绝对不能**在后端使用循环去数据库查 20 次个人折扣表! * **正确做法**:将购物车里所有商品的 `product_id` 组装成一个数组。执行一次 `SELECT * FROM ml_user_product_discounts WHERE user_id = 'xxx' AND product_id IN (id1, id2, id3...);` 构建一个映射字典(Map/Hash),然后在内存在结算链中匹配。 --- ## 5. 项目分期与落地计划 为了控制风险保障业务不中断,建议采取“两周敏捷迭代”策略。 * **Phase 1 (第一期):打通通道与数据库** * 在 Supabase `ml_user_product_discounts` 建表与打入测试数据。 * 改写买家端商品详情与结算页的逻辑,先完成**后端价格过滤模型**。这一步让消费者能准确以多级降级的形式算清最后的价格。 * **Phase 2 (第二期):商家端可视化管理体系** * 开发并上线商家的【客户管理页】。 * 根据客户维度拉取列表,并制作批量打折与分配商品的界面。 * 上线后通知业务方进行试发价。