
门店小程序做到「能下单、能核销」不难,难的是当门店从三五家扩张到几十上百家时,一个后台能不能把这些店管明白。很多系统在门店多了以后开始出事:A 店的订单串到了 B 店、店员点开了总部报表、店长看不到自己店的数据、总部对账怎么都对不上。这些问题的根源,往往不是功能不够,而是数据隔离和权限设计从一开始就没做对。本文不堆术语,把多门店后台最核心的两件事——数据隔离和角色权限——讲透。
多门店系统里,订单、库存、会员、员工、优惠券、对账记录这些业务数据,如果全部堆在一起不做区分,会出现三类典型问题:
串数据:查询没带门店条件,A 店的库存把 B 店的也算进去了,发错货、对错账。
越权:门店员工能看到别家店乃至总部的财务和经营数据,这是管理事故,也是合规风险。
统计失真:总部要做单店毛利、店均客流、人效对比,数据混在一起根本算不出来,只能靠手工导出后再拼,越拼越乱。
所以「一个后台管百家店」的第一步,不是把页面做得多花哨,而是先让每一笔数据清清楚楚地知道自己属于哪家店。
数据隔离的前提,是先把组织关系定义清楚。绝大多数连锁业态是这样一个层级:
总部(集团)→ 区域(大区/城市)→ 门店
设计时通常给每个层级一个唯一编号,门店层用 store_id(门店ID)作为最核心的维度字段。凡是跟业务相关的表——订单表、库存表、会员表、卡券表、流水表——都必须带上门店ID这一列,这是整个数据隔离方案的地基。
同时建议预留一个「门店状态」字段(营业中、停业、装修、已注销),门店关闭后历史数据要保留,但不能再产生新业务,这个字段在权限和统计上都有用。
多门店数据隔离在工程上主要有三种做法,各有适用场景:
方式一:每个门店一套独立数据库。 隔离最彻底,物理上互不相通,安全性最高,但成本也最高——每一家店都要维护一套库,升级要全部同步,跨门店汇总还得专门做数据汇聚,通常只在数据合规要求极其严格的场景下使用。
方式二:共享库、按门店拆表。 每个门店一套同名表(如 order_01、order_02),看起来隔离了,但门店一多表爆炸,跨店统计要把上百张表合并,改表结构要批量改,属于中间态做法,不建议新项目采用。
方式三:共享库、共享表、靠门店ID字段区分(主流方案)。 所有门店共用一个数据库、一张订单表,靠 store_id 这一列区分归属。这是绝大多数连锁小程序的选择,因为它的扩展成本最低:新开一家店,只要在门店表里加一条记录,再往业务表写数据时带上新门店ID即可,几乎零改造成本。
选用方式三时,有几个细节必须做好:一是唯一业务编号要带门店维度(如订单号由「门店标识+序号」组成),避免两家店订单号冲突;二是在门店ID和常用查询字段上建联合索引,门店越多越不能靠全表扫描;三是历史数据与当前数据分离,门店停业不影响其他门店的查询性能。
有了门店ID字段还不够,真正容易翻车的是查询漏写门店条件。一张订单表几百个查询接口,只要漏了一个,某个员工就可能看到全部门店的数据。
工程上的做法是:不要依赖每个开发人员都记得写门店条件,而是通过后端统一拦截器(中间件)在请求入口做约束——解析出当前登录用户的可见门店范围,自动往查询条件里注入门店过滤,把「不带门店范围的数据访问」在源头拦掉。这样即使有人漏写,系统也会默认只返回其权限范围内的数据,而不是全部数据。这是多门店系统安全性的第一道闸门。
数据隔离解决「数据属于谁」,权限体系解决「谁能看到、能操作谁的数据」。权限设计用经典的 RBAC(基于角色的访问控制)模型:用户 → 角色 → 权限。一个人可以挂多个角色,权限挂在角色上而不是直接挂在人上,这样人员流动时只需调整角色,管理成本最低。
结合门店场景,典型角色可以这样划分:
平台超级管理员:拥有全部数据、全部功能,负责系统级配置。
区域负责人:管理本区域下多家门店的数据和人员。
店长:管理本店全部数据,能看本店报表、处理本店退换货。
店员:只做本店内的限定操作,比如接单、核销、记会员,看不到经营数据和财务数据。
权限点建议拆成三层来管:菜单权限(能不能看到某个功能入口)、操作权限(能不能点某个按钮,如删除、导出、调价)、数据权限(能看到哪些范围的数据)。前两者是功能控制,第三者是数据控制,三者叠加才构成完整权限。
这是多门店系统最容易被低估的一环。功能权限好做——「有没有这个按钮」判断一次就行;数据权限难做——「同样的一个报表,不同角色看到的内容完全不同」。
数据范围建议做成四级:
全局:总部级别,能看所有门店数据,一般只给平台超管。
区域:能看本区域所有门店,给区域负责人。
门店:只能看本店数据,给店长。
个人:只能看自己产生的数据(如本人经手的订单),给部分受限店员。
权限校验的顺序很关键:先判断功能权限,再判断数据权限。也就是说,先确认「这个人有没有资格进入门店报表这个功能」,再确认「他进入之后能看到哪几家店的数据」。缺了第二层,就会出现「店员能打开报表,结果看到的是全公司数据」的事故。
技术实现上,几个关键点:
登录态要带权限信息。 用户登录成功后,把用户ID、角色列表、数据范围一起放进登录凭证(如令牌)中,后续每个请求都能快速取到当前用户是谁、能管哪些店,不用每次访问数据库重新查一遍。
后端统一鉴权。 在接口入口统一做两层校验:功能权限用拦截器校验;数据权限结合上一节的门店过滤条件一起处理。凡是写操作(改价格、删订单、调库存),还要额外校验「目标门店是否在当前用户的可管理范围内」,防止越权操作。
前端权限控制只做体验,不做安全。 菜单、按钮根据权限点做显示或隐藏,让界面干净、符合角色;但真正的安全必须落在后端——前端隐藏了按钮,不代表接口就安全,恶意请求一样能绕过界面直接调用接口。所以一切以服务端校验为准。
权限设计得再完整,也挡不住「设计之外」的漏洞。几个必须做扎实的细节:
参数防篡改:门店ID、订单ID这类参数不能信任前端传值,后端必须二次校验其归属。
敏感操作二次确认:批量改价、大额退款、删除数据这类高风险操作,建议做二次校验或留痕。
全量审计日志:记录「谁、在什么时间、对哪个门店的哪条数据、做了什么操作」。平时用不上,一旦出事(对不上账、员工违规)就是唯一依据。审计日志本身不可被普通角色修改。
人员变动及时回收:员工离职、调岗、门店注销时,权限要能一键停用,避免「人走了账号还在」的安全隐患。
数据隔离方案决定了系统的扩展上限。门店几十家时,共享表方案很轻松;到几百家、数据量上来后,要提前做好这些准备:
索引策略:所有带门店ID的查询都要走索引,统计类查询按需建联合索引。
读写分离与缓存:高频读取的配置数据(门店信息、商品信息)放缓存,减少数据库压力。
按门店分库分表:当单表数据量巨大时,可按门店维度做水平拆分,这是共享表方案的天然延伸,迁移时改动可控。
异步汇总:总部报表如果实时汇总上百家店会拖垮数据库,建议定时把各店数据汇总到独立的统计表,报表只读统计表。
记住一条原则:隔离结构要能支撑「新增一家店 = 数据库加一行配置」,而不是每开一家店都要改一次代码。这才是「一个后台管百家店」的真正含义。
最后列几条最容易踩的坑,开发时对照自查:
只做了前端权限控制,接口裸奔,是最大的坑。
查询漏带门店条件,靠人肉记,迟早串数据。
报表权限一刀切,门店能看到总部数据,数据权限没分层。
门店ID信任前端,参数可篡改,越权漏洞根源。
离职不回收权限,账号烂在系统里。
新门店上线要改代码,说明隔离模型设计失败。
一个后台管百家店,核心就三句话:数据层用门店ID把每一笔数据归属清楚,权限层用「功能权限+数据权限」双维度控制谁能看什么,技术层靠后端强制校验兜底、靠审计日志留痕。把这三件事做扎实,门店从十家开到一百家,后台架构都不用推翻重来;这三件事漏了任何一件,门店越多,事故越大。这套设计思路,值得在项目动工第一天就写进方案里。