多端智慧物业:统一身份与API网关架构实践
发布时间:2026/9/15 6:38:42 作者:尧图编辑部 阅读量:1,286

简介一套面向智慧物业业务场景的多端一体化解决方案覆盖微信公众平台、小程序、电脑管理端、H5页面以及智能硬件设备的多入口统一管理。后端选用Koa与TypeScript构建具备分布式部署能力前端基于Vue与View Design封装组件实现精细界面与流畅交互动画。系统包含精确到每个菜单的权限控制无缝对接公众号与小程序数据支持定时任务、长连接通信及小区门禁、道闸等硬件接入。从文件构成看资源包共2226个文件压缩后约31.21MB主要包含Vue单文件组件、TypeScript业务逻辑、微信小程序页面文件wxml/wxss/wxs、JSON配置以及SVG、PNG、JPG等静态资源目录结构清晰便于按模块定位开发。目前已有119人学习适合具备Node.js与Vue基础的中高级开发者用于二次开发也可作为智慧物业项目从权限设计、多端数据打通到硬件联动的完整参考工程。1. 多端智慧物业难点不在端而在共享业务层一个常规的智慧物业项目业主端要能用微信公众号收缴费通知、用小程序开门禁和报修物业办公室要用 PC 管理工单和查看财务报表停车场道闸和人脸门禁机要实时上报事件。很多团队接到这类需求后的第一反应是拆成四五个独立项目各做各的结果做到一半就发现业主在公众号交了费小程序里看不到记录PC 端改了一个房号硬件端联动全部失效。这套系统的关键结论是多端不是多做几套界面而是用一套 API 网关加统一用户体系把公众号、小程序、PC、H5 和硬件全部挂到同一个业务中台上。本文就按这个思路从统一身份到各端接入再到业务闭环把可落地的做法讲清楚。2. 统一身份与 API 网关先解决「五个端认一个人」多端物业系统最先要面对的问题是同一个业主在公众号里是一个 openid在小程序里是另一个 openid在硬件端又变成了一张 IC 卡编号。如果不做统一身份业务数据就会被切碎缴费记录挂在公众号账号下门禁记录挂在手机号下PC 端查询时要跨多个表关联维护成本极高。2.1 用微信生态的 unionid 打通公众号与小程序微信生态里同一微信用户在不同公众号、小程序、APP 下的 openid 都不一样但在同一微信开放平台账号下unionid 是唯一的。只要把公众号和小程序绑定到同一个微信开放平台账号前端登录后把 code 传给后端后端调用微信接口换取 openid 和 unionid就能把两个端归到一个人。常见的表结构设计如下CREATE TABLE user ( id bigint(20) NOT NULL AUTO_INCREMENT, phone varchar(20) DEFAULT NULL, unionid varchar(64) DEFAULT NULL, status tinyint(4) DEFAULT 1, PRIMARY KEY (id), KEY idx_unionid (unionid) ) ENGINEInnoDB; CREATE TABLE user_identity ( id bigint(20) NOT NULL AUTO_INCREMENT, user_id bigint(20) NOT NULL, app_type varchar(20) NOT NULL COMMENT WECHAT_MP公众号 / WECHAT_MA小程序 / PC / H5 / HARDWARE, openid varchar(64) DEFAULT NULL, device_no varchar(64) DEFAULT NULL COMMENT 硬件设备编号, PRIMARY KEY (id), UNIQUE KEY uk_app_openid (app_type, openid) ) ENGINEInnoDB;用户首次通过公众号访问时user_identity里插入一条WECHAT_MP的记录之后在小程序里登录发现 unionid 已存在就把新 openid 追加为WECHAT_MA记录不再新建用户。这样所有端的操作最终都收敛到同一个user_id上。2.2 双 token 机制覆盖小程序和 H5 不同的会话诉求移动端常见做法是登录后发一个短期access_token加一个长期refresh_token。小程序里可以使用wx.storage保存H5 端要特别注意微信内置浏览器的 localStorage 可能被清理建议同时把 refresh_token 写入 cookie。// 登录成功后端返回双 token前端统一封装存储 const loginRes await request(/api/auth/login, { code: wxCode // 小程序里 wx.login 获取的 codeH5 则是 OAuth 授权 code }); wx.setStorageSync(access_token, loginRes.accessToken); wx.setStorageSync(refresh_token, loginRes.refreshToken); // 请求拦截器里统一附带 token const request (url, data) { return new Promise((resolve, reject) { wx.request({ url, data, header: { Authorization: Bearer wx.getStorageSync(access_token) }, success: (res) { if (res.data.code 401) { // 调用 refresh 接口换新 token refreshToken().then(() resolve(redoRequest(url, data))); } else { resolve(res.data); } } }); }); };后端在签发 token 时把user_id、app_type、identity_id放进 JWT 的 payload业务接口里从 token 直接取user_id就能做到「一处登录处处识别」。注意app_type很重要后续做消息推送和权限控制时要区分请求来自哪个端。2.3 API 网关把硬件流量和业务流量分开硬件设备门禁、车闸、水电表的网络环境和移动端差别很大。设备可能处于内网或受限网络宕机重连频繁数据上报间隔短、量大。建议网关层把设备流量和用户流量分成两套入口用户端入口api.example.com走 HTTPS JWT承接公众号、小程序、PC、H5设备端入口iot.example.com走 MQTT 或 HTTPS 设备鉴权承接硬件上报设备鉴权不建议用 JWT因为设备的 token 刷新机制不如移动端成熟。常见做法是给每台设备分配device_no和device_secret上报时用 HMAC-SHA256 签名网关验签后放行。下面是一段 Node.js 的设备签名校验示例const crypto require(crypto); // 设备上报数据 const payload { deviceNo: DJ-001, eventType: OPEN_DOOR, timestamp: Math.floor(Date.now() / 1000), data: { cardNo: A12345, result: success } }; // 设备端签名device_secret 关键字段拼接 const signStr ${payload.deviceNo}\n${payload.timestamp}\n${payload.eventType}; const signature crypto .createHmac(sha256, device_secret_here) .update(signStr) .digest(hex);网关收到请求后先用设备编号查出对应 secret再用同样算法重算签名比对一致才继续转发。这种方式不需要设备保存易失的 token只要保证device_secret不泄露长期有效也没问题。提示不要在网关层对硬件上报做重试设备断网重连后的积压数据要靠时间戳去重和按序落库否则门禁记录会出现乱序覆盖。3. 公众号、小程序、PC、H5 与硬件的接入落法统一身份和网关搭好之后各端的接入就是一个「套模板」的过程但每一端都有自己的坑。公众号端的核心是网页授权和 JS-SDK 签名小程序端要注意手机号快捷验证和订阅消息PC 端重点是权限模型硬件端则要设计好心跳和指令下发机制。3.1 微信公众号 H5网页授权与 JS-SDK 签名公众号内打开的 H5 页面要走微信 OAuth2.0 网页授权获取用户身份。snsapi_base是静默授权用户无感知就能拿到 openidsnsapi_userinfo需要用户点击确认能拿到昵称头像。物业场景下缴费通知、账单查询这类页面用静默授权就够只有首次绑定业主身份时才需要用户手动输入房号。# Flask 示例处理微信 OAuth 回调 app.route(/api/wechat/oauth_callback) def oauth_callback(): code request.args.get(code) resp requests.get( https://api.weixin.qq.com/sns/oauth2/access_token, params{ appid: APP_ID, secret: APP_SECRET, code: code, grant_type: authorization_code } ).json() openid resp[openid] # 用 openid 找到 user_identity 里的 user_id签发业务 token user_id find_user_by_openid(WECHAT_MP, openid) return redirect(f/index?token{issue_token(user_id)})页面里还需要调用微信 JS-SDK 的能力比如获取地理位置定位到小区、调用扫一扫识别访客二维码。JS-SDK 要求后端生成签名签名的参数是jsapi_ticket、noncestr、timestamp、url。有个高频踩坑点签名用的url必须是当前页面的完整 URL去掉#后面的部分而且要在进入页面时就传给后端不要在异步路由跳转后再生成。3.2 小程序端登录、手机号与订阅消息小程序登录流程是wx.login拿 code后端换 openid 和 session_key。新版小程序还可以用手机号快捷验证组件直接在前端拉起微信官方弹窗获取手机号替代「账号 密码 短信验证码」的传统流程。!-- 小程序页面里引入手机号验证组件 -- button open-typegetPhoneNumber bindgetphonenumberonGetPhone 绑定手机号 /buttonPage({ async onGetPhone(e) { if (e.detail.errMsg ! getPhoneNumber:ok) return; // 把 code 发给后端后端用 code 换取手机号 const { phone } await request(/api/user/bind_phone, { code: e.detail.code }); this.setData({ phone }); } });后端换手机号用的是phonenumber.getPhoneNumber接口需要 access_token注意这个接口有频率限制不能每次都调。订阅消息的触发点也要规划好业主提交报修后询问是否订阅「进度通知」而不是一进小程序就弹订阅框。3.3 PC 管理端权限模型与操作审计PC 端给物业经理、客服、财务、保安队长用核心是 RBAC 权限模型。表设计上建议菜单权限只控制「页面是否可见」按钮级权限用permission_code字符串控制。一个常见的坑是前端根据角色隐藏按钮后端接口不校验懂技术的物业人员绕过界面直接调接口就能越权。// Java Spring Boot 示例接口级权限校验 PreAuthorize(hasPermission(property:refund:audit)) PostMapping(/api/refund/audit) public Result audit(RequestBody AuditRequest req) { // 只有财务角色拥有 property:refund:audit 权限码 refundService.audit(req.getRefundId(), req.getResult()); return Result.ok(); }PC 端还要做操作审计。谁在什么时间审核了哪笔缴费、谁把哪套房的业主信息改了都要可追溯建议落一张独立的operation_log表和业务表分开存储避免业务表过大影响查询。3.4 智能硬件接入MQTT 上报与下发门禁、道闸这类设备主流接入方案是 MQTT over TLS。设备端保持长连接心跳 30 秒一次业务系统通过订阅设备 topic 接收事件通过发布指令 topic 下发命令。Topic 设计建议按物模型分层Topic方向作用iot/{deviceNo}/event设备 - 云端上报开门记录、故障、心跳iot/{deviceNo}/command云端 - 设备远程开门、重启、参数下发iot/{deviceNo}/response设备 - 云端指令执行结果回执门禁上报事件时payload 里带上event_id做幂等。设备可能因为网络抖动重发消息业务端消费时用event_id查重避免一条开门记录被记成两次。{ eventId: uuid-abc-123, deviceNo: DJ-001, eventType: OPEN_DOOR, timestamp: 1710000000, data: { method: CARD, identifier: A12345, result: success, errorCode: } }消费端收到事件后根据identifier反查业主信息把开门记录写入访问日志同时触发对应的业务动作比如夜间陌生人开门推送提醒。3.5 H5 端的独立场景访客邀请与缴费分享H5 除了嵌在公众号里还有一个应用场景是业主把缴费单或访客邀请链接分享给非业主的访客。访客点开链接时没有微信授权也不需要登录。访客邀请链接建议用短时效 token例如 30 分钟有效携带visitor_code参数H5 页面只展示二维码和剩余有效时间。4. 三个核心业务闭环在多端之间的流转身份和接入搞定之后真正体现智慧物业价值的是报修、缴费、访客通行这几条业务链路能不能跨端无缝流转。4.1 报修工单业主端提交、物业端派单、PC 端监管业主在小程序或公众号里提交报修选择房号、问题类型、上传图片或短视频。后端生成工单后物业人员的小程序端或 PC 端都能看到待办。这里的关键设计是工单状态机的统一待受理 - 已派单 - 处理中 - 待验收 - 已完成 \- 已驳回业主端的「取消报修」操作只在「待受理」和「已派单」两个状态允许物业端的「驳回」必须填写原因并触发订阅消息通知业主。PC 端管理台展示的是所有工单的流转记录和时间节点而不是只显示当前状态这样出了问题可以回溯是哪一环卡住了。4.2 缴费公众号收单、小程序查明细、PC 管对账微信支付在公众号 H5 和小程序里用的是不同的下单接口。公众号里用 JSAPI 下单openid取的是公众号授权登录的 openid小程序里也用 JSAPI 支付但openid换成小程序身份的 openid。后端在下单时一定要从当前登录态的app_type判断用哪个 openid否则会出现「公众号付了款小程序订单状态没变」的诡异问题。// 后端下单伪代码 function createPaymentOrder(user) { const order createLocalOrder(user.userId, amount); const payParams { outTradeNo: order.orderNo, body: 物业费, totalFee: amount * 100, openid: user.openid, // 来自当前请求的 app_type tradeType: JSAPI }; const payResult wxPay.unifiedOrder(payParams); return payResult; }缴费完成后的对账建议每天凌晨拉取微信支付账单和本地订单表比对。对不上时把差异记录写进recon_difference表由财务在 PC 端人工处理。4.3 访客通行H5 生成码、门禁验证、消息回调访客通行的完整链路是业主在小程序里录入访客车牌或手机号系统生成访客码访客到小区门口时保安在门禁一体机上输入访客车牌或者访客自己扫二维码通行。这个场景跨了小程序业主端、硬件门禁识别、公众号/小程序消息通知三个端。门禁设备验证通过后通过 MQTT 上报事件后端消费事件后写入访客通行记录调用微信订阅消息通知业主「访客已进入」摄像头抓拍的照片推送给业主小程序注意访客码要区分「一次性码」和「时段码」。一次性码验一次就作废时段码在有效期内可多次通行适合家政保洁人员每天固定时间上门。5. 多端联调与线上排错的几个实用技巧多端系统最耗时间的不是开发而是联调。公众号回调、硬件推送、支付回调各自有各自的调试方式这里分享几个直接能用的经验。5.1 内网穿透调试微信回调微信公众平台配置的回调 URL 必须是公网可达地址。本地开发时常见做法是用内网穿透工具把本机服务映射到公网临时域名。注意微信回调要求 80 或 443 端口穿透工具分配的端口如果不是这两个要在后台把回调地址改成带端口的完整 URL。# 本地启动服务监听 8080 # 穿透到公网得到 https://xxx.tunnel.com # 在微信公众平台网页授权域名/服务器URL里填 https://xxx.tunnel.com/api/wechat改完配置后用微信开发者工具打开公众号 H5 页面如果不能获取 code先检查「网页授权域名」和「JS 接口安全域名」是否都配置了这两个域名容易搞混。5.2 硬件设备与服务器的时间同步问题硬件设备离线一段时间后再上报它的本地时间很可能和服务器时间偏差很大。如果业务端直接用上报时间做统计财务报表会错。建议设备上报 payload 里带timestamp的同时服务端记录ingest_time网关收到时间两个字段都存。统计报表用ingest_time设备状态判断用timestamp。5.3 在微信浏览器和 App WebView 里调试 H5PC 端 Chrome 的 F12 在微信内置浏览器里不适用。页面上引入 vConsole 是一个快捷方案它会直接在 H5 页面里生成一个悬浮调试按钮查看 console 日志和网络请求。!-- 只在测试环境引入 vConsole -- script srchttps://unpkg.com/vconsole/dist/vconsole.min.js/script script if (location.href.includes(debug1)) { new VConsole(); } /script生产环境一定不要带debug1参数否则用户也能看到调试面板。另一个技巧是处理「真机正常、微信开发者工具异常」的问题这类问题 90% 是user-agent差异导致的前端兼容性 bug优先排查 CSSposition: fixed和100vh相关的渲染。5.4 多端发布顺序建议每次版本迭代建议按「后端 - 硬件固件 - 小程序 - 公众号 H5 - PC 端」的顺序发布。后端先行保证接口兼容旧版客户端小程序有微信审核周期要提前提审公众号 H5 和 PC 端是网页应用随时可以发布。硬件固件的升级要谨慎最好支持灰度发布先升级一栋楼的门禁确认稳定后再全量推送。本文还有配套的精品资源点击获取