From bcf5fa868cd12e6121ee00c54677250609c811e8 Mon Sep 17 00:00:00 2001
From: dzc <2388224167@qq.com>
Date: Mon, 31 Aug 2026 15:04:30 +0800
Subject: [PATCH] =?UTF-8?q?feat:=E9=80=9A=E7=9F=A5=E6=B6=88=E6=81=AF?=
=?UTF-8?q?=E6=8E=88=E6=9D=83=E4=BF=AE=E6=94=B9?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
.env | 8 +--
AGENTS.md | 82 ++++++++++++++++++++++++++
src/App.vue | 20 +++++--
src/pages/order/daily-menu-confirm.vue | 7 ++-
src/sheep/utils/permission.ts | 13 ++--
5 files changed, 114 insertions(+), 16 deletions(-)
create mode 100644 AGENTS.md
diff --git a/.env b/.env
index c14ef26..3d3dc0b 100644
--- a/.env
+++ b/.env
@@ -33,15 +33,15 @@ VITE_OAUTH2_SOCIAL_CLIENT='social:social'
# 是否开启websocket 消息接受,
VITE_WEBSOCKET_ENABLE = true
# --------------------------- start 开发环境 start ----------------------------------
-VITE_APP_DEV_SERVICE = https://www.zianxin.com/api
+# VITE_APP_DEV_SERVICE = https://www.zianxin.com/api
# VITE_APP_DEV_SERVICE = https://dzc-test-1.fy.takin.cc
# VITE_APP_DEV_SERVICE = http://127.0.0.1:9999
# VITE_APP_DEV_SERVICE = https://www.zianxin.com/api
-# VITE_APP_DEV_SERVICE = https://dzc-test-1.fy.takin.cc
+VITE_APP_DEV_SERVICE = https://dzc-test-1.fy.takin.cc
#VITE_APP_DEV_SERVICE = http://127.0.0.1:9999
-VITE_IMAGE_DEV_PATH = https://www.zianxin.com/api
-# VITE_IMAGE_DEV_PATH = https://dzc-test-1.fy.takin.cc
+# VITE_IMAGE_DEV_PATH = https://www.zianxin.com/api
+VITE_IMAGE_DEV_PATH = https://dzc-test-1.fy.takin.cc
# VITE_IMAGE_DEV_PATH = http://127.0.0.1:9999
# VITE_IMAGE_DEV_PATH = https://www.zianxin.com/api
# VITE_IMAGE_DEV_PATH = https://dzc-test-1.fy.takin.cc
diff --git a/AGENTS.md b/AGENTS.md
new file mode 100644
index 0000000..68b3801
--- /dev/null
+++ b/AGENTS.md
@@ -0,0 +1,82 @@
+# `biz_zax_app_cloud` 开发规则
+
+> 适用于 uni-app 移动端项目。执行任务前必须先完整阅读 [HQ Platform 通用规则](../agents/common.md),并继续检查目标目录内更具体的说明和现有同类实现。
+
+## 技术栈基线与平台范围
+
+以下版本是当前项目扫描结果,后续以 `package.json`、`src/uni_modules/tm-ui/package.json` 和锁文件为准。
+
+- 应用框架:uni-app Vue 3,DCloud 依赖版本为 `3.0.0-5000720260410001`,应用由 `createSSRApp` 创建。
+- 基础运行时:Vue `3.4.x`、TypeScript `4.9.x`、Vite `5.2.8`。
+- UI 框架:项目内置 uni_modules 版 tm-ui `3.2.0`,Vue 3 + TypeScript,支持 App Vue 与 H5;本地组件描述明确不支持 App NVUE,因此使用 NVUE 前必须单独核对组件兼容性。
+- 样式体系:UnoCSS `0.58.9`、`unocss-preset-weapp`、Sass。UnoCSS 已启用 `whRpx`、Attributify 和 class transformer。
+- 状态管理:Pinia `3.0.x` 与 `pinia-plugin-persistedstate`,持久化适配器使用 `uni.getStorageSync` / `uni.setStorageSync`,不得直接替换为浏览器 `localStorage`。
+- 网络层:`luch-request`,统一封装位于 `src/sheep/utils/request.ts`,负责 H5/App Base URL、Token、Token 刷新、租户头、TOC 头、请求/响应加解密、登录过期跳转和统一提示。
+- 路由:以 `src/pages.json` 为页面与分包真源,通过 Vite 路由插件读取 `meta`,业务跳转统一使用 `src/sheep/router` 对 `uni.navigateTo`、`switchTab`、`redirectTo`、`reLaunch` 的封装。
+- 列表与数据展示:`z-paging` 用于分页列表;`@qiun/uni-ucharts` 和本地 qiun/uCharts 组件用于跨端图表。
+- 图形能力:用户关系树使用 `@antv/hierarchy` 的 `compactBox` 布局;不要把 PC 端 `@vue-flow` 直接搬到移动端。
+- 动效与工具:Lottie Web、Day.js、Radash、CryptoJS、Base64 等已经存在,使用前先检查跨端封装。
+- 目标平台:**iOS App、Android App、H5**。项目虽保留多个小程序构建依赖和脚本,但当前需求默认不以小程序为验收目标,除非用户另行指定。
+
+## 关键目录与入口
+
+- `src/main.ts`:创建应用,加载 `uno.css`,注册 Pinia 和 tm-ui。
+- `src/App.vue`:应用生命周期、启动逻辑、App 平台推送/权限初始化、全局状态联动等。
+- `src/pages`:实际页面,包含登录、用户、食堂、商城、订单、钱包、配送、门禁/人脸、商户和管理等业务。
+- `src/pages.json`:页面、分包、导航栏、TabBar 和 Easycom 配置。新增页面必须同步登记,优先放入对应业务分包。
+- `src/sheep/api`:移动端接口层;页面不得直接散落 `uni.request` 或新建请求实例。
+- `src/sheep/components`:基础组件、CRUD 组件和业务公共组件;Easycom 已将 `base-*`、`crud-*` 自动映射到此处。
+- `src/sheep/hooks`:页面与列表公共逻辑;新页面应先搜索分页、状态和业务 Hook。
+- `src/sheep/stores`:用户、TabBar、购物车、支付、推送等 Pinia Store。
+- `src/sheep/router`:统一路由跳转、TabBar 判断、防重复跳转和返回处理。
+- `src/sheep/utils`:请求、环境、加解密、文件、支付、推送、平台跳转等工具。
+- `src/uni_modules/tm-ui`:项目实际使用的 TMUI 源码与组件,不得直接修改第三方组件来解决单页问题,除非明确要求进行全局修复。
+- `src/static/app-plus` 与 `src/static/h5`:平台专属资源;共用资源放在通用 `src/static` 下。
+- `vite.config.ts`:`@` 指向 `src`,`@@` 指向 `src/sheep`;接入 uni、UnoCSS、路由插件和 IIFE 构建兼容处理,开发服务端口为 `8889`。
+
+## UI 与 UnoCSS 约定
+
+- `src/pages.json` 已通过 Easycom 自动映射 `tm-*`、`base-*`、`crud-*` 和 `z-paging*`,优先直接使用这些既有组件命名。
+- 修改前必须检查 `unocss.config.ts`。当前已有 `flex-col-center`、`flex-row-center`、`flex-col`、`flex-row`、`border-base` shortcuts,以及 `theme-text-*`、`main-text-*`、`sub-text-*`、`second-text-*`、`show-line-*`、`card`、`shadow-main` 等规则。
+- `whRpx: true` 会把宽高相关原子值按 rpx 体系处理。新增尺寸前先理解现有类的实际输出,避免把 px、rpx 和设计稿数值混用。
+- 普通布局、间距、字号、圆角、颜色、截断优先用 UnoCSS;只有平台差异、动态计算、第三方组件深层覆盖或复杂动画才使用局部 SCSS/CSS。
+- UI 组件优先使用项目内 tm-ui 与 `sheep/components` 封装。需要核对 API 时参考 与本地组件源码,不能凭其他 UI 框架经验猜测属性和事件。
+- 页面视觉应延续同业务现有风格,尤其是顶栏、安全区、卡片密度、列表行高、按钮尺寸、表单校验、弹层和加载/空状态。
+
+## 请求、状态与路由约定
+
+- 所有业务请求通过 `src/sheep/utils/request.ts` 和 `src/sheep/api` 发起;不得绕过现有 Token 刷新、请求加密、租户和错误处理。
+- H5 的 Base URL 从 `VITE_API_URL` 读取,非 H5 由 `getBaseApiUrl()` 根据开发/生产环境读取服务地址;修改环境逻辑前必须同时核对两条路径。
+- Token 与用户信息使用项目 storage 常量和 Pinia 持久化,不得另建同义 Key。
+- 页面跳转优先使用 `@@/router`,保持 TabBar、节流、防重复跳转和无历史返回逻辑一致。
+- 新增页面时先判断属于主包还是现有分包,避免扩大主包;页面路径、TabBar 路径和路由辅助逻辑必须保持一致。
+
+## 原生与跨平台能力
+
+- `src/manifest.json` 已配置 Push、Payment、OAuth、Share、VideoPlayer、Maps、Barcode、Camera 等 App 模块,以及 Android/iOS 权限、Universal Links、支付、地图和推送配置。
+- 不得随意修改 AppID、包名、Bundle ID、证书、Universal Links、推送 AppKey、支付参数、地图 Key、权限或隐私描述。需求涉及这些配置时先说明影响并取得确认。
+- App 生命周期与推送初始化已有 `APP-PLUS` 条件编译;新增平台代码必须沿用 `#ifdef` / `#ifndef`,并提供 H5 或另一移动平台的合理降级。
+- H5 专属 DOM、Lottie 或浏览器 API 必须隔离;App 原生插件、`plus` API 和权限请求也必须隔离。共享模块不能在导入阶段直接访问单平台全局对象。
+- 必须检查安全区域、状态栏、底部手势区、软键盘、页面滚动、返回行为、触摸目标和不同屏宽。
+
+## 常用命令与验证
+
+- H5 开发:`pnpm dev:h5`。
+- H5 构建:`pnpm build:h5`。
+- 类型检查:`pnpm type-check`。
+- App 真机与发行包按项目现有 HBuilderX / uni-app 工作流执行;不得把 H5 构建成功等同于 iOS、Android 已验证。
+- 涉及条件编译、原生权限、支付、推送、地图、相机或扫码时,必须分别核对 Android、iOS 与 H5 路径,并如实说明哪些平台只做了静态检查。
+
+## 开发规则
+
+- 修改前必须查看 `unocss.config.ts`、`vite.config.ts`、`src/pages.json`、`src/manifest.json`、全局样式和同类页面,确认已有快捷类、主题、页面配置与平台配置。
+- UI 组件优先使用项目内现有 tm-ui 组件和封装,并遵循当前项目的组件调用方式;需要确认组件能力时参考 TMUI 文档,不凭印象编造属性或事件。
+- 常规样式优先使用 UnoCSS 原子类和项目已有 shortcuts/rules,不重复写可被原子类表达的 scoped CSS。
+- 所有页面和功能必须同时考虑 iOS、Android、H5,不得只按单一平台实现。涉及平台能力差异时,使用 uni-app 官方能力或规范的条件编译,并为不支持的平台提供合理降级。
+- 注意安全区域、状态栏、导航栏、底部操作区、键盘顶起、滚动容器、触摸区域、单位选择和横竖屏/不同屏宽下的表现。
+- 禁止直接使用仅浏览器可用的 DOM/BOM API 或仅 App 可用的原生能力而不做平台隔离。
+- 日常修改不自动执行 H5 或 App 构建;收到用户明确的集中验证指令后,再检查 H5 构建,并按改动范围核对 iOS、Android 分支及相关配置,明确说明实际验证范围。
+
+## 完成前项目检查
+
+- [ ] 移动端改动已考虑 iOS、Android、H5 适配。
diff --git a/src/App.vue b/src/App.vue
index ebc1e05..08d15b4 100644
--- a/src/App.vue
+++ b/src/App.vue
@@ -10,6 +10,9 @@ import jgPush from "@/sheep/utils/jg-push"
import { consumePendingPushRoute } from "@/sheep/utils/push-route"
import { showPermissionUsage } from "@/sheep/utils/permission"
+/** 通知权限用途说明已由用户处理过的本地标记,避免未授权时每次冷启动重复弹窗。 */
+const PUSH_PERMISSION_USAGE_HANDLED_STORAGE_KEY = "push_permission_usage_handled_v1"
+
export default {
data() {
return {
@@ -36,11 +39,18 @@ export default {
pushStatus.notificationPermission === "granted" ||
pushStatus.notificationPermission === "provisional" ||
pushStatus.notificationEnabled === true
- if (!pushPermissionGranted) {
- const shouldRequestPushPermission = await showPermissionUsage("通知", {
- feature: "消息通知",
- purpose: "用于接收订单、配送、核销和系统服务状态等重要消息提醒。",
- })
+ const pushPermissionUsageHandled = Boolean(uni.getStorageSync(PUSH_PERMISSION_USAGE_HANDLED_STORAGE_KEY))
+ if (!pushPermissionGranted && !pushPermissionUsageHandled) {
+ const shouldRequestPushPermission = await showPermissionUsage(
+ "通知",
+ {
+ feature: "消息通知",
+ purpose: "用于接收订单、配送、核销和系统服务状态等重要消息提醒。",
+ },
+ "去授权",
+ )
+ // 用户确认或取消都视为已完成一次选择,后续由用户在系统设置中自行调整通知权限。
+ uni.setStorageSync(PUSH_PERMISSION_USAGE_HANDLED_STORAGE_KEY, true)
if (shouldRequestPushPermission) {
if (this.system.platform === "android") {
await jgPush.requestAndroidPermission()
diff --git a/src/pages/order/daily-menu-confirm.vue b/src/pages/order/daily-menu-confirm.vue
index 3b38830..cfca7a4 100644
--- a/src/pages/order/daily-menu-confirm.vue
+++ b/src/pages/order/daily-menu-confirm.vue
@@ -12,8 +12,7 @@
+ :allowed-identity-types="allowedIdentityTypes" @open="openDrawer" />