巴青农资商城

购物车前端技术方案.md 9.4KB

购物车 — 前端技术方案(C 端 · shop-app)

依据: 《购物车功能需求.md》v1.0、《购物车技术方案.md》v1.0(仅作接口对照,本文档独立维护
关联: 《商品详情内页前端技术方案》、《确认订单页(多商品)前端技术方案》v1.0、《店铺主页前端技术方案》
范围: C 端 购物车 Tab 列表、详情 加购、勾选/改量/删除/清理失效、同店去结算;确认订单 多商品页 见另册,本模块负责跳转与 prepare 门禁。
实现状态: Tab 页、组件、API、checkout-cart 跳转链路 已落地


1. 技术栈与约定

说明
框架 uni-app Vue 3 + uview-plus
请求 @/utils/request;列表 AjaxResult.dataitems[] + checkedSummary
鉴权 全部 /api/cart/** 须会员 Token
页面位置 主包 Tab pages/cart/index(与 pages.json tabBar 一致)
规格 v1 统一规格;加购 specKey 不传,specText 由详情拼接或「默认」
防抖 改量/勾选/去结算使用 useActionGuard
参考 subpackage/order/checkout-cart.vue(去结算下游)、pages/mine 未登录态

2. 页面与路由

页面 需求代号 路径 入口
购物车列表 A pages/cart/index 底部 Tab「购物车」;详情加购后可自行切 Tab
确认订单(多商品) subpackage/order/checkout-cart 本页 去结算(另册维护)

未登录: 空态 +「去登录」→ PAGE_LOGIN(CT0)

路径常量:

常量 路径
PAGE_CART /pages/cart/index
PAGE_CHECKOUT_CART /subpackage/order/checkout-cart

预加载: pages.jsonpreloadRulepages/cart/index 预加载 pkg-order


3. 文件清单

类型 路径 说明
Tab 页 shop-app/pages/cart/index.vue 分组列表、工具栏、底栏全选/合计/去结算
店组 shop-app/components/cart/CartShopGroup.vue 店头全选、进店、休息中标签
商品行 shop-app/components/cart/CartItemRow.vue 勾选、数量、小计、失效标签、删除、进详情
购物车 API shop-app/api/cart.js /api/cart/**
展示 shop-app/utils/cartDisplay.js 扁平 items 按店分组、失效文案、勾选统计
结算导航 shop-app/utils/checkoutNav.js goCartCheckout(cartItemIds)
规格展示 shop-app/utils/cartSpec.js parseCartSpecText§ 分隔)
常量 shop-app/constants/cart.js 失效类型、空态、跨店提示
常量 shop-app/constants/checkout.js CART_CHECKOUT_IDS_KEY

已改上游:

文件 改动
subpackage/goods/detail.vue doAddCartPOST /api/cart/items

4. 接口封装(api/cart.js

基路径: /api/cart

方法 HTTP 路径 场景
getCartList GET /api/cart Tab onShow 拉列表
addCartItem POST /api/cart/items 详情加购
updateCartQuantity PUT /api/cart/items/{id}/quantity +/- 改量
updateCartChecked PUT /api/cart/items/checked 行/店/全选
removeCartItem DELETE /api/cart/items/{id} 单行删除
removeCartItems DELETE /api/cart/items 删除选中
cleanInvalidCart DELETE /api/cart/invalid 清理失效
prepareCartCheckout POST /api/cart/checkout/prepare 去结算门禁

4.1 列表响应 CartListVO

字段 说明
items[] 扁平购物车行(含 shopId/shopName/shopStatus);排序 cart_item_id DESC
checkedSummary 已勾选且 purchasable 行合计

前端 mapCartListitems[] shopId 分组 为 UI 用 groups[](后端不分组)。

4.2 加购 Body(详情)

字段 说明
goodsId 必填
quantity 必填
specText 规格快照;无则「默认」

4.3 批量勾选 Body

{
  "items": [
    { "cartItemId": 1, "checked": true }
  ]
}

4.4 去结算 Body

{ "cartItemIds": [1, 2] }

成功后再跳转确认订单页;不在购物车页缓存 prepare 结果(确认页走 POST /api/checkout/preview)。


5. 列表页结构(pages/cart/index.vue

购物车 Tab
├── 未登录:空态 + 去登录
├── 加载中 / 加载失败(重试)
├── 空购物车:「购物车是空的」+ 去逛逛(首页 Tab)
└── 有数据
    ├── 顶栏工具条
    │   ├── 清理失效商品(有失效行时显示)
    │   └── 删除选中(有勾选时显示)
    ├── scroll-view · CartShopGroup × N
    └── 底栏
        ├── 全选(仅可购行)
        ├── 合计 ¥checkedSummary.checkedAmountText
        └── 去结算(N)

6. 列表页逻辑

onShow
  → 无 Token:访客空态
  → 有 Token:GET /api/cart → mapCartList(items 按店分组)

店组头勾选
  → 该店全部 purchasable 行 checked 同步 → PUT checked → 刷新

行勾选 / 底栏全选
  → PUT checked → 刷新(含 checkedSummary)

数量 +/-
  → PUT quantity → 刷新(库存不足后端 400)

删除单行
  → 二次确认 → DELETE 单行 → 刷新

删除选中
  → 二次确认(展示件数)→ DELETE 批量 → 刷新

清理失效
  → countInvalidCartItems → 二次确认(展示件数)→ DELETE /invalid → Toast removedCount

去结算
  → 无勾选可购行:提示
  → 跨店勾选:Toast「请选择同一店铺的商品结算」
  → POST prepare 成功 → goCartCheckout(ids)
  → prepare 失败:request 已 Toast,不跳转
需求规则 实现
CT2 按店分组 groupCartItemsByShop
失效不可勾选 purchasable=false 置灰勾选
CT-S1 不跨店结算 getCheckedShopIds.size > 1 拦截
CT7 清理失效 顶栏按钮 + 件数确认
缺货/下架进详情 点击主图/名称 goGoodsDetail
进店 点击店名 goShopHome
行小计 subtotalText 展示

6.1 底栏合计

使用接口 checkedSummary(仅 已勾选且可购 行),与后端口径一致。

6.2 失效标签

invalidTypegetCartInvalidLabelcartDisplay.js):

invalidType 默认文案
OUT_OF_STOCK 缺货
OFF_SHELF 已下架
SHOP_CLOSED 休息中
CATEGORY_HIDDEN 不可购买
GOODS_DELETED 已失效
SHOP_DELETED 店铺失效

优先使用后端 invalidMsg


7. 组件说明

7.1 CartShopGroup.vue

  • 店头:勾选(仅当有可购行)、店名、停业「休息中」、进店箭头
  • 子组件 CartItemRow 列表

7.2 CartItemRow.vue

  • 可购:勾选、+/- 改量、删除
  • 失效:勾选禁用、数量只读、失效标签、仍可删、可点进详情
  • 展示:主图、名称、规格列表、单价、小计

8. 数据映射(cartDisplay.js

函数 用途
mapCartList items[]groups[] + checkedSummary
groupCartItemsByShop 内部:按 shopId 分组,保持行序
hasInvalidCartItems 是否显示「清理失效」
countInvalidCartItems 清理前展示件数
getCheckedPurchasableIds 去结算 / prepare 入参
getCheckedShopIds 跨店校验
getAllPurchasableItems 全选逻辑
getCartInvalidLabel 失效标签文案

行模型要点: displayPicpriceTextsubtotalTextspecListinvalidLabelpurchasable


9. 与确认订单(多商品)边界

购物车侧
prepare POST /api/cart/checkout/prepare 门禁(四条件、同店)
跳转 goCartCheckoutcheckout-cart?cartItemIds= + storage 兜底
预览/提交 不在本页;见《确认订单页(多商品)前端技术方案》
支付成功删行 后端 处理;返回 Tab 刷新可见
去结算
  → prepareCartCheckout(ids)
  → goCartCheckout(ids)
       → setStorage CART_CHECKOUT_IDS_KEY
       → navigateTo PAGE_CHECKOUT_CART

10. 联调检查清单

  • 未登录 Tab 仅引导登录
  • 详情加购后 Tab 刷新可见,同规格数量累加
  • 列表 items 正确按店分组展示
  • 失效行不可勾选、标签与进店/进详情可用
  • 改量超过库存 → 400「库存不足」
  • 跨店勾选去结算 → 前端拦截文案
  • 同店 prepare 成功 → 跳转 checkout-cart
  • 清理失效展示件数;删除选中二次确认
  • 停业店可展示,prepare 拦截停业

11. 非本期(前端不实现)

说明
列表/搜索快捷加购 仅详情加购
跨店一键多单 CT-S1 不支持
优惠券、凑单 未要求
失效自动删除 用户触发「清理失效」

12. 修订记录

版本 说明
v1.1 对齐需求 v1.0:items 前端按店分组、清理失效件数确认、行小计、去结算跳转 checkout-cart;更新与多商品确认页边界
v1.0 首版:Tab 购物车、详情加购、同店 prepare

文档版本:v1.1 · 不修改《购物车技术方案.md》(后端方案)。